diff options
| author | Matthias Krüger <matthias.krueger@famsik.de> | 2023-04-25 21:06:34 +0200 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2023-04-25 21:06:34 +0200 |
| commit | f5a3039addd7dcdf6b79d47d8f308ad068cf3cb8 (patch) | |
| tree | 1b06b64ef934d17212850ee0cdd0de2957f17aec /compiler | |
| parent | 95e9f68eb50cfdaa830b07b3d960a311e4a0e540 (diff) | |
| parent | 040e1b6b5fccc4c9e084ce620f95ebf8fd13ed8d (diff) | |
| download | rust-f5a3039addd7dcdf6b79d47d8f308ad068cf3cb8.tar.gz rust-f5a3039addd7dcdf6b79d47d8f308ad068cf3cb8.zip | |
Rollup merge of #110783 - dtolnay:safeprint, r=petrochenkov
Fix ICE on --print=... i/o errors
`rustc --print=cfg > /dev/full`
**Before:** ICE (see below)
**After:** exits quietly with code 1.
```console
thread 'rustc' panicked at 'failed printing to stdout: No space left on device (os error 28)', library/std/src/io/stdio.rs:1019:9
stack backtrace:
0: 0x7ffa84d68f33 - std::backtrace_rs::backtrace::libunwind::trace::h527d8d64d53ade2d
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/../../backtrace/src/backtrace/libunwind.rs:93:5
1: 0x7ffa84d68f33 - std::backtrace_rs::backtrace::trace_unsynchronized::hfb55b01517dd6379
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/../../backtrace/src/backtrace/mod.rs:66:5
2: 0x7ffa84d68f33 - std::sys_common::backtrace::_print_fmt::hd134e914eea0bd97
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/sys_common/backtrace.rs:65:5
3: 0x7ffa84d68f33 - <std::sys_common::backtrace::_print::DisplayBacktrace as core::fmt::Display>::fmt::h1480db11ec399d77
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/sys_common/backtrace.rs:44:22
4: 0x7ffa84dc9d4f - core::fmt::write::h67ec4c4171c92b26
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/core/src/fmt/mod.rs:1247:17
5: 0x7ffa84d5bed1 - std::io::Write::write_fmt::h3b12aef0fff2463b
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/io/mod.rs:1712:15
6: 0x7ffa84d68d45 - std::sys_common::backtrace::_print::h584400135abdbd51
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/sys_common/backtrace.rs:47:5
7: 0x7ffa84d68d45 - std::sys_common::backtrace::print::hce41d3c8bd91096b
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/sys_common/backtrace.rs:34:9
8: 0x7ffa84d6b84f - std::panicking::default_hook::{{closure}}::h2043b657a3791225
9: 0x7ffa84d6b507 - std::panicking::default_hook::h99252b8d3dd5719c
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/panicking.rs:293:9
10: 0x7ffa87fdf915 - <rustc_driver_impl[d30cd2737d9d343a]::DEFAULT_HOOK::{closure#0}::{closure#0} as core[cc19a662f3570270]::ops::function::FnOnce<(&core[cc19a662f3570270]::panic::panic_info::PanicInfo,)>>::call_once::{shim:vtable#0}
11: 0x7ffa84d6c005 - <alloc::boxed::Box<F,A> as core::ops::function::Fn<Args>>::call::h222a2b674b9f4762
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/alloc/src/boxed.rs:1976:9
12: 0x7ffa84d6c005 - std::panicking::rust_panic_with_hook::h7f49b36bf7f8ff77
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/panicking.rs:704:13
13: 0x7ffa84d6bd73 - std::panicking::begin_panic_handler::{{closure}}::haa23a7352589e31e
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/panicking.rs:595:13
14: 0x7ffa84d69376 - std::sys_common::backtrace::__rust_end_short_backtrace::h3d0cf6e3c96e3fe9
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/sys_common/backtrace.rs:150:18
15: 0x7ffa84d6ba72 - rust_begin_unwind
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/panicking.rs:584:5
16: 0x7ffa84dc5fe3 - core::panicking::panic_fmt::hf4b4ea11e3fdb110
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/core/src/panicking.rs:67:14
17: 0x7ffa84d5aa07 - std::io::stdio::print_to::h55760b9ede306280
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/io/stdio.rs:1019:9
18: 0x7ffa84d5aa07 - std::io::stdio::_print::h93deb6099db33eab
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/io/stdio.rs:1095:5
19: 0x7ffa871e163b - rustc_driver_impl[d30cd2737d9d343a]::print_crate_info
20: 0x7ffa87fb8e01 - rustc_span[9551eaa044f53f4f]::set_source_map::<(), rustc_interface[c2b70c9b1dae0906]::interface::run_compiler<(), rustc_driver_impl[d30cd2737d9d343a]::run_compiler::{closure#0}>::{closure#0}::{closure#0}>
21: 0x7ffa87fb6d59 - std[71a32ca0600a6a04]::sys_common::backtrace::__rust_begin_short_backtrace::<rustc_interface[c2b70c9b1dae0906]::util::run_in_thread_pool_with_globals<rustc_interface[c2b70c9b1dae0906]::interface::run_compiler<(), rustc_driver_impl[d30cd2737d9d343a]::run_compiler::{closure#0}>::{closure#0}, ()>::{closure#0}::{closure#0}, ()>
22: 0x7ffa87fe25b4 - std[71a32ca0600a6a04]::panicking::try::<(), core[cc19a662f3570270]::panic::unwind_safe::AssertUnwindSafe<<std[71a32ca0600a6a04]::thread::Builder>::spawn_unchecked_<rustc_interface[c2b70c9b1dae0906]::util::run_in_thread_pool_with_globals<rustc_interface[c2b70c9b1dae0906]::interface::run_compiler<(), rustc_driver_impl[d30cd2737d9d343a]::run_compiler::{closure#0}>::{closure#0}, ()>::{closure#0}::{closure#0}, ()>::{closure#1}::{closure#0}>>
23: 0x7ffa87fb0cf1 - <<std[71a32ca0600a6a04]::thread::Builder>::spawn_unchecked_<rustc_interface[c2b70c9b1dae0906]::util::run_in_thread_pool_with_globals<rustc_interface[c2b70c9b1dae0906]::interface::run_compiler<(), rustc_driver_impl[d30cd2737d9d343a]::run_compiler::{closure#0}>::{closure#0}, ()>::{closure#0}::{closure#0}, ()>::{closure#1} as core[cc19a662f3570270]::ops::function::FnOnce<()>>::call_once::{shim:vtable#0}
24: 0x7ffa84d763e5 - <alloc::boxed::Box<F,A> as core::ops::function::FnOnce<Args>>::call_once::hf15d802f31f86225
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/alloc/src/boxed.rs:1962:9
25: 0x7ffa84d763e5 - <alloc::boxed::Box<F,A> as core::ops::function::FnOnce<Args>>::call_once::hac564355b46c52d6
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/alloc/src/boxed.rs:1962:9
26: 0x7ffa84d763e5 - std::sys::unix::thread::Thread::new::thread_start::h86fb3aedb7811f07
at /rustc/7f94b314cead7059a71a265a8b64905ef2511796/library/std/src/sys/unix/thread.rs:108:17
27: 0x7ffa84a94b43 - start_thread
at ./nptl/pthread_create.c:442:8
28: 0x7ffa84b26a00 - clone3
at ./misc/../sysdeps/unix/sysv/linux/x86_64/clone3.S:81
29: 0x0 - <unknown>
error: the compiler unexpectedly panicked. this is a bug.
note: we would appreciate a bug report: https://github.com/rust-lang/rust/issues/new?labels=C-bug%2C+I-ICE%2C+T-compiler&template=ice.md
note: rustc 1.71.0-nightly (7f94b314c 2023-04-23) running on x86_64-unknown-linux-gnu
query stack during panic:
end of query stack
```
Diffstat (limited to 'compiler')
| -rw-r--r-- | compiler/rustc_driver_impl/src/lib.rs | 88 | ||||
| -rw-r--r-- | compiler/rustc_driver_impl/src/print.rs | 20 |
2 files changed, 68 insertions, 40 deletions
diff --git a/compiler/rustc_driver_impl/src/lib.rs b/compiler/rustc_driver_impl/src/lib.rs index 1a80b4fc314..5fac485de64 100644 --- a/compiler/rustc_driver_impl/src/lib.rs +++ b/compiler/rustc_driver_impl/src/lib.rs @@ -58,8 +58,16 @@ use std::str; use std::sync::LazyLock; use std::time::Instant; +// This import blocks the use of panicking `print` and `println` in all the code +// below. Please use `safe_print` and `safe_println` to avoid ICE when +// encountering an I/O error during print. +#[allow(unused_imports)] +use std::{compile_error as print, compile_error as println}; + pub mod args; pub mod pretty; +#[macro_use] +mod print; mod session_diagnostics; use crate::session_diagnostics::{ @@ -511,7 +519,7 @@ fn handle_explain(registry: Registry, code: &str, output: ErrorOutputType) { if io::stdout().is_terminal() { show_content_with_pager(&text); } else { - print!("{text}"); + safe_print!("{text}"); } } Err(InvalidErrorCode) => { @@ -547,7 +555,7 @@ fn show_content_with_pager(content: &str) { // If pager fails for whatever reason, we should still print the content // to standard output if fallback_to_println { - print!("{content}"); + safe_print!("{content}"); } } @@ -601,7 +609,7 @@ pub fn list_metadata(sess: &Session, metadata_loader: &dyn MetadataLoader) -> Co let path = &(*ifile); let mut v = Vec::new(); locator::list_file_metadata(&sess.target, path, metadata_loader, &mut v).unwrap(); - println!("{}", String::from_utf8(v).unwrap()); + safe_println!("{}", String::from_utf8(v).unwrap()); } Input::Str { .. } => { early_error(ErrorOutputType::default(), "cannot list metadata for stdin"); @@ -642,12 +650,12 @@ fn print_crate_info( TargetList => { let mut targets = rustc_target::spec::TARGETS.to_vec(); targets.sort_unstable(); - println!("{}", targets.join("\n")); + safe_println!("{}", targets.join("\n")); } - Sysroot => println!("{}", sess.sysroot.display()), - TargetLibdir => println!("{}", sess.target_tlib_path.dir.display()), + Sysroot => safe_println!("{}", sess.sysroot.display()), + TargetLibdir => safe_println!("{}", sess.target_tlib_path.dir.display()), TargetSpec => { - println!("{}", serde_json::to_string_pretty(&sess.target.to_json()).unwrap()); + safe_println!("{}", serde_json::to_string_pretty(&sess.target.to_json()).unwrap()); } AllTargetSpecs => { let mut targets = BTreeMap::new(); @@ -656,7 +664,7 @@ fn print_crate_info( let target = Target::expect_builtin(&triple); targets.insert(name, target.to_json()); } - println!("{}", serde_json::to_string_pretty(&targets).unwrap()); + safe_println!("{}", serde_json::to_string_pretty(&targets).unwrap()); } FileNames | CrateName => { let Some(attrs) = attrs.as_ref() else { @@ -666,14 +674,14 @@ fn print_crate_info( let t_outputs = rustc_interface::util::build_output_filenames(attrs, sess); let id = rustc_session::output::find_crate_name(sess, attrs); if *req == PrintRequest::CrateName { - println!("{id}"); + safe_println!("{id}"); continue; } let crate_types = collect_crate_types(sess, attrs); for &style in &crate_types { let fname = rustc_session::output::filename_for_input(sess, style, id, &t_outputs); - println!("{}", fname.file_name().unwrap().to_string_lossy()); + safe_println!("{}", fname.file_name().unwrap().to_string_lossy()); } } Cfg => { @@ -707,13 +715,13 @@ fn print_crate_info( cfgs.sort(); for cfg in cfgs { - println!("{cfg}"); + safe_println!("{cfg}"); } } CallingConventions => { let mut calling_conventions = rustc_target::spec::abi::all_names(); calling_conventions.sort_unstable(); - println!("{}", calling_conventions.join("\n")); + safe_println!("{}", calling_conventions.join("\n")); } RelocationModels | CodeModels @@ -733,7 +741,7 @@ fn print_crate_info( let stable = sess.target.options.supported_split_debuginfo.contains(split); let unstable_ok = sess.unstable_options(); if stable || unstable_ok { - println!("{split}"); + safe_println!("{split}"); } } } @@ -770,14 +778,14 @@ pub fn version_at_macro_invocation( ) { let verbose = matches.opt_present("verbose"); - println!("{binary} {version}"); + safe_println!("{binary} {version}"); if verbose { - println!("binary: {binary}"); - println!("commit-hash: {commit_hash}"); - println!("commit-date: {commit_date}"); - println!("host: {}", config::host_triple()); - println!("release: {release}"); + safe_println!("binary: {binary}"); + safe_println!("commit-hash: {commit_hash}"); + safe_println!("commit-date: {commit_date}"); + safe_println!("host: {}", config::host_triple()); + safe_println!("release: {release}"); let debug_flags = matches.opt_strs("Z"); let backend_name = debug_flags.iter().find_map(|x| x.strip_prefix("codegen-backend=")); @@ -807,7 +815,7 @@ fn usage(verbose: bool, include_unstable_options: bool, nightly_build: bool) { } else { "" }; - println!( + safe_println!( "{options}{at_path}\nAdditional help: -C help Print codegen options -W help \ @@ -820,7 +828,7 @@ fn usage(verbose: bool, include_unstable_options: bool, nightly_build: bool) { } fn print_wall_help() { - println!( + safe_println!( " The flag `-Wall` does not exist in `rustc`. Most useful lints are enabled by default. Use `rustc -W help` to see all available lints. It's more common to put @@ -832,7 +840,7 @@ the command line flag directly. /// Write to stdout lint command options, together with a list of all available lints pub fn describe_lints(sess: &Session, lint_store: &LintStore, loaded_plugins: bool) { - println!( + safe_println!( " Available lint options: -W <foo> Warn about <foo> @@ -877,21 +885,21 @@ Available lint options: s }; - println!("Lint checks provided by rustc:\n"); + safe_println!("Lint checks provided by rustc:\n"); let print_lints = |lints: Vec<&Lint>| { - println!(" {} {:7.7} {}", padded("name"), "default", "meaning"); - println!(" {} {:7.7} {}", padded("----"), "-------", "-------"); + safe_println!(" {} {:7.7} {}", padded("name"), "default", "meaning"); + safe_println!(" {} {:7.7} {}", padded("----"), "-------", "-------"); for lint in lints { let name = lint.name_lower().replace('_', "-"); - println!( + safe_println!( " {} {:7.7} {}", padded(&name), lint.default_level(sess.edition()).as_str(), lint.desc ); } - println!("\n"); + safe_println!("\n"); }; print_lints(builtin); @@ -912,14 +920,14 @@ Available lint options: s }; - println!("Lint groups provided by rustc:\n"); + safe_println!("Lint groups provided by rustc:\n"); let print_lint_groups = |lints: Vec<(&'static str, Vec<LintId>)>, all_warnings| { - println!(" {} sub-lints", padded("name")); - println!(" {} ---------", padded("----")); + safe_println!(" {} sub-lints", padded("name")); + safe_println!(" {} ---------", padded("----")); if all_warnings { - println!(" {} all lints that are set to issue warnings", padded("warnings")); + safe_println!(" {} all lints that are set to issue warnings", padded("warnings")); } for (name, to) in lints { @@ -929,26 +937,26 @@ Available lint options: .map(|x| x.to_string().replace('_', "-")) .collect::<Vec<String>>() .join(", "); - println!(" {} {}", padded(&name), desc); + safe_println!(" {} {}", padded(&name), desc); } - println!("\n"); + safe_println!("\n"); }; print_lint_groups(builtin_groups, true); match (loaded_plugins, plugin.len(), plugin_groups.len()) { (false, 0, _) | (false, _, 0) => { - println!("Lint tools like Clippy can provide additional lints and lint groups."); + safe_println!("Lint tools like Clippy can provide additional lints and lint groups."); } (false, ..) => panic!("didn't load lint plugins but got them anyway!"), - (true, 0, 0) => println!("This crate does not load any lint plugins or lint groups."), + (true, 0, 0) => safe_println!("This crate does not load any lint plugins or lint groups."), (true, l, g) => { if l > 0 { - println!("Lint checks provided by plugins loaded by this crate:\n"); + safe_println!("Lint checks provided by plugins loaded by this crate:\n"); print_lints(plugin); } if g > 0 { - println!("Lint groups provided by plugins loaded by this crate:\n"); + safe_println!("Lint groups provided by plugins loaded by this crate:\n"); print_lint_groups(plugin_groups, false); } } @@ -996,12 +1004,12 @@ pub fn describe_flag_categories(matches: &Matches) -> bool { } fn describe_debug_flags() { - println!("\nAvailable options:\n"); + safe_println!("\nAvailable options:\n"); print_flag_list("-Z", config::Z_OPTIONS); } fn describe_codegen_flags() { - println!("\nAvailable codegen options:\n"); + safe_println!("\nAvailable codegen options:\n"); print_flag_list("-C", config::CG_OPTIONS); } @@ -1012,7 +1020,7 @@ fn print_flag_list<T>( let max_len = flag_list.iter().map(|&(name, _, _, _)| name.chars().count()).max().unwrap_or(0); for &(name, _, _, desc) in flag_list { - println!( + safe_println!( " {} {:>width$}=val -- {}", cmdline_opt, name.replace('_', "-"), diff --git a/compiler/rustc_driver_impl/src/print.rs b/compiler/rustc_driver_impl/src/print.rs new file mode 100644 index 00000000000..70de55320f7 --- /dev/null +++ b/compiler/rustc_driver_impl/src/print.rs @@ -0,0 +1,20 @@ +use std::fmt; +use std::io::{self, Write as _}; + +macro_rules! safe_print { + ($($arg:tt)*) => {{ + $crate::print::print(std::format_args!($($arg)*)); + }}; +} + +macro_rules! safe_println { + ($($arg:tt)*) => { + safe_print!("{}\n", std::format_args!($($arg)*)) + }; +} + +pub(crate) fn print(args: fmt::Arguments<'_>) { + if let Err(_) = io::stdout().write_fmt(args) { + rustc_errors::FatalError.raise(); + } +} |
