From c62f12b54acd0f2ca7d392efbf873873e2ee7d22 Mon Sep 17 00:00:00 2001 From: Young-Flash Date: Sat, 12 Oct 2024 16:27:55 +0800 Subject: [PATCH] internal: use cc -O2 for native --release --- crates/moon/src/cli.rs | 30 +++- crates/moon/src/cli/build.rs | 4 +- crates/moon/src/cli/bundle.rs | 2 +- crates/moon/src/cli/check.rs | 4 +- crates/moon/src/cli/generate_test_driver.rs | 4 +- crates/moon/src/cli/run.rs | 3 +- crates/moon/src/cli/test.rs | 4 +- crates/moon/tests/test_cases/mod.rs | 167 ++++++++++++++++++++ 8 files changed, 205 insertions(+), 13 deletions(-) diff --git a/crates/moon/src/cli.rs b/crates/moon/src/cli.rs index d47c8e91..dd26eaa6 100644 --- a/crates/moon/src/cli.rs +++ b/crates/moon/src/cli.rs @@ -64,7 +64,7 @@ use moonutil::{ cli::UniversalFlags, common::{ read_module_desc_file_in_dir, BuildPackageFlags, LinkCoreFlags, MooncOpt, OutputFormat, - SurfaceTarget, TargetBackend, MOONBITLANG_CORE, MOON_MOD_JSON, + RunMode, SurfaceTarget, TargetBackend, MOONBITLANG_CORE, MOON_MOD_JSON, }, mooncakes::{LoginSubcommand, PackageSubcommand, PublishSubcommand, RegisterSubcommand}, }; @@ -188,14 +188,38 @@ impl BuildFlags { } } -pub fn get_compiler_flags(src_dir: &Path, build_flags: &BuildFlags) -> anyhow::Result { +pub fn get_compiler_flags( + src_dir: &Path, + build_flags: &BuildFlags, + run_mode: RunMode, +) -> anyhow::Result { // read moon.mod.json if !moonutil::common::check_moon_mod_exists(src_dir) { bail!("could not find `{}`", MOON_MOD_JSON); } let moon_mod = read_module_desc_file_in_dir(src_dir)?; let extra_build_opt = moon_mod.compile_flags.unwrap_or_default(); - let extra_link_opt = moon_mod.link_flags.unwrap_or_default(); + let mut extra_link_opt = moon_mod.link_flags.unwrap_or_default(); + + #[cfg(unix)] + match run_mode { + // need link-core for build, test and run + RunMode::Build | RunMode::Test | RunMode::Run => { + if build_flags.release && build_flags.target_backend == Some(TargetBackend::Native) { + // check if cc exists in PATH + if let Err(e) = which::which("cc") { + eprintln!( + "error: 'cc' not found in PATH, which is used for native backend release compilation: {}", + e + ); + std::process::exit(1); + } + // use "cc -O2" to compile + extra_link_opt.extend_from_slice(&["-cc".to_string(), "cc -O2".to_string()]); + } + } + _ => {} + } let output_format = if build_flags.output_wat { OutputFormat::Wat diff --git a/crates/moon/src/cli/build.rs b/crates/moon/src/cli/build.rs index 2fd4bd5d..55065850 100644 --- a/crates/moon/src/cli/build.rs +++ b/crates/moon/src/cli/build.rs @@ -117,9 +117,9 @@ fn run_build_internal( )?; let raw_target_dir = target_dir; - let mut moonc_opt = super::get_compiler_flags(source_dir, &cmd.build_flags)?; - moonc_opt.build_opt.deny_warn = cmd.build_flags.deny_warn; let run_mode = RunMode::Build; + let mut moonc_opt = super::get_compiler_flags(source_dir, &cmd.build_flags, run_mode)?; + moonc_opt.build_opt.deny_warn = cmd.build_flags.deny_warn; let target_dir = mk_arch_mode_dir(source_dir, target_dir, &moonc_opt, run_mode)?; let _lock = FileLock::lock(&target_dir)?; let sort_input = cmd.build_flags.sort_input; diff --git a/crates/moon/src/cli/bundle.rs b/crates/moon/src/cli/bundle.rs index 8f5057be..187cbc06 100644 --- a/crates/moon/src/cli/bundle.rs +++ b/crates/moon/src/cli/bundle.rs @@ -126,8 +126,8 @@ fn run_bundle_internal( cli.quiet, )?; - let mut moonc_opt = super::get_compiler_flags(source_dir, &cmd.build_flags)?; let run_mode = RunMode::Bundle; + let mut moonc_opt = super::get_compiler_flags(source_dir, &cmd.build_flags, run_mode)?; let sort_input = cmd.build_flags.sort_input; let raw_target_dir = target_dir.to_path_buf(); diff --git a/crates/moon/src/cli/check.rs b/crates/moon/src/cli/check.rs index a1988959..abe71783 100644 --- a/crates/moon/src/cli/check.rs +++ b/crates/moon/src/cli/check.rs @@ -134,9 +134,9 @@ fn run_check_internal( )?; let raw_target_dir = target_dir; - let mut moonc_opt = get_compiler_flags(source_dir, &cmd.build_flags)?; - moonc_opt.build_opt.deny_warn = cmd.build_flags.deny_warn; let run_mode = RunMode::Check; + let mut moonc_opt = get_compiler_flags(source_dir, &cmd.build_flags, run_mode)?; + moonc_opt.build_opt.deny_warn = cmd.build_flags.deny_warn; let target_dir = mk_arch_mode_dir(source_dir, target_dir, &moonc_opt, run_mode)?; let _lock = FileLock::lock(&target_dir)?; diff --git a/crates/moon/src/cli/generate_test_driver.rs b/crates/moon/src/cli/generate_test_driver.rs index 5f226225..7e8bf532 100644 --- a/crates/moon/src/cli/generate_test_driver.rs +++ b/crates/moon/src/cli/generate_test_driver.rs @@ -124,9 +124,9 @@ pub fn generate_test_driver( }); cmd.build_flags.target_backend = target_backend; - let moonc_opt = super::get_compiler_flags(&source_dir, &cmd.build_flags)?; - let run_mode = RunMode::Test; + let moonc_opt = super::get_compiler_flags(&source_dir, &cmd.build_flags, run_mode)?; + let sort_input = cmd.build_flags.sort_input; let filter_package = cmd.package.map(|it| it.into_iter().collect()); diff --git a/crates/moon/src/cli/run.rs b/crates/moon/src/cli/run.rs index 30c6d58c..4824c34e 100644 --- a/crates/moon/src/cli/run.rs +++ b/crates/moon/src/cli/run.rs @@ -227,8 +227,9 @@ pub fn run_run_internal(cli: &UniversalFlags, cmd: RunSubcommand) -> anyhow::Res cli.quiet, )?; - let mut moonc_opt = super::get_compiler_flags(&source_dir, &cmd.build_flags)?; let run_mode = RunMode::Run; + let mut moonc_opt = super::get_compiler_flags(&source_dir, &cmd.build_flags, run_mode)?; + let raw_target_dir = target_dir.to_path_buf(); let target_dir = mk_arch_mode_dir(&source_dir, &target_dir, &moonc_opt, run_mode)?; let _lock = FileLock::lock(&target_dir)?; diff --git a/crates/moon/src/cli/test.rs b/crates/moon/src/cli/test.rs index 964b8e6c..f831a558 100644 --- a/crates/moon/src/cli/test.rs +++ b/crates/moon/src/cli/test.rs @@ -151,13 +151,13 @@ fn run_test_internal( cli.quiet, )?; - let mut moonc_opt = super::get_compiler_flags(source_dir, &cmd.build_flags)?; + let run_mode = RunMode::Test; + let mut moonc_opt = super::get_compiler_flags(source_dir, &cmd.build_flags, run_mode)?; // release is 'false' by default, so we will run test at debug mode(to gain more detailed stack trace info), unless `--release` is specified // however, other command like build, check, run, etc, will run at release mode by default moonc_opt.build_opt.debug_flag = !cmd.build_flags.release; moonc_opt.link_opt.debug_flag = !cmd.build_flags.release; - let run_mode = RunMode::Test; let raw_target_dir = target_dir.to_path_buf(); let target_dir = mk_arch_mode_dir(source_dir, target_dir, &moonc_opt, run_mode)?; let _lock = FileLock::lock(&target_dir)?; diff --git a/crates/moon/tests/test_cases/mod.rs b/crates/moon/tests/test_cases/mod.rs index 6e014805..92500f10 100644 --- a/crates/moon/tests/test_cases/mod.rs +++ b/crates/moon/tests/test_cases/mod.rs @@ -6994,3 +6994,170 @@ fn test_moonfmt() { "#]], ); } + +#[cfg(unix)] +#[test] +fn test_use_cc_for_native_release() { + let dir = TestDir::new("moon_test_hello_exec_fntest.in"); + // build + { + check( + get_stdout( + &dir, + [ + "build", + "--target", + "native", + "--release", + "--sort-input", + "--dry-run", + ], + ), + expect![[r#" + moonc build-package ./lib/hello.mbt -o ./target/native/release/build/lib/lib.core -pkg moonbitlang/hello/lib -std-path $MOON_HOME/lib/core/target/native/release/bundle -pkg-sources moonbitlang/hello/lib:./lib -target native + moonc build-package ./main/main.mbt -o ./target/native/release/build/main/main.core -pkg moonbitlang/hello/main -is-main -std-path $MOON_HOME/lib/core/target/native/release/bundle -i ./target/native/release/build/lib/lib.mi:lib -pkg-sources moonbitlang/hello/main:./main -target native + moonc link-core $MOON_HOME/lib/core/target/native/release/bundle/core.core ./target/native/release/build/lib/lib.core ./target/native/release/build/main/main.core -main moonbitlang/hello/main -o ./target/native/release/build/main/main.exe -pkg-sources moonbitlang/hello/lib:./lib -pkg-sources moonbitlang/hello/main:./main -pkg-sources moonbitlang/core:$MOON_HOME/lib/core -target native -cc "cc -O2" + "#]], + ); + // if --release is not specified, it should not use cc + check( + get_stdout( + &dir, + ["build", "--target", "native", "--sort-input", "--dry-run"], + ), + expect![[r#" + moonc build-package ./lib/hello.mbt -o ./target/native/release/build/lib/lib.core -pkg moonbitlang/hello/lib -std-path $MOON_HOME/lib/core/target/native/release/bundle -pkg-sources moonbitlang/hello/lib:./lib -target native + moonc build-package ./main/main.mbt -o ./target/native/release/build/main/main.core -pkg moonbitlang/hello/main -is-main -std-path $MOON_HOME/lib/core/target/native/release/bundle -i ./target/native/release/build/lib/lib.mi:lib -pkg-sources moonbitlang/hello/main:./main -target native + moonc link-core $MOON_HOME/lib/core/target/native/release/bundle/core.core ./target/native/release/build/lib/lib.core ./target/native/release/build/main/main.core -main moonbitlang/hello/main -o ./target/native/release/build/main/main.exe -pkg-sources moonbitlang/hello/lib:./lib -pkg-sources moonbitlang/hello/main:./main -pkg-sources moonbitlang/core:$MOON_HOME/lib/core -target native + "#]], + ); + check( + get_stdout( + &dir, + [ + "build", + "--target", + "native", + "--debug", + "--sort-input", + "--dry-run", + ], + ), + expect![[r#" + moonc build-package ./lib/hello.mbt -o ./target/native/debug/build/lib/lib.core -pkg moonbitlang/hello/lib -std-path $MOON_HOME/lib/core/target/native/release/bundle -pkg-sources moonbitlang/hello/lib:./lib -target native -g + moonc build-package ./main/main.mbt -o ./target/native/debug/build/main/main.core -pkg moonbitlang/hello/main -is-main -std-path $MOON_HOME/lib/core/target/native/release/bundle -i ./target/native/debug/build/lib/lib.mi:lib -pkg-sources moonbitlang/hello/main:./main -target native -g + moonc link-core $MOON_HOME/lib/core/target/native/release/bundle/core.core ./target/native/debug/build/lib/lib.core ./target/native/debug/build/main/main.core -main moonbitlang/hello/main -o ./target/native/debug/build/main/main.exe -pkg-sources moonbitlang/hello/lib:./lib -pkg-sources moonbitlang/hello/main:./main -pkg-sources moonbitlang/core:$MOON_HOME/lib/core -target native -g + "#]], + ); + } + + // run + { + check( + get_stdout( + &dir, + [ + "run", + "main", + "--target", + "native", + "--release", + "--sort-input", + "--dry-run", + ], + ), + expect![[r#" + moonc build-package ./lib/hello.mbt -o ./target/native/release/build/lib/lib.core -pkg moonbitlang/hello/lib -std-path $MOON_HOME/lib/core/target/native/release/bundle -pkg-sources moonbitlang/hello/lib:./lib -target native + moonc build-package ./main/main.mbt -o ./target/native/release/build/main/main.core -pkg moonbitlang/hello/main -is-main -std-path $MOON_HOME/lib/core/target/native/release/bundle -i ./target/native/release/build/lib/lib.mi:lib -pkg-sources moonbitlang/hello/main:./main -target native + moonc link-core $MOON_HOME/lib/core/target/native/release/bundle/core.core ./target/native/release/build/lib/lib.core ./target/native/release/build/main/main.core -main moonbitlang/hello/main -o ./target/native/release/build/main/main.exe -pkg-sources moonbitlang/hello/lib:./lib -pkg-sources moonbitlang/hello/main:./main -pkg-sources moonbitlang/core:$MOON_HOME/lib/core -target native -cc "cc -O2" + ./target/native/release/build/main/main.exe + "#]], + ); + // if --release is not specified, it should not use cc + check( + get_stdout( + &dir, + [ + "run", + "main", + "--target", + "native", + "--sort-input", + "--dry-run", + ], + ), + expect![[r#" + moonc build-package ./lib/hello.mbt -o ./target/native/release/build/lib/lib.core -pkg moonbitlang/hello/lib -std-path $MOON_HOME/lib/core/target/native/release/bundle -pkg-sources moonbitlang/hello/lib:./lib -target native + moonc build-package ./main/main.mbt -o ./target/native/release/build/main/main.core -pkg moonbitlang/hello/main -is-main -std-path $MOON_HOME/lib/core/target/native/release/bundle -i ./target/native/release/build/lib/lib.mi:lib -pkg-sources moonbitlang/hello/main:./main -target native + moonc link-core $MOON_HOME/lib/core/target/native/release/bundle/core.core ./target/native/release/build/lib/lib.core ./target/native/release/build/main/main.core -main moonbitlang/hello/main -o ./target/native/release/build/main/main.exe -pkg-sources moonbitlang/hello/lib:./lib -pkg-sources moonbitlang/hello/main:./main -pkg-sources moonbitlang/core:$MOON_HOME/lib/core -target native + ./target/native/release/build/main/main.exe + "#]], + ); + check( + get_stdout( + &dir, + [ + "run", + "main", + "--target", + "native", + "--debug", + "--sort-input", + "--dry-run", + ], + ), + expect![[r#" + moonc build-package ./lib/hello.mbt -o ./target/native/debug/build/lib/lib.core -pkg moonbitlang/hello/lib -std-path $MOON_HOME/lib/core/target/native/release/bundle -pkg-sources moonbitlang/hello/lib:./lib -target native -g + moonc build-package ./main/main.mbt -o ./target/native/debug/build/main/main.core -pkg moonbitlang/hello/main -is-main -std-path $MOON_HOME/lib/core/target/native/release/bundle -i ./target/native/debug/build/lib/lib.mi:lib -pkg-sources moonbitlang/hello/main:./main -target native -g + moonc link-core $MOON_HOME/lib/core/target/native/release/bundle/core.core ./target/native/debug/build/lib/lib.core ./target/native/debug/build/main/main.core -main moonbitlang/hello/main -o ./target/native/debug/build/main/main.exe -pkg-sources moonbitlang/hello/lib:./lib -pkg-sources moonbitlang/hello/main:./main -pkg-sources moonbitlang/core:$MOON_HOME/lib/core -target native -g + ./target/native/debug/build/main/main.exe + "#]], + ); + } + + // test + { + check( + get_stdout( + &dir, + [ + "test", + "--target", + "native", + "--release", + "--sort-input", + "--dry-run", + ], + ), + expect![[r#" + moon generate-test-driver --source-dir . --target-dir ./target/native/release/test --package moonbitlang/hello/lib --sort-input --target native --driver-kind whitebox + moonc build-package ./lib/hello.mbt ./lib/hello_wbtest.mbt ./target/native/release/test/lib/__generated_driver_for_whitebox_test.mbt -o ./target/native/release/test/lib/lib.whitebox_test.core -pkg moonbitlang/hello/lib -is-main -std-path $MOON_HOME/lib/core/target/native/release/bundle -pkg-sources moonbitlang/hello/lib:./lib -target native + moonc link-core $MOON_HOME/lib/core/target/native/release/bundle/core.core ./target/native/release/test/lib/lib.whitebox_test.core -main moonbitlang/hello/lib -o ./target/native/release/test/lib/lib.whitebox_test.exe -test-mode -pkg-sources moonbitlang/hello/lib:./lib -pkg-sources moonbitlang/core:$MOON_HOME/lib/core -exported_functions moonbit_test_driver_internal_execute -target native -cc "cc -O2" + moon generate-test-driver --source-dir . --target-dir ./target/native/release/test --package moonbitlang/hello/lib --sort-input --target native --driver-kind internal + moonc build-package ./lib/hello.mbt ./target/native/release/test/lib/__generated_driver_for_internal_test.mbt -o ./target/native/release/test/lib/lib.internal_test.core -pkg moonbitlang/hello/lib -is-main -std-path $MOON_HOME/lib/core/target/native/release/bundle -pkg-sources moonbitlang/hello/lib:./lib -target native + moonc link-core $MOON_HOME/lib/core/target/native/release/bundle/core.core ./target/native/release/test/lib/lib.internal_test.core -main moonbitlang/hello/lib -o ./target/native/release/test/lib/lib.internal_test.exe -test-mode -pkg-sources moonbitlang/hello/lib:./lib -pkg-sources moonbitlang/core:$MOON_HOME/lib/core -exported_functions moonbit_test_driver_internal_execute -target native -cc "cc -O2" + "#]], + ); + check( + get_stdout( + &dir, + [ + "test", + "--target", + "native", + "--debug", + "--sort-input", + "--dry-run", + ], + ), + expect![[r#" + moon generate-test-driver --source-dir . --target-dir ./target/native/debug/test --package moonbitlang/hello/lib --sort-input --target native --driver-kind whitebox + moonc build-package ./lib/hello.mbt ./lib/hello_wbtest.mbt ./target/native/debug/test/lib/__generated_driver_for_whitebox_test.mbt -o ./target/native/debug/test/lib/lib.whitebox_test.core -pkg moonbitlang/hello/lib -is-main -std-path $MOON_HOME/lib/core/target/native/release/bundle -pkg-sources moonbitlang/hello/lib:./lib -target native -g + moonc link-core $MOON_HOME/lib/core/target/native/release/bundle/core.core ./target/native/debug/test/lib/lib.whitebox_test.core -main moonbitlang/hello/lib -o ./target/native/debug/test/lib/lib.whitebox_test.exe -test-mode -pkg-sources moonbitlang/hello/lib:./lib -pkg-sources moonbitlang/core:$MOON_HOME/lib/core -exported_functions moonbit_test_driver_internal_execute -target native -g + moon generate-test-driver --source-dir . --target-dir ./target/native/debug/test --package moonbitlang/hello/lib --sort-input --target native --driver-kind internal + moonc build-package ./lib/hello.mbt ./target/native/debug/test/lib/__generated_driver_for_internal_test.mbt -o ./target/native/debug/test/lib/lib.internal_test.core -pkg moonbitlang/hello/lib -is-main -std-path $MOON_HOME/lib/core/target/native/release/bundle -pkg-sources moonbitlang/hello/lib:./lib -target native -g + moonc link-core $MOON_HOME/lib/core/target/native/release/bundle/core.core ./target/native/debug/test/lib/lib.internal_test.core -main moonbitlang/hello/lib -o ./target/native/debug/test/lib/lib.internal_test.exe -test-mode -pkg-sources moonbitlang/hello/lib:./lib -pkg-sources moonbitlang/core:$MOON_HOME/lib/core -exported_functions moonbit_test_driver_internal_execute -target native -g + "#]], + ); + } +}