look at this shit. they're patching up musl https://github.com/rust-lang/compiler-builtins/blob/master/crates/musl-math-sys/build.rs and doing it in a way that remains entirely hidden to the entire rest of the build graph, because cargo has no concept of patching, or resources, or anything linked across the dependency graph. so even the fucking bootstrap strip just refers to a global directory path
#[allow(dead_code)]
#[derive(Debug)]
struct Config {
manifest_dir: PathBuf,
out_dir: PathBuf,
musl_dir: PathBuf,
musl_arch: String,
target_arch: String,
target_env: String,
target_family: String,
target_os: String,
target_string: String,
target_vendor: String,
target_features: Vec<String>,
}
no shared abstraction for this kind of config. there's a completely separate target concept made up for the llvm build in another crate https://github.com/rust-lang/compiler-builtins/blob/82a32c6bd1b82b55de5aea0cddb707732b54855f/compiler-builtins/configure.rs#L7-L21
pub struct Target {
pub triple: String,
pub triple_split: Vec<String>,
pub opt_level: String,
pub cargo_features: Vec<String>,
pub os: String,
pub arch: String,
pub vendor: String,
pub env: String,
pub pointer_width: u8,
pub little_endian: bool,
pub features: Vec<String>,
pub reliable_f128: bool,
pub reliable_f16: bool,
}
little_endian as a fucking bool, which of course means you have to fuck around like this
let little_endian = match env::var("CARGO_CFG_TARGET_ENDIAN").unwrap().as_str() {
"little" => true,
"big" => false,
x => panic!("unknown endian {x}"),
};
what is the point of creating an entirely separate build system in rust if you're not going to share type definitions and not even using enums
but the real problem is in the output (https://github.com/rust-lang/compiler-builtins/blob/82a32c6bd1b82b55de5aea0cddb707732b54855f/compiler-builtins/configure.rs#L91-L109):
/* Not all backends support `f16` and `f128` to the same level on all architectures, so we
* need to disable things if the compiler may crash. See configuration at:
* * https://github.com/rust-lang/rust/blob/c65dccabacdfd6c8a7f7439eba13422fdd89b91e/compiler/rustc_codegen_llvm/src/llvm_util.rs#L367-L432
* * https://github.com/rust-lang/rustc_codegen_gcc/blob/4b5c44b14166083eef8d71f15f5ea1f53fc976a0/src/lib.rs#L496-L507
* * https://github.com/rust-lang/rustc_codegen_cranelift/blob/c713ffab3c6e28ab4b4dd4e392330f786ea657ad/src/lib.rs#L196-L226
*/
// If the feature is set, disable both of these types.
let no_f16_f128 = target.cargo_features.iter().any(|s| s == "no-f16-f128");
println!("cargo::rustc-check-cfg=cfg(f16_enabled)");
if target.reliable_f16 && !no_f16_f128 {
println!("cargo::rustc-cfg=f16_enabled");
}
println!("cargo::rustc-check-cfg=cfg(f128_enabled)");
if target.reliable_f128 && !no_f16_f128 {
println!("cargo::rustc-cfg=f128_enabled");
}
how do we fix an ICE? easy, we print a line to stdout that sets global state within a subcrate that we need to remember to call in a build script. that's three separate backends depending upon the global state written by this method, which isn't even the top-level build script