diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 1b3c0f0..7792bc8 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -166,6 +166,67 @@ jobs: # Run the image - should automatically select the right architecture docker run --rm $IMAGE_REF + # Test extended platform support + extended-platforms: + name: Extended Platform Support + runs-on: ubuntu-latest + needs: [test] # Only run after basic tests pass + steps: + - uses: actions/checkout@v4 + - name: Install Rust + uses: dtolnay/rust-toolchain@stable + with: + targets: x86_64-unknown-linux-musl,i686-unknown-linux-musl,aarch64-unknown-linux-musl,armv7-unknown-linux-musleabihf + - name: Install cross-compilation tools + run: | + sudo apt-get update + sudo apt-get install -y musl-tools gcc-multilib + - name: Setup cargo config + run: | + mkdir -p .cargo + cat > .cargo/config.toml << 'EOF' + [target.x86_64-unknown-linux-musl] + linker = "x86_64-linux-musl-gcc" + + [target.i686-unknown-linux-musl] + linker = "musl-gcc" + rustflags = ["-C", "target-cpu=i686"] + + [target.aarch64-unknown-linux-musl] + linker = "aarch64-linux-gnu-gcc" + + [target.armv7-unknown-linux-musleabihf] + linker = "arm-linux-gnueabihf-gcc" + EOF + - name: Build krust + run: cargo build --release + - name: Test multi-platform build with Alpine base + run: | + # Create a test project that uses Alpine (which supports many platforms) + mkdir -p test-alpine-platforms/src + cat > test-alpine-platforms/Cargo.toml << 'EOF' + [package] + name = "test-alpine" + version = "0.1.0" + edition = "2021" + + [package.metadata.krust] + base-image = "alpine:latest" + EOF + cat > test-alpine-platforms/src/main.rs << 'EOF' + fn main() { + println!("Hello from Alpine multi-platform test!"); + } + EOF + + # Test that platform detection works (even if we can't build all platforms) + cd test-alpine-platforms + ../target/release/krust build --no-push --image test.local/alpine-test:latest . 2>&1 | tee build.log + + # Verify platform detection happened + grep -q "Detecting available platforms from base image: alpine:latest" build.log + grep -q "Found platforms:" build.log + # Takes too long to run on CI, so it's commented out for now. # coverage: # name: Code coverage diff --git a/README.md b/README.md index dbe8f77..01087ce 100644 --- a/README.md +++ b/README.md @@ -42,6 +42,32 @@ rustup target add aarch64-unknown-linux-musl # For linux/arm/v7 rustup target add armv7-unknown-linux-musleabihf + +# For linux/arm/v6 +rustup target add arm-unknown-linux-musleabihf + +# For linux/386 +rustup target add i686-unknown-linux-musl + +# For linux/ppc64le +rustup target add powerpc64le-unknown-linux-musl + +# For linux/s390x +rustup target add s390x-unknown-linux-musl + +# For linux/riscv64 +rustup target add riscv64gc-unknown-linux-musl + +# Or install all supported targets at once +rustup target add \ + x86_64-unknown-linux-musl \ + aarch64-unknown-linux-musl \ + armv7-unknown-linux-musleabihf \ + arm-unknown-linux-musleabihf \ + i686-unknown-linux-musl \ + powerpc64le-unknown-linux-musl \ + s390x-unknown-linux-musl \ + riscv64gc-unknown-linux-musl ``` #### macOS Cross-compilation Setup @@ -52,6 +78,9 @@ On macOS, you'll need a cross-compilation toolchain: # Install musl cross-compilation tools brew install filosottile/musl-cross/musl-cross +# Note: The musl-cross formula typically only includes x86_64 and aarch64 toolchains. +# For other architectures, you may need additional toolchains or use Docker/remote builders. + # Create a .cargo/config.toml in your project with: cat > .cargo/config.toml << 'EOF' [target.x86_64-unknown-linux-musl] @@ -59,6 +88,11 @@ linker = "x86_64-linux-musl-gcc" [target.aarch64-unknown-linux-musl] linker = "aarch64-linux-musl-gcc" + +# For other architectures, you'll need to install the appropriate cross-compiler +# or use cargo-zigbuild which can target all platforms: +# cargo install cargo-zigbuild +# Then build with: cargo zigbuild --target EOF ``` @@ -125,6 +159,11 @@ krust build -- --features=prod - `linux/amd64` (x86_64-unknown-linux-musl) - `linux/arm64` (aarch64-unknown-linux-musl) - `linux/arm/v7` (armv7-unknown-linux-musleabihf) +- `linux/arm/v6` (arm-unknown-linux-musleabihf) +- `linux/386` (i686-unknown-linux-musl) +- `linux/ppc64le` (powerpc64le-unknown-linux-musl) +- `linux/s390x` (s390x-unknown-linux-musl) +- `linux/riscv64` (riscv64gc-unknown-linux-musl) ### Multi-Architecture Images @@ -320,9 +359,21 @@ cd krust brew install messense/macos-cross-toolchains/x86_64-unknown-linux-musl brew install messense/macos-cross-toolchains/aarch64-unknown-linux-musl -# Install Rust targets +# For full platform support, consider using cargo-zigbuild: +cargo install cargo-zigbuild + +# Install Rust targets (at minimum for tests) rustup target add x86_64-unknown-linux-musl -rustup target add aarch64-unknown-linux-musl # Optional, for ARM64 support +rustup target add aarch64-unknown-linux-musl + +# For full platform support, add all targets: +rustup target add \ + armv7-unknown-linux-musleabihf \ + arm-unknown-linux-musleabihf \ + i686-unknown-linux-musl \ + powerpc64le-unknown-linux-musl \ + s390x-unknown-linux-musl \ + riscv64gc-unknown-linux-musl # Install pre-commit hooks pip install pre-commit diff --git a/src/builder/mod.rs b/src/builder/mod.rs index 538e4c6..a7c097c 100644 --- a/src/builder/mod.rs +++ b/src/builder/mod.rs @@ -191,6 +191,11 @@ pub fn get_rust_target_triple(platform: &str) -> Result { "linux/amd64" => Ok("x86_64-unknown-linux-musl".to_string()), "linux/arm64" => Ok("aarch64-unknown-linux-musl".to_string()), "linux/arm/v7" => Ok("armv7-unknown-linux-musleabihf".to_string()), + "linux/arm/v6" => Ok("arm-unknown-linux-musleabihf".to_string()), + "linux/386" => Ok("i686-unknown-linux-musl".to_string()), + "linux/ppc64le" => Ok("powerpc64le-unknown-linux-musl".to_string()), + "linux/s390x" => Ok("s390x-unknown-linux-musl".to_string()), + "linux/riscv64" => Ok("riscv64gc-unknown-linux-musl".to_string()), _ => anyhow::bail!("Unsupported platform: {}", platform), } } diff --git a/src/builder/tests.rs b/src/builder/tests.rs index e9bc397..8aa0c08 100644 --- a/src/builder/tests.rs +++ b/src/builder/tests.rs @@ -16,6 +16,26 @@ mod tests { get_rust_target_triple("linux/arm/v7").unwrap(), "armv7-unknown-linux-musleabihf" ); + assert_eq!( + get_rust_target_triple("linux/arm/v6").unwrap(), + "arm-unknown-linux-musleabihf" + ); + assert_eq!( + get_rust_target_triple("linux/386").unwrap(), + "i686-unknown-linux-musl" + ); + assert_eq!( + get_rust_target_triple("linux/ppc64le").unwrap(), + "powerpc64le-unknown-linux-musl" + ); + assert_eq!( + get_rust_target_triple("linux/s390x").unwrap(), + "s390x-unknown-linux-musl" + ); + assert_eq!( + get_rust_target_triple("linux/riscv64").unwrap(), + "riscv64gc-unknown-linux-musl" + ); assert!(get_rust_target_triple("windows/amd64").is_err()); } } diff --git a/src/registry/mod.rs b/src/registry/mod.rs index 68145e1..a88d292 100644 --- a/src/registry/mod.rs +++ b/src/registry/mod.rs @@ -234,7 +234,12 @@ impl RegistryClient { let normalized = match platform.as_str() { "linux/amd64" => Some("linux/amd64".to_string()), "linux/arm64" | "linux/arm64/v8" => Some("linux/arm64".to_string()), - "linux/arm/v6" | "linux/arm/v7" => Some("linux/arm/v7".to_string()), + "linux/arm/v7" => Some("linux/arm/v7".to_string()), + "linux/arm/v6" => Some("linux/arm/v6".to_string()), + "linux/386" => Some("linux/386".to_string()), + "linux/ppc64le" => Some("linux/ppc64le".to_string()), + "linux/s390x" => Some("linux/s390x".to_string()), + "linux/riscv64" => Some("linux/riscv64".to_string()), _ => { debug!("Skipping unsupported platform: {}", platform); None