cross-rs / cross-toolchains

Additional Dockerfiles and crosstool-ng config files to build additional toolchains.
Apache License 2.0
88 stars 16 forks source link

Avoid critical config in the entrypoint (ignored by `CROSS_REMOTE=1`) #31

Open demurgos opened 1 year ago

demurgos commented 1 year ago

During this week, I configured my repo to use GitLab CI to cross-compile to Mac (target x86_64-apple-darwin). I figured it out in the end, but it was a bit tricky.

First of all, I followed the help in this issue which was very helpful. This let me cross compile to ARM. In particular, I've set CROSS_REMOTE=1.

The issue I've hit was that I had ring as a dependency, and it failed to compile in GitLab CI. This was because it used the Linux compiler instead of the the one from osxcross (cc: error: unrecognized command line option '-arch').

Full ring error ```txt error: failed to run custom build command for `ring v0.16.20` Caused by: process didn't exit successfully: `/cross/project/target/release/build/ring-719859dcd2b78047/build-script-build` (exit status: 101) --- stdout OPT_LEVEL = Some("z") TARGET = Some("x86_64-apple-darwin") HOST = Some("x86_64-unknown-linux-gnu") cargo:rerun-if-env-changed=CC_x86_64-apple-darwin CC_x86_64-apple-darwin = None cargo:rerun-if-env-changed=CC_x86_64_apple_darwin CC_x86_64_apple_darwin = None cargo:rerun-if-env-changed=TARGET_CC TARGET_CC = None cargo:rerun-if-env-changed=CC CC = None RUSTC_LINKER = None cargo:rerun-if-env-changed=CROSS_COMPILE CROSS_COMPILE = None cargo:rerun-if-env-changed=CFLAGS_x86_64-apple-darwin CFLAGS_x86_64-apple-darwin = None cargo:rerun-if-env-changed=CFLAGS_x86_64_apple_darwin CFLAGS_x86_64_apple_darwin = Some("-stdlib=libc++") cargo:rerun-if-env-changed=CRATE_CC_NO_DEFAULTS CRATE_CC_NO_DEFAULTS = None DEBUG = Some("false") CARGO_CFG_TARGET_FEATURE = Some("fxsr,sse,sse2,sse3,ssse3") --- stderr running "cc" "-Os" "-ffunction-sections" "-fdata-sections" "-fPIC" "-m64" "-arch" "x86_64" "-stdlib=libc++" "-I" "include" "-pedantic" "-pedantic-errors" "-Wall" "-Wextra" "-Wcast-align" "-Wcast-qual" "-Wconversion" "-Wenum-compare" "-Wfloat-equal" "-Wformat=2" "-Winline" "-Winvalid-pch" "-Wmissing-field-initializers" "-Wmissing-include-dirs" "-Wredundant-decls" "-Wshadow" "-Wsign-compare" "-Wsign-conversion" "-Wundef" "-Wuninitialized" "-Wwrite-strings" "-fno-strict-aliasing" "-fvisibility=hidden" "-fstack-protector" "-gfull" "-DNDEBUG" "-c" "-o/cross/project/target/x86_64-apple-darwin/release/build/ring-dc3763bb75c01cb2/out/aesni-x86_64-macosx.o" "/cargo/registry/src/github.com-1ecc6299db9ec823/ring-0.16.20/pregenerated/aesni-x86_64-macosx.S" cc: error: x86_64: No such file or directory cc: error: unrecognized debug output level 'full' cc: error: unrecognized command line option '-arch' cc: error: unrecognized command line option '-stdlib=libc++' thread 'main' panicked at 'execution failed', /cargo/registry/src/github.com-1ecc6299db9ec823/ring-0.16.20/build.rs:656:9 note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace thread 'main' panicked at 'called `Result::unwrap()` on an `Err` value: "non-success exit status"', xtask/src/main.rs:60:19 note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace ```

After adding some debug statements and comparing it to the logs when building locally using cross, I found that when using CROSS_REMOTE=1, the 4 environment variables defined in the entrypoint darwin-entry.sh were missing. In my case, those were:

I did not dig too much into it, but I assume it's because the entrypoint is ignored when using CROSS_REMOTE=1. As a workaround, I created a derived image where I've set the variables directly in the Dockerfile with ENV statements: this fixed the issue.

A solution to avoid this issue would be to avoid putting critical configuration value in the entrypoints. Another solution would be for CROSS_REMOTE to use the entrypoint.

demurgos commented 1 year ago

I looked into writing a fix for this issue. My workaround hardcoded the values, but the proper fix would be to set the ENV fields with the values from the script. The problem is that both the variable names and values are computed at build time. It seems that a proper fix would depend on first having support for computed env vars in docker:

Another solution would be to go through the entrypoint, even with CROSS_REMOTE=1.