Skip to main content
Building m87 from source gives you the latest development features and allows you to customize the build for your specific needs.

Prerequisites

Before building m87, ensure you have the required tools installed.

Required Tools

1

Rust 1.85 or newer

m87 requires Rust 1.85 or later. Install or update Rust using rustup:
# Install rustup (if not already installed)
curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh

# Update to latest stable
rustup update stable

# Verify version
rustc --version
Expected output: rustc 1.85.0 or higher.
2

Git

Git is required to clone the repository:
# Verify git is installed
git --version

# Install if needed (Debian/Ubuntu)
sudo apt-get install git

# Install if needed (macOS)
brew install git
3

System Dependencies

Install system dependencies required for compilation:Debian/Ubuntu:
sudo apt-get update
sudo apt-get install build-essential pkg-config libssl-dev
Fedora/RHEL:
sudo dnf install gcc pkg-config openssl-devel
macOS:
# Xcode Command Line Tools
xcode-select --install

Quick Build

For most users, the standard build process is:
git clone https://github.com/make87/m87.git
cd m87
cargo build --release
The compiled binary will be at target/release/m87.

Detailed Build Instructions

1

Clone the repository

Clone the m87 repository from GitHub:
git clone https://github.com/make87/m87.git
cd m87
To build a specific version:
git clone https://github.com/make87/m87.git
cd m87
git checkout v0.x.x  # Replace with desired version
2

Build the project

Build the release version:
cargo build --release
This compiles m87 with full optimizations. The build process may take several minutes.
The --release flag enables optimizations and produces a smaller, faster binary. Development builds (without --release) are faster to compile but slower to run.
3

Locate the binary

After compilation, the binary is located at:
ls -lh target/release/m87
4

Install the binary

Copy the binary to a directory in your PATH:
# Copy to user bin directory
cp target/release/m87 ~/.local/bin/

# Or copy to system bin directory (requires sudo)
sudo cp target/release/m87 /usr/local/bin/

# Verify installation
m87 --version
Ensure ~/.local/bin is in your PATH. Add to your shell profile if needed:
export PATH="$HOME/.local/bin:$PATH"

Build Options

Building Specific Components

The m87 workspace contains multiple packages. You can build specific components: Build only the CLI:
cargo build --release -p m87-client
Build only shared libraries:
cargo build --release -p m87-shared
Build server components (AGPL license):
cargo build --release -p m87-server

Platform-Specific Builds

Build configuration is automatically detected based on your operating system:
  • Linux: Full functionality (CLI + runtime)
  • macOS: CLI only (runtime not available)
The m87 runtime only runs on Linux. macOS builds include the CLI commands but exclude runtime functionality.

Development Build

For faster compilation during development:
cargo build
Development builds:
  • Compile faster (~50% faster)
  • Include debug symbols
  • No optimizations (significantly slower at runtime)
  • Located at target/debug/m87
Development builds are not suitable for production use due to reduced performance.

Build Configuration

The build is configured via Cargo.toml in the workspace root.

Release Profile Settings

The release profile is optimized for performance and minimal binary size:
[profile.release]
opt-level = 3              # Maximum optimization
lto = "fat"                # Full link-time optimization
codegen-units = 1          # Better optimization (slower compile)
strip = true               # Strip debug symbols
These settings produce:
  • Smaller binary size (~40-60% reduction)
  • Better runtime performance
  • Longer compilation time
  • No debug symbols (use strip = false if needed)

Custom Build Profiles

Create a custom profile for specific needs:
# Fast compile, some optimization
cargo build --profile dev-opt
Add to Cargo.toml:
[profile.dev-opt]
inherits = "dev"
opt-level = 2

Cross-Compilation

Build for different architectures using cross-compilation.

Setup Cross-Compilation

Install the target architecture:
# For ARM64 (aarch64)
rustup target add aarch64-unknown-linux-gnu

# For ARMv7 (32-bit ARM)
rustup target add armv7-unknown-linux-gnueabihf

# For x86_64 Linux (from macOS)
rustup target add x86_64-unknown-linux-gnu

Build for Target Architecture

# Build for ARM64
cargo build --release --target aarch64-unknown-linux-gnu

# Binary location
ls target/aarch64-unknown-linux-gnu/release/m87

Using cross for Easy Cross-Compilation

For easier cross-compilation, use the cross tool:
# Install cross
cargo install cross

# Build for ARM64 using Docker
cross build --release --target aarch64-unknown-linux-gnu

# Build for ARMv7
cross build --release --target armv7-unknown-linux-gnueabihf
cross uses Docker to provide a complete cross-compilation environment, eliminating the need for target-specific system dependencies.

Building with Docker

Build m87 inside a Docker container for a consistent environment.
1

Build the Docker image

git clone https://github.com/make87/m87.git
cd m87
docker build -f m87-client/Dockerfile -t m87 .
2

Run m87 from the container

docker run -it --rm \
  --user "$(id -u):$(id -g)" \
  -v "$HOME/.config/m87:/.config/m87" \
  -e HOME=/ \
  m87 --version
3

Create a shell alias

Add to your ~/.bashrc or ~/.zshrc:
alias m87='docker run -it --rm --user "$(id -u):$(id -g)" -v "$HOME/.config/m87:/.config/m87" -e HOME=/ m87'
Now use m87 as usual:
m87 login
m87 devices list

Optimizing Build Times

Use Cargo Cache

Cargo caches dependencies. Keep them updated:
cargo update

Parallel Compilation

Increase parallel jobs (default is number of CPU cores):
cargo build --release -j 8

Use sccache

Distributed compilation cache:
# Install sccache
cargo install sccache

# Configure
export RUSTC_WRAPPER=sccache

# Build
cargo build --release

# Check cache stats
sccache --show-stats

Incremental Compilation

Enabled by default for dev builds, disabled for release. Enable for faster release builds:
[profile.release]
incremental = true
Incremental compilation may produce slightly larger binaries.

Verifying the Build

1

Check binary size

ls -lh target/release/m87
Expected size: 10-30 MB depending on platform and optimization.
2

Run basic commands

./target/release/m87 --version
./target/release/m87 --help
3

Test authentication

./target/release/m87 login
./target/release/m87 devices list
4

Compare with official binary

Compare behavior with the official release to ensure consistency.

Development Workflow

For active development:
# Watch for changes and rebuild automatically
cargo install cargo-watch
cargo watch -x 'build --release'

# Run tests
cargo test

# Run tests with output
cargo test -- --nocapture

# Check for issues without building
cargo check

# Format code
cargo fmt

# Lint with clippy
cargo clippy -- -D warnings

Troubleshooting Build Issues

Error: package requires rustc 1.85 or newerSolution:
rustup update stable
rustc --version
Error: could not find native static librarySolution: Install required system libraries:
# Debian/Ubuntu
sudo apt-get install build-essential pkg-config libssl-dev

# Fedora/RHEL
sudo dnf install gcc pkg-config openssl-devel

# macOS
xcode-select --install
Error: linking with 'cc' failedSolution: Ensure you have a C compiler installed:
# Check compiler
cc --version
gcc --version

# Install if missing
sudo apt-get install build-essential  # Debian/Ubuntu
Error: No space left on deviceSolution: Cargo builds can use significant disk space. Clean old builds:
cargo clean
rm -rf ~/.cargo/registry/cache
Problem: Build takes too long.Solutions:
  • Use development build instead: cargo build (no --release)
  • Enable incremental compilation
  • Use sccache for caching
  • Increase parallel jobs: cargo build -j 8

Next Steps

After building from source:
  1. Install the binary: Copy to ~/.local/bin or /usr/local/bin
  2. Set up development environment: Run m87 login and connect a device
  3. Contribute: Submit improvements via GitHub pull requests

Contributing

Contributions are welcome! Before submitting:
# Format code
cargo fmt

# Check for issues
cargo clippy

# Run tests
cargo test

# Build release binary
cargo build --release
See the Contributing Guide for more details.
The m87-client and m87-shared packages are licensed under Apache-2.0. The m87-server package is licensed under AGPL-3.0-or-later.