Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
69 changes: 60 additions & 9 deletions crates/moon/src/cli.rs
Original file line number Diff line number Diff line change
Expand Up @@ -152,19 +152,22 @@ pub struct BuildFlags {
#[clap(long, long = "nostd")]
no_std: bool,

/// Emit debug information
/// Compile in debug mode
#[clap(long, short = 'g')]
pub debug: bool,

/// Compile in release mode
#[clap(long, conflicts_with = "debug")]
pub release: bool,

/// Enable stripping debug information
/// Do not emit debug information
#[clap(long, conflicts_with = "no_strip")]
pub strip: bool,

/// Disable stripping debug information
/// Emit debug information (no effect)
///
/// This flag currently has no effect, as debug information is emitted by
/// default unless `--strip` is specified.
#[clap(long, conflicts_with = "strip")]
pub no_strip: bool,

Expand Down Expand Up @@ -265,12 +268,50 @@ impl BuildFlags {
pub fn strip(&self) -> bool {
if self.strip {
true
} else if self.no_strip {
false
} else {
!self.debug
// `--no-strip` has no effect now
false
}
}

pub fn keep_debug_info(&self) -> bool {
!self.strip()
}

/// Legacy defaulting rule for compilation mode.
///
/// - When `default_release` is false (most commands: build/test/check/info), we default to
/// debug mode if the user did not specify `--debug` or `--release`. In the legacy pipeline
/// this maps to "no optimization" (-O0) and keeps debug symbols ON unless `--strip` is set.
/// - When `default_release` is true (bundle/bench), we default to release if neither flag
/// was specified. In release mode, optimization is enabled; debug symbols remain ON unless
/// `--strip` is set.
///
/// Notes (legacy path):
/// - Debug/Release selection here only determines the high-level mode. The actual C/C++ flags
/// (-O0/-Og/-O2 etc.) are derived downstream in the build generator. Debug mode results in
/// no optimization in legacy, while release selects optimized builds.
pub fn default_to_release(&mut self, default_release: bool) {
if !self.debug && !self.release {
if default_release {
self.release = true;
} else {
self.debug = true;
}
}
}

pub fn default_debug() -> Self {
let mut flags = Self::default();
flags.default_to_release(false);
flags
}

pub fn default_release() -> Self {
let mut flags = Self::default();
flags.default_to_release(true);
flags
}
}

pub fn get_compiler_flags(src_dir: &Path, build_flags: &BuildFlags) -> anyhow::Result<MooncOpt> {
Expand Down Expand Up @@ -304,13 +345,21 @@ pub fn get_compiler_flags(src_dir: &Path, build_flags: &BuildFlags) -> anyhow::R
_ => output_format,
};

// Legacy stripping & debug mapping:
// - `strip` disables emitting debug info and source maps; by default, we do NOT strip.
// - `keep_debug` mirrors the default behavior: debug symbols ON unless the user passed `--strip`.
// - `debug_flag` indicates high-level debug mode (selected by `default_to_release(false)` in most commands),
// which flows down to no optimization (-O0) in the legacy compiler command generation.
// - `source_map` only applies to backends that support it (Js/WasmGC) and is tied to `keep_debug`.
let strip_flag = build_flags.strip();
let keep_debug = build_flags.keep_debug_info();
let debug_flag = build_flags.debug;
let enable_coverage = build_flags.enable_coverage;
let source_map = debug_flag && target_backend.supports_source_map();
let source_map = keep_debug && target_backend.supports_source_map();

let build_opt = BuildPackageFlags {
debug_flag,
strip_flag: build_flags.strip(),
strip_flag,
source_map,
enable_coverage,
deny_warn: false,
Expand All @@ -320,13 +369,15 @@ pub fn get_compiler_flags(src_dir: &Path, build_flags: &BuildFlags) -> anyhow::R
enable_value_tracing: build_flags.enable_value_tracing,
};

// Link step mirrors debug info flags so symbol visibility is consistent across compile/link.
let link_opt = LinkCoreFlags {
debug_flag,
debug_flag: keep_debug,
source_map,
output_format,
target_backend,
};

// stdlib handling and rendering flags; unrelated to debug/strip logic.
let nostd = !build_flags.std() || moon_mod.name == MOONBITLANG_CORE;
let render =
!build_flags.no_render || std::env::var("MOON_NO_RENDER").unwrap_or_default() == "1";
Expand Down
4 changes: 4 additions & 0 deletions crates/moon/src/cli/bench.rs
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,10 @@ pub struct BenchSubcommand {

#[instrument(skip_all)]
pub fn run_bench(cli: UniversalFlags, cmd: BenchSubcommand) -> anyhow::Result<i32> {
let mut cmd = cmd;
// LEGACY default: bench uses release mode (optimized). Debug symbols remain ON unless `--strip`.
cmd.build_flags.default_to_release(true);

let PackageDirs {
source_dir,
target_dir,
Expand Down
19 changes: 16 additions & 3 deletions crates/moon/src/cli/build.rs
Original file line number Diff line number Diff line change
Expand Up @@ -108,11 +108,15 @@ fn run_build_internal(
source_dir: &Path,
target_dir: &Path,
) -> anyhow::Result<i32> {
let mut cmd = cmd.clone();
// LEGACY default: compile in debug mode (-O0). Debug symbols are enabled by default and only disabled via `--strip`.
cmd.build_flags.default_to_release(false);

let f = || {
if cli.unstable_feature.rupes_recta {
run_build_rr(cli, cmd, source_dir, target_dir)
run_build_rr(cli, &cmd, source_dir, target_dir)
} else {
run_build_legacy(cli, cmd, source_dir, target_dir)
run_build_legacy(cli, &cmd, source_dir, target_dir)
}
};

Expand All @@ -135,7 +139,7 @@ fn run_build_rr(
cli,
&cmd.build_flags,
target_dir,
OptLevel::Release,
OptLevel::Debug,
RunMode::Build,
);
let (_build_meta, build_graph) = rr_build::plan_build(
Expand Down Expand Up @@ -167,6 +171,12 @@ fn run_build_rr(
}
}

//// Legacy compilation mode & stripping (build):
//// - Mode selection: build defaults to debug via `BuildFlags::default_to_release(false)`.
//// In the legacy pipeline this maps to no optimization (-O0).
//// - Debug info: emitted by default; disabled only when `--strip` is set.
//// - Source maps: only emitted for backends that support them (Js/WasmGC) when not stripped.
//// - Link step mirrors debug info flags to keep symbol visibility consistent across compile/link.
#[instrument(skip_all)]
fn run_build_legacy(
cli: &UniversalFlags,
Expand All @@ -184,6 +194,9 @@ fn run_build_legacy(

let raw_target_dir = target_dir;
let run_mode = RunMode::Build;
// Legacy path: `get_compiler_flags` maps BuildFlags into MooncOpt.
// With `default_to_release(false)`, we default into debug mode which the legacy pipeline
// translates to no optimization (-O0). Debug symbols remain ON unless `--strip` is provided.
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 target_dir = mk_arch_mode_dir(source_dir, target_dir, &moonc_opt, run_mode)?;
Expand Down
11 changes: 11 additions & 0 deletions crates/moon/src/cli/bundle.rs
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,10 @@ pub struct BundleSubcommand {

#[instrument(skip_all)]
pub fn run_bundle(cli: UniversalFlags, cmd: BundleSubcommand) -> anyhow::Result<i32> {
let mut cmd = cmd;
// LEGACY default: bundle uses release mode (optimized). Debug symbols remain ON unless `--strip`.
cmd.build_flags.default_to_release(true);

let PackageDirs {
source_dir,
target_dir,
Expand Down Expand Up @@ -157,6 +161,11 @@ pub fn run_bundle_internal_rr(
}
}

//// Legacy compilation mode & stripping (bundle):
//// - Mode selection: bundle defaults to release via `BuildFlags::default_to_release(true)`,
//// selecting optimized builds in legacy.
//// - Debug info: ON by default even in release; disable only with `--strip`.
//// - Source maps: emitted for Js/WasmGC when not stripped.
#[instrument(level = Level::DEBUG, skip_all)]
fn run_bundle_internal_legacy(
cli: &UniversalFlags,
Expand All @@ -173,6 +182,8 @@ fn run_bundle_internal_legacy(
)?;

let run_mode = RunMode::Bundle;
// Legacy path: bundle defaults to release (optimized). Debug symbols remain ON unless `--strip`.
// Source maps apply to supported backends when not stripped.
let moonc_opt = super::get_compiler_flags(source_dir, &cmd.build_flags)?;
let sort_input = cmd.build_flags.sort_input;

Expand Down
34 changes: 24 additions & 10 deletions crates/moon/src/cli/check.rs
Original file line number Diff line number Diff line change
Expand Up @@ -116,10 +116,14 @@ fn run_check_internal(
source_dir: &Path,
target_dir: &Path,
) -> anyhow::Result<i32> {
let mut cmd = cmd.clone();
// LEGACY default: compile in debug mode (-O0). Debug symbols are enabled by default and only disabled via `--strip`.
cmd.build_flags.default_to_release(false);

if cmd.single_file.is_some() {
run_check_for_single_file(cli, cmd)
run_check_for_single_file(cli, &cmd)
} else {
run_check_normal_internal(cli, cmd, source_dir, target_dir)
run_check_normal_internal(cli, &cmd, source_dir, target_dir)
}
}

Expand All @@ -145,11 +149,13 @@ fn run_check_for_single_file(cli: &UniversalFlags, cmd: &CheckSubcommand) -> any
.unwrap_or(TargetBackend::WasmGC)
};

let release_flag = !cmd.build_flags.debug;
let release_build = cmd.build_flags.release;
let strip_flag = cmd.build_flags.strip();
let keep_debug = !strip_flag;

let target_dir = raw_target_dir
.join(target_backend.to_dir_name())
.join(if release_flag { "release" } else { "debug" })
.join(if release_build { "release" } else { "debug" })
.join(RunMode::Check.to_dir_name());

let moonbuild_opt = MoonbuildOpt {
Expand Down Expand Up @@ -180,9 +186,9 @@ fn run_check_for_single_file(cli: &UniversalFlags, cmd: &CheckSubcommand) -> any
};
let moonc_opt = MooncOpt {
build_opt: moonutil::common::BuildPackageFlags {
debug_flag: !release_flag,
strip_flag: false,
source_map: false,
debug_flag: !release_build,
strip_flag,
source_map: keep_debug,
enable_coverage: false,
deny_warn: false,
target_backend,
Expand All @@ -191,8 +197,8 @@ fn run_check_for_single_file(cli: &UniversalFlags, cmd: &CheckSubcommand) -> any
enable_value_tracing: cmd.build_flags.enable_value_tracing,
},
link_opt: moonutil::common::LinkCoreFlags {
debug_flag: !release_flag,
source_map: !release_flag,
debug_flag: keep_debug,
source_map: keep_debug,
output_format: match target_backend {
TargetBackend::Js => OutputFormat::Js,
TargetBackend::Native => OutputFormat::Native,
Expand Down Expand Up @@ -258,7 +264,7 @@ fn run_check_normal_internal_rr(
cli,
&cmd.build_flags,
target_dir,
moonutil::cond_expr::OptLevel::Release,
moonutil::cond_expr::OptLevel::Debug,
RunMode::Check,
);
preconfig.moonc_output_json |= cmd.output_json;
Expand Down Expand Up @@ -304,6 +310,12 @@ fn run_check_normal_internal_rr(
}
}

//// Legacy compilation mode & stripping (check):
//// - Mode selection: check defaults to debug via `BuildFlags::default_to_release(false)`,
//// mapping to no optimization (-O0) in legacy.
//// - Debug info: ON by default; turned OFF only with `--strip`.
//// - Source maps: only for Js/WasmGC when not stripped.
//// - Link flags mirror compile-time debug info to keep symbol visibility consistent.
#[instrument(skip_all)]
fn run_check_normal_internal_legacy(
cli: &UniversalFlags,
Expand All @@ -321,6 +333,8 @@ fn run_check_normal_internal_legacy(

let raw_target_dir = target_dir;
let run_mode = RunMode::Check;
// Legacy path: `get_compiler_flags` enforces default debug (-O0) unless the user specified release.
// Debug symbols remain ON unless `--strip`; source maps only for Js/WasmGC when not stripped.
let mut moonc_opt = get_compiler_flags(source_dir, &cmd.build_flags)?;
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)?;
Expand Down
7 changes: 4 additions & 3 deletions crates/moon/src/cli/doc.rs
Original file line number Diff line number Diff line change
Expand Up @@ -69,13 +69,14 @@ pub fn run_doc_rr(cli: UniversalFlags, cmd: DocSubcommand) -> anyhow::Result<i32
let source_dir = dir.source_dir;
let target_dir = dir.target_dir;

let flags = BuildFlags::default_debug();
// FIXME: This is copied from `moon check`'s code
let mut preconfig = preconfig_compile(
&cmd.auto_sync_flags,
&cli,
&BuildFlags::default(),
&flags,
&target_dir,
moonutil::cond_expr::OptLevel::Release,
moonutil::cond_expr::OptLevel::Debug,
RunMode::Check,
);
preconfig.docs_serve = cmd.serve;
Expand Down Expand Up @@ -105,7 +106,7 @@ pub fn run_doc_rr(cli: UniversalFlags, cmd: DocSubcommand) -> anyhow::Result<i32
rr_build::generate_metadata(&source_dir, &target_dir, &_build_meta)?;

// Execute the build
let cfg = BuildConfig::from_flags(&BuildFlags::default(), &cli.unstable_feature);
let cfg = BuildConfig::from_flags(&flags, &cli.unstable_feature);
let result = rr_build::execute_build(&cfg, build_graph, &target_dir)?;
result.print_info(cli.quiet, "checking")?;

Expand Down
17 changes: 12 additions & 5 deletions crates/moon/src/cli/info.rs
Original file line number Diff line number Diff line change
Expand Up @@ -93,12 +93,13 @@ pub fn run_info_rr(cli: UniversalFlags, cmd: InfoSubcommand) -> anyhow::Result<i
target_dir,
} = cli.source_tgt_dir.try_into_package_dirs()?;

let flags = BuildFlags::default_debug();
let mut preconfig = rr_build::preconfig_compile(
&cmd.auto_sync_flags,
&cli,
&BuildFlags::default(),
&flags,
&target_dir,
OptLevel::Release,
OptLevel::Debug,
RunMode::Build,
);
preconfig.info_no_alias = cmd.no_alias;
Expand Down Expand Up @@ -145,6 +146,10 @@ fn calc_user_intent(
Ok(res.into())
}

//// Legacy compilation mode & stripping (info):
//// - `moon info` wraps check semantics but historically bypassed `BuildFlags`.
//// It now uses `default_debug` + `get_compiler_flags`, so legacy behavior matches build/check/test:
//// debug mode by default (-O0), debug symbols ON unless `--strip`, source maps for Js/WasmGC.
pub fn run_info_legacy(cli: UniversalFlags, cmd: InfoSubcommand) -> anyhow::Result<i32> {
let PackageDirs {
source_dir,
Expand Down Expand Up @@ -259,9 +264,11 @@ pub fn run_info_internal(
)
})?;
let module_name = &mod_desc.name;
let mut moonc_opt = MooncOpt::default();
moonc_opt.link_opt.target_backend = cmd.target_backend.unwrap_or_default();
moonc_opt.build_opt.target_backend = cmd.target_backend.unwrap_or_default();
/// Legacy behavior: run `moon info` under debug mode (-O0) to match build/check/test defaults.
/// Debug symbols are enabled by default and only disabled via `--strip` (passed via BuildFlags).
let mut flags = crate::cli::BuildFlags::default_debug();
flags.target_backend = cmd.target_backend;
let mut moonc_opt = crate::cli::get_compiler_flags(source_dir, &flags)?;

let raw_target_dir = target_dir.to_path_buf();
let target_dir = mk_arch_mode_dir(source_dir, target_dir, &moonc_opt, RunMode::Check)?;
Expand Down
Loading