From 0522da7b25b26b88c7d0cd30b67ddefd8afad037 Mon Sep 17 00:00:00 2001 From: Andrew Pennebaker Date: Fri, 31 Mar 2023 20:02:53 -0500 Subject: [PATCH] close #34 --- DEVELOPMENT.md | 6 ++++-- README.md | 17 +++++++++++++++-- src/crit.rs | 19 ++++++++++++++----- 3 files changed, 33 insertions(+), 9 deletions(-) diff --git a/DEVELOPMENT.md b/DEVELOPMENT.md index 1a1d808..ff237f7 100644 --- a/DEVELOPMENT.md +++ b/DEVELOPMENT.md @@ -3,6 +3,7 @@ * [rustup](https://rustup.rs/) 1.25.2+ * [Rust](https://www.rust-lang.org/en-US/) 1.68.2+ with `rustup component add clippy` and `cargo install cargo-audit@0.17.5 tinyrick@0.0.9` * [Docker](https://www.docker.com/) 20.10.12+ +* a POSIX compliant [sh](https://pubs.opengroup.org/onlinepubs/9699919799/utilities/sh.html) implementation ## Recommended @@ -11,6 +12,7 @@ * [cargo-cache](https://crates.io/crates/cargo-cache) * [tree](https://en.wikipedia.org/wiki/Tree_(command)) * GNU compatible [time](https://www.gnu.org/software/time/) +* [zip](https://en.wikipedia.org/wiki/ZIP_(file_format)) # INSTALL BINARIES FROM SOURCE @@ -33,6 +35,6 @@ $ cargo audit # PORT ```console -$ crit -... +$ crit -b crit-0.0.4 +$ sh -c "cd .crit/bin && zip -r crit-0.0.4.zip crit-0.0.4" ``` diff --git a/README.md b/README.md index e63e616..b67db6d 100644 --- a/README.md +++ b/README.md @@ -63,6 +63,7 @@ FreeBSD * [ASDF](https://asdf-vm.com/) 0.10 (run `asdf reshim` after each Rust application binary installation) * [direnv](https://direnv.net/) 2 * [cargo-cache](https://crates.io/crates/cargo-cache) +* [tar](https://en.wikipedia.org/wiki/Tar_(computing)) / [zip](https://en.wikipedia.org/wiki/ZIP_(file_format)) * [tree](https://en.wikipedia.org/wiki/Tree_(command)) * GNU compatible [time](https://www.gnu.org/software/time/) * [Amphetamine](https://apps.apple.com/us/app/amphetamine/id937984704?mt=12) (macOS), [The Caffeine](https://www.microsoft.com/store/productId/9PJBW5SCH9LC) (Windows), [Caffeine](https://launchpad.net/caffeine) (Linux) can prevent hibernation during any long builds @@ -75,7 +76,7 @@ For more details on developing crit itself, see [DEVELOPMENT.md](DEVELOPMENT.md) ## Help, some targets are broken? -First, check that your project is able to build with conventional `cross` or `cargo` commands. A project which does not compile, will naturally have difficulty cross-compiling. +Check that your project is able to build with conventional `cross` or `cargo` commands against a single target. A project that does not compile against a single target, will naturally have difficulty when attempting to cross-compile for multiple targets. Note that Rust introduces new, under-supported targets all the time. We try to keep up, but sometimes we miss a few of these. Regardless, you can declare which targets are disabled, by writing a custom pattern for the `-e` / `--exclude-targets` flag. @@ -85,9 +86,20 @@ Some targets may lack stock support for the Rust `std` library. This is common f * Avoid using the `std` library, in both your code, as well as the dependency tree. This is actually common practice for many Rust projects, as an proactive stance on embedded development support. * Disable undesired targets. +## Help, cross-compilation appears frozen? + +crit hides a lot of compiler noise. While a target is building, you can use common Docker commands to inspect the compilation process: + +* `docker ps -a` +* `docker logs [--follow] ` + ## Help, cross-compilation is slow? -Yes, it is. The Rust compiler is notoriously analytical, often taking a long time to compile a single target. When cross-compiling multiple targets, that time multiplies by the number of targets. +Yes, it sure is! Almost as slow as using Virtual Machines for cross-compilation. + +Rustaceans come to expect that the Rust compiler is analytical, spending more time optimizing programs, so that the final binaries will run safer and faster. The Rust compiler often taking a long time to compile each individual target. + +Naturally, when cross-compiling multiple targets, that time multiplies by the number of targets. Some cross-compilation performance tips: @@ -95,6 +107,7 @@ Some cross-compilation performance tips: * Temporarily disable common Cargo build profile options (`codegen-units`, `lto`, `strip`, etc.) * Use debug mode (e.g., `--`) * Use fewer dependencies +* Design with the [UNIX Philosophy](https://en.wikipedia.org/wiki/Unix_philosophy), namely *Make each program do one thing well.* Not a hundred features poorly. * Keep the host awake (see Amphetamine / The Caffeine / Caffeine above) * Reserve cross-compilation as a release-time step, distinct from more rapid development tasks * Perform cross-compilation in a CI/CD pipeline with more CPU, disk, and RAM resources diff --git a/src/crit.rs b/src/crit.rs index ba9ff28..7a3d67f 100644 --- a/src/crit.rs +++ b/src/crit.rs @@ -66,7 +66,7 @@ fn usage(brief : &str, opts : &getopts::Options) { } /// Show version information -pub fn banner() { +pub fn version() { println!("{} {}", env!("CARGO_PKG_NAME"), env!("CARGO_PKG_VERSION")); } @@ -74,6 +74,7 @@ pub fn banner() { fn main() { let brief = format!("Usage: {} [OPTIONS] [-- ]", env!("CARGO_PKG_NAME")); let artifact_root : &path::Path = path::Path::new(CRIT_ARTIFACT_ROOT); + let mut banner : String = "".to_string(); let mut target_exclusion_pattern : regex::Regex = DEFAULT_TARGET_EXCLUSION_PATTERNS.clone(); let list_targets : bool; @@ -84,6 +85,7 @@ fn main() { let mut opts : getopts::Options = getopts::Options::new(); opts.optflag("c", "clean", "delete crit artifacts directory tree"); + opts.optopt("b", "banner", "nest artifacts with a further subdirectory label", ""); opts.optopt("e", "exclude-targets", "exclude targets", ""); opts.optflag("l", "list-targets", "list enabled targets"); opts.optflag("h", "help", "print usage info"); @@ -103,7 +105,7 @@ fn main() { usage(&brief, &opts); process::exit(0); } else if optmatches.opt_present("v") { - banner(); + version(); process::exit(0); } else if optmatches.opt_present("c") { if artifact_root.exists() { @@ -112,9 +114,12 @@ fn main() { } process::exit(0); + } else if optmatches.opt_present("b") { + banner = optmatches.opt_str("b") + .expect("error: missing value for banner flag"); } else if optmatches.opt_present("e") { let ep = optmatches.opt_str("e") - .expect("error: missing exclusion pattern flag value"); + .expect("error: missing value for exclusion flag"); target_exclusion_pattern = regex::Regex::new(&ep) .expect("error: unable to compile Rust regular expression"); @@ -210,10 +215,14 @@ fn main() { process::exit(1); } - let bin_dir : &path::PathBuf = &artifact_root.join("bin"); + let mut bin_dir : path::PathBuf = artifact_root.join("bin"); + + if banner != "" { + bin_dir = bin_dir.join(banner); + } // cross automatically creates its --target-dir paths - let cross_dir : &path::PathBuf = &artifact_root.join("cross"); + let cross_dir : path::PathBuf = artifact_root.join("cross"); for target in targets.keys() { println!("building {}...", target);