From 4cfb7add771367757ee2dd26da4e29d333c93cb6 Mon Sep 17 00:00:00 2001 From: Cameron Steffen Date: Thu, 21 Oct 2021 09:01:16 -0500 Subject: [PATCH 1/5] Fix a format_args span to be expansion --- compiler/rustc_builtin_macros/src/format.rs | 5 ++++- src/test/ui/borrowck/borrowck-and-init.stderr | 2 ++ src/test/ui/borrowck/borrowck-break-uninit-2.stderr | 2 ++ src/test/ui/borrowck/borrowck-break-uninit.stderr | 2 ++ src/test/ui/borrowck/borrowck-or-init.stderr | 2 ++ src/test/ui/borrowck/borrowck-while-break.stderr | 2 ++ src/test/ui/borrowck/issue-24267-flow-exit.stderr | 4 ++++ .../closures/2229_closure_analysis/diagnostics/arrays.stderr | 2 ++ .../ui/closures/2229_closure_analysis/diagnostics/box.stderr | 2 ++ .../2229_closure_analysis/diagnostics/repr_packed.stderr | 1 + .../diagnostics/simple-struct-min-capture.stderr | 2 ++ src/test/ui/codemap_tests/tab_3.stderr | 1 + .../ui/consts/const-eval/conditional_array_execution.stderr | 1 + src/test/ui/consts/const-eval/issue-43197.stderr | 2 ++ src/test/ui/generator/yield-while-ref-reborrowed.stderr | 2 ++ src/test/ui/issues/issue-42796.stderr | 2 ++ src/test/ui/issues/issue-47646.stderr | 2 ++ src/test/ui/limits/issue-55878.stderr | 1 + src/test/ui/liveness/liveness-move-in-while.stderr | 2 ++ src/test/ui/liveness/liveness-use-after-move.stderr | 2 ++ src/test/ui/liveness/liveness-use-after-send.stderr | 2 ++ src/test/ui/loops/loop-proper-liveness.stderr | 2 ++ .../ui/moves/moves-based-on-type-capture-clause-bad.stderr | 2 ++ src/test/ui/try-block/try-block-maybe-bad-lifetime.stderr | 2 ++ src/test/ui/use/use-after-move-based-on-type.stderr | 2 ++ src/test/ui/walk-struct-literal-with.stderr | 1 + 26 files changed, 51 insertions(+), 1 deletion(-) diff --git a/compiler/rustc_builtin_macros/src/format.rs b/compiler/rustc_builtin_macros/src/format.rs index f0056cb79766a..3f9ea371583be 100644 --- a/compiler/rustc_builtin_macros/src/format.rs +++ b/compiler/rustc_builtin_macros/src/format.rs @@ -793,7 +793,10 @@ impl<'a, 'b> Context<'a, 'b> { for arg_ty in self.arg_unique_types[i].iter() { locals.push(Context::format_arg(self.ecx, self.macsp, e.span, arg_ty, name)); } - heads.push(self.ecx.expr_addr_of(e.span, e)); + // use the arg span for `&arg` so that borrowck errors + // point to the specific expression passed to the macro + // (the span is otherwise unavailable in MIR) + heads.push(self.ecx.expr_addr_of(e.span.with_ctxt(self.macsp.ctxt()), e)); } for pos in self.count_args { let index = match pos { diff --git a/src/test/ui/borrowck/borrowck-and-init.stderr b/src/test/ui/borrowck/borrowck-and-init.stderr index c7e357d4604f7..d2c7473c036b8 100644 --- a/src/test/ui/borrowck/borrowck-and-init.stderr +++ b/src/test/ui/borrowck/borrowck-and-init.stderr @@ -3,6 +3,8 @@ error[E0381]: borrow of possibly-uninitialized variable: `i` | LL | println!("{}", i); | ^ use of possibly-uninitialized `i` + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/borrowck/borrowck-break-uninit-2.stderr b/src/test/ui/borrowck/borrowck-break-uninit-2.stderr index bc9b25c0221fc..b134f5cc2d8e3 100644 --- a/src/test/ui/borrowck/borrowck-break-uninit-2.stderr +++ b/src/test/ui/borrowck/borrowck-break-uninit-2.stderr @@ -3,6 +3,8 @@ error[E0381]: borrow of possibly-uninitialized variable: `x` | LL | println!("{}", x); | ^ use of possibly-uninitialized `x` + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/borrowck/borrowck-break-uninit.stderr b/src/test/ui/borrowck/borrowck-break-uninit.stderr index 766d5cfd6348c..652d7d3076fbd 100644 --- a/src/test/ui/borrowck/borrowck-break-uninit.stderr +++ b/src/test/ui/borrowck/borrowck-break-uninit.stderr @@ -3,6 +3,8 @@ error[E0381]: borrow of possibly-uninitialized variable: `x` | LL | println!("{}", x); | ^ use of possibly-uninitialized `x` + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/borrowck/borrowck-or-init.stderr b/src/test/ui/borrowck/borrowck-or-init.stderr index 3fe8d9eededc5..6c757759f7134 100644 --- a/src/test/ui/borrowck/borrowck-or-init.stderr +++ b/src/test/ui/borrowck/borrowck-or-init.stderr @@ -3,6 +3,8 @@ error[E0381]: borrow of possibly-uninitialized variable: `i` | LL | println!("{}", i); | ^ use of possibly-uninitialized `i` + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/borrowck/borrowck-while-break.stderr b/src/test/ui/borrowck/borrowck-while-break.stderr index 3eaaf8d7df08d..fc144a066bb27 100644 --- a/src/test/ui/borrowck/borrowck-while-break.stderr +++ b/src/test/ui/borrowck/borrowck-while-break.stderr @@ -3,6 +3,8 @@ error[E0381]: borrow of possibly-uninitialized variable: `v` | LL | println!("{}", v); | ^ use of possibly-uninitialized `v` + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/borrowck/issue-24267-flow-exit.stderr b/src/test/ui/borrowck/issue-24267-flow-exit.stderr index 4eb41ca24ddfe..e29cf7a1a7519 100644 --- a/src/test/ui/borrowck/issue-24267-flow-exit.stderr +++ b/src/test/ui/borrowck/issue-24267-flow-exit.stderr @@ -3,12 +3,16 @@ error[E0381]: borrow of possibly-uninitialized variable: `x` | LL | println!("{}", x); | ^ use of possibly-uninitialized `x` + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error[E0381]: borrow of possibly-uninitialized variable: `x` --> $DIR/issue-24267-flow-exit.rs:18:20 | LL | println!("{}", x); | ^ use of possibly-uninitialized `x` + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to 2 previous errors diff --git a/src/test/ui/closures/2229_closure_analysis/diagnostics/arrays.stderr b/src/test/ui/closures/2229_closure_analysis/diagnostics/arrays.stderr index a3f2f25e447e1..f6c2190183211 100644 --- a/src/test/ui/closures/2229_closure_analysis/diagnostics/arrays.stderr +++ b/src/test/ui/closures/2229_closure_analysis/diagnostics/arrays.stderr @@ -81,6 +81,8 @@ LL | println!("{}", arr[3]); ... LL | c(); | - mutable borrow later used here + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error[E0502]: cannot borrow `arr` as immutable because it is also borrowed as mutable --> $DIR/arrays.rs:73:24 diff --git a/src/test/ui/closures/2229_closure_analysis/diagnostics/box.stderr b/src/test/ui/closures/2229_closure_analysis/diagnostics/box.stderr index 2badf0514187e..29228d85324ef 100644 --- a/src/test/ui/closures/2229_closure_analysis/diagnostics/box.stderr +++ b/src/test/ui/closures/2229_closure_analysis/diagnostics/box.stderr @@ -25,6 +25,8 @@ LL | println!("{}", e.0.0.m.x); LL | LL | c(); | - mutable borrow later used here + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error[E0506]: cannot assign to `e.0.0.m.x` because it is borrowed --> $DIR/box.rs:55:5 diff --git a/src/test/ui/closures/2229_closure_analysis/diagnostics/repr_packed.stderr b/src/test/ui/closures/2229_closure_analysis/diagnostics/repr_packed.stderr index d2466681a0877..5acf3797ab53f 100644 --- a/src/test/ui/closures/2229_closure_analysis/diagnostics/repr_packed.stderr +++ b/src/test/ui/closures/2229_closure_analysis/diagnostics/repr_packed.stderr @@ -8,6 +8,7 @@ LL | println!("{}", foo.x); = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release! = note: for more information, see issue #82523 = note: fields of packed structs are not properly aligned, and creating a misaligned reference is undefined behavior (even if that reference is never dereferenced) + = note: this warning originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) warning: 1 warning emitted diff --git a/src/test/ui/closures/2229_closure_analysis/diagnostics/simple-struct-min-capture.stderr b/src/test/ui/closures/2229_closure_analysis/diagnostics/simple-struct-min-capture.stderr index 32705af3d0166..4f9fdbd368a88 100644 --- a/src/test/ui/closures/2229_closure_analysis/diagnostics/simple-struct-min-capture.stderr +++ b/src/test/ui/closures/2229_closure_analysis/diagnostics/simple-struct-min-capture.stderr @@ -13,6 +13,8 @@ LL | println!("{:?}", p); LL | LL | c(); | - mutable borrow later used here + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/codemap_tests/tab_3.stderr b/src/test/ui/codemap_tests/tab_3.stderr index e067dbbf85bdd..ceb91142ac826 100644 --- a/src/test/ui/codemap_tests/tab_3.stderr +++ b/src/test/ui/codemap_tests/tab_3.stderr @@ -14,6 +14,7 @@ note: this function takes ownership of the receiver `self`, which moves `some_ve | LL | fn into_iter(self) -> Self::IntoIter; | ^^^^ + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/consts/const-eval/conditional_array_execution.stderr b/src/test/ui/consts/const-eval/conditional_array_execution.stderr index 356a7f58d8562..9dc40030a6ff8 100644 --- a/src/test/ui/consts/const-eval/conditional_array_execution.stderr +++ b/src/test/ui/consts/const-eval/conditional_array_execution.stderr @@ -28,6 +28,7 @@ LL | println!("{}", FOO); | = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release! = note: for more information, see issue #71800 + = note: this warning originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error; 2 warnings emitted diff --git a/src/test/ui/consts/const-eval/issue-43197.stderr b/src/test/ui/consts/const-eval/issue-43197.stderr index d4d8cbc669a7b..32ab7c74b891f 100644 --- a/src/test/ui/consts/const-eval/issue-43197.stderr +++ b/src/test/ui/consts/const-eval/issue-43197.stderr @@ -39,6 +39,7 @@ LL | println!("{} {}", X, Y); | = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release! = note: for more information, see issue #71800 + = note: this warning originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error[E0080]: evaluation of constant value failed --> $DIR/issue-43197.rs:16:26 @@ -54,6 +55,7 @@ LL | println!("{} {}", X, Y); | = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release! = note: for more information, see issue #71800 + = note: this warning originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to 2 previous errors; 4 warnings emitted diff --git a/src/test/ui/generator/yield-while-ref-reborrowed.stderr b/src/test/ui/generator/yield-while-ref-reborrowed.stderr index 68d785efcfe5d..67cd1f64d94aa 100644 --- a/src/test/ui/generator/yield-while-ref-reborrowed.stderr +++ b/src/test/ui/generator/yield-while-ref-reborrowed.stderr @@ -10,6 +10,8 @@ LL | println!("{}", x); | ^ second borrow occurs here LL | Pin::new(&mut b).resume(()); | ------ first borrow later used here + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/issues/issue-42796.stderr b/src/test/ui/issues/issue-42796.stderr index 61cf3f25d0d07..4a1debf37a079 100644 --- a/src/test/ui/issues/issue-42796.stderr +++ b/src/test/ui/issues/issue-42796.stderr @@ -8,6 +8,8 @@ LL | let mut s_copy = s; ... LL | println!("{}", s); | ^ value borrowed here after move + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/issues/issue-47646.stderr b/src/test/ui/issues/issue-47646.stderr index eff1de3e01752..32e8588b3c074 100644 --- a/src/test/ui/issues/issue-47646.stderr +++ b/src/test/ui/issues/issue-47646.stderr @@ -12,6 +12,8 @@ LL | println!("{:?}", heap); ... LL | }; | - ... and the mutable borrow might be used here, when that temporary is dropped and runs the destructor for type `(Option>, ())` + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/limits/issue-55878.stderr b/src/test/ui/limits/issue-55878.stderr index a7e382479021a..90411353f0825 100644 --- a/src/test/ui/limits/issue-55878.stderr +++ b/src/test/ui/limits/issue-55878.stderr @@ -18,6 +18,7 @@ LL | println!("Size: {}", std::mem::size_of::<[u8; u64::MAX as usize]>()); = note: `#[deny(const_err)]` on by default = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release! = note: for more information, see issue #71800 + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to 2 previous errors diff --git a/src/test/ui/liveness/liveness-move-in-while.stderr b/src/test/ui/liveness/liveness-move-in-while.stderr index 6a8f239bd09a8..ff6c02f2110f6 100644 --- a/src/test/ui/liveness/liveness-move-in-while.stderr +++ b/src/test/ui/liveness/liveness-move-in-while.stderr @@ -28,6 +28,8 @@ LL | println!("{}", y); | ^ value borrowed here after move LL | while true { while true { while true { x = y; x.clone(); } } } | - value moved here, in previous iteration of loop + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error; 3 warnings emitted diff --git a/src/test/ui/liveness/liveness-use-after-move.stderr b/src/test/ui/liveness/liveness-use-after-move.stderr index 292ce013dcc76..df54af9f0f2ce 100644 --- a/src/test/ui/liveness/liveness-use-after-move.stderr +++ b/src/test/ui/liveness/liveness-use-after-move.stderr @@ -8,6 +8,8 @@ LL | let y = x; LL | LL | println!("{}", *x); | ^^ value borrowed here after move + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/liveness/liveness-use-after-send.stderr b/src/test/ui/liveness/liveness-use-after-send.stderr index 50ae98ca9bedc..becede1ceb6b3 100644 --- a/src/test/ui/liveness/liveness-use-after-send.stderr +++ b/src/test/ui/liveness/liveness-use-after-send.stderr @@ -7,6 +7,8 @@ LL | send(ch, message); | ------- value moved here LL | println!("{}", message); | ^^^^^^^ value borrowed here after move + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/loops/loop-proper-liveness.stderr b/src/test/ui/loops/loop-proper-liveness.stderr index d55f9ff31e3ee..20d5c66a3f205 100644 --- a/src/test/ui/loops/loop-proper-liveness.stderr +++ b/src/test/ui/loops/loop-proper-liveness.stderr @@ -3,6 +3,8 @@ error[E0381]: borrow of possibly-uninitialized variable: `x` | LL | println!("{:?}", x); | ^ use of possibly-uninitialized `x` + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/moves/moves-based-on-type-capture-clause-bad.stderr b/src/test/ui/moves/moves-based-on-type-capture-clause-bad.stderr index acb0932f6d6b9..ac921c18e07d5 100644 --- a/src/test/ui/moves/moves-based-on-type-capture-clause-bad.stderr +++ b/src/test/ui/moves/moves-based-on-type-capture-clause-bad.stderr @@ -10,6 +10,8 @@ LL | println!("{}", x); LL | }); LL | println!("{}", x); | ^ value borrowed here after move + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/try-block/try-block-maybe-bad-lifetime.stderr b/src/test/ui/try-block/try-block-maybe-bad-lifetime.stderr index c092aa26946f6..d6822d94ca8c9 100644 --- a/src/test/ui/try-block/try-block-maybe-bad-lifetime.stderr +++ b/src/test/ui/try-block/try-block-maybe-bad-lifetime.stderr @@ -21,6 +21,8 @@ LL | ::std::mem::drop(x); LL | }; LL | println!("{}", x); | ^ value borrowed here after move + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error[E0506]: cannot assign to `i` because it is borrowed --> $DIR/try-block-maybe-bad-lifetime.rs:40:9 diff --git a/src/test/ui/use/use-after-move-based-on-type.stderr b/src/test/ui/use/use-after-move-based-on-type.stderr index 11ce005bb457c..361a6e2d8c278 100644 --- a/src/test/ui/use/use-after-move-based-on-type.stderr +++ b/src/test/ui/use/use-after-move-based-on-type.stderr @@ -7,6 +7,8 @@ LL | let _y = x; | - value moved here LL | println!("{}", x); | ^ value borrowed here after move + | + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error diff --git a/src/test/ui/walk-struct-literal-with.stderr b/src/test/ui/walk-struct-literal-with.stderr index cda08b0f4e09c..377a807445891 100644 --- a/src/test/ui/walk-struct-literal-with.stderr +++ b/src/test/ui/walk-struct-literal-with.stderr @@ -13,6 +13,7 @@ note: this function takes ownership of the receiver `self`, which moves `start` | LL | fn make_string_bar(mut self) -> Mine{ | ^^^^ + = note: this error originates in the macro `$crate::format_args_nl` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to previous error From b16ac4cbbae108bfd184569a2c50bde247d04fdf Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tomasz=20Mi=C4=85sko?= Date: Fri, 12 Nov 2021 00:00:00 +0000 Subject: [PATCH 2/5] Use brief format for optimization remarks --- compiler/rustc_codegen_llvm/src/back/write.rs | 9 ++------- 1 file changed, 2 insertions(+), 7 deletions(-) diff --git a/compiler/rustc_codegen_llvm/src/back/write.rs b/compiler/rustc_codegen_llvm/src/back/write.rs index 3d05fc15b38f4..80fc39846cd1b 100644 --- a/compiler/rustc_codegen_llvm/src/back/write.rs +++ b/compiler/rustc_codegen_llvm/src/back/write.rs @@ -337,13 +337,8 @@ unsafe extern "C" fn diagnostic_handler(info: &DiagnosticInfo, user: *mut c_void if enabled { diag_handler.note_without_error(&format!( - "optimization {} for {} at {}:{}:{}: {}", - opt.kind.describe(), - opt.pass_name, - opt.filename, - opt.line, - opt.column, - opt.message + "{}:{}:{}: {}: {}", + opt.filename, opt.line, opt.column, opt.pass_name, opt.message, )); } } From 6846674c75530796b3d7709ff8a602e046ce08d8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tomasz=20Mi=C4=85sko?= Date: Fri, 12 Nov 2021 00:00:00 +0000 Subject: [PATCH 3/5] Emit LLVM optimization remarks when enabled with `-Cremark` The default diagnostic handler considers all remarks to be disabled by default unless configured otherwise through LLVM internal flags: `-pass-remarks`, `-pass-remarks-missed`, and `-pass-remarks-analysis`. This behaviour makes `-Cremark` ineffective on its own. Fix this by configuring a custom diagnostic handler that enables optimization remarks based on the value of `-Cremark` option. With `-Cremark=all` enabling all remarks. --- compiler/rustc_codegen_llvm/src/back/write.rs | 30 ++++++- compiler/rustc_codegen_llvm/src/llvm/ffi.rs | 31 +++++-- .../rustc_llvm/llvm-wrapper/RustWrapper.cpp | 90 +++++++++++++++++++ src/test/ui/optimization-remark.rs | 19 ++++ 4 files changed, 158 insertions(+), 12 deletions(-) create mode 100644 src/test/ui/optimization-remark.rs diff --git a/compiler/rustc_codegen_llvm/src/back/write.rs b/compiler/rustc_codegen_llvm/src/back/write.rs index 80fc39846cd1b..460a8cc69128e 100644 --- a/compiler/rustc_codegen_llvm/src/back/write.rs +++ b/compiler/rustc_codegen_llvm/src/back/write.rs @@ -259,6 +259,7 @@ pub(crate) fn save_temp_bitcode( pub struct DiagnosticHandlers<'a> { data: *mut (&'a CodegenContext, &'a Handler), llcx: &'a llvm::Context, + old_handler: Option<&'a llvm::DiagnosticHandler>, } impl<'a> DiagnosticHandlers<'a> { @@ -267,12 +268,35 @@ impl<'a> DiagnosticHandlers<'a> { handler: &'a Handler, llcx: &'a llvm::Context, ) -> Self { + let remark_passes_all: bool; + let remark_passes: Vec; + match &cgcx.remark { + Passes::All => { + remark_passes_all = true; + remark_passes = Vec::new(); + } + Passes::Some(passes) => { + remark_passes_all = false; + remark_passes = + passes.iter().map(|name| CString::new(name.as_str()).unwrap()).collect(); + } + }; + let remark_passes: Vec<*const c_char> = + remark_passes.iter().map(|name: &CString| name.as_ptr()).collect(); let data = Box::into_raw(Box::new((cgcx, handler))); unsafe { + let old_handler = llvm::LLVMRustContextGetDiagnosticHandler(llcx); + llvm::LLVMRustContextConfigureDiagnosticHandler( + llcx, + diagnostic_handler, + data.cast(), + remark_passes_all, + remark_passes.as_ptr(), + remark_passes.len(), + ); llvm::LLVMRustSetInlineAsmDiagnosticHandler(llcx, inline_asm_handler, data.cast()); - llvm::LLVMContextSetDiagnosticHandler(llcx, diagnostic_handler, data.cast()); + DiagnosticHandlers { data, llcx, old_handler } } - DiagnosticHandlers { data, llcx } } } @@ -281,7 +305,7 @@ impl<'a> Drop for DiagnosticHandlers<'a> { use std::ptr::null_mut; unsafe { llvm::LLVMRustSetInlineAsmDiagnosticHandler(self.llcx, inline_asm_handler, null_mut()); - llvm::LLVMContextSetDiagnosticHandler(self.llcx, diagnostic_handler, null_mut()); + llvm::LLVMRustContextSetDiagnosticHandler(self.llcx, self.old_handler); drop(Box::from_raw(self.data)); } } diff --git a/compiler/rustc_codegen_llvm/src/llvm/ffi.rs b/compiler/rustc_codegen_llvm/src/llvm/ffi.rs index 749eec459aca1..9bff020e5d704 100644 --- a/compiler/rustc_codegen_llvm/src/llvm/ffi.rs +++ b/compiler/rustc_codegen_llvm/src/llvm/ffi.rs @@ -672,8 +672,12 @@ pub struct OperandBundleDef<'a>(InvariantOpaque<'a>); #[repr(C)] pub struct Linker<'a>(InvariantOpaque<'a>); -pub type DiagnosticHandler = unsafe extern "C" fn(&DiagnosticInfo, *mut c_void); -pub type InlineAsmDiagHandler = unsafe extern "C" fn(&SMDiagnostic, *const c_void, c_uint); +extern "C" { + pub type DiagnosticHandler; +} + +pub type DiagnosticHandlerTy = unsafe extern "C" fn(&DiagnosticInfo, *mut c_void); +pub type InlineAsmDiagHandlerTy = unsafe extern "C" fn(&SMDiagnostic, *const c_void, c_uint); pub mod coverageinfo { use super::coverage_map; @@ -2286,12 +2290,6 @@ extern "C" { #[allow(improper_ctypes)] pub fn LLVMRustWriteTwineToString(T: &Twine, s: &RustString); - pub fn LLVMContextSetDiagnosticHandler( - C: &Context, - Handler: DiagnosticHandler, - DiagnosticContext: *mut c_void, - ); - #[allow(improper_ctypes)] pub fn LLVMRustUnpackOptimizationDiagnostic( DI: &'a DiagnosticInfo, @@ -2321,7 +2319,7 @@ extern "C" { pub fn LLVMRustSetInlineAsmDiagnosticHandler( C: &Context, - H: InlineAsmDiagHandler, + H: InlineAsmDiagHandlerTy, CX: *mut c_void, ); @@ -2436,4 +2434,19 @@ extern "C" { mod_id: *const c_char, data: &ThinLTOData, ); + + pub fn LLVMRustContextGetDiagnosticHandler(Context: &Context) -> Option<&DiagnosticHandler>; + pub fn LLVMRustContextSetDiagnosticHandler( + context: &Context, + diagnostic_handler: Option<&DiagnosticHandler>, + ); + pub fn LLVMRustContextConfigureDiagnosticHandler( + context: &Context, + diagnostic_handler_callback: DiagnosticHandlerTy, + diagnostic_handler_context: *mut c_void, + remark_all_passes: bool, + remark_passes: *const *const c_char, + remark_passes_len: usize, + ); + } diff --git a/compiler/rustc_llvm/llvm-wrapper/RustWrapper.cpp b/compiler/rustc_llvm/llvm-wrapper/RustWrapper.cpp index e77d29bed7122..e8b490fb019a7 100644 --- a/compiler/rustc_llvm/llvm-wrapper/RustWrapper.cpp +++ b/compiler/rustc_llvm/llvm-wrapper/RustWrapper.cpp @@ -1,5 +1,6 @@ #include "LLVMWrapper.h" #include "llvm/IR/DebugInfoMetadata.h" +#include "llvm/IR/DiagnosticHandler.h" #include "llvm/IR/DiagnosticInfo.h" #include "llvm/IR/DiagnosticPrinter.h" #include "llvm/IR/GlobalVariable.h" @@ -1767,3 +1768,92 @@ extern "C" LLVMRustResult LLVMRustWriteImportLibrary( return LLVMRustResult::Success; } } + +// Transfers ownership of DiagnosticHandler unique_ptr to the caller. +extern "C" DiagnosticHandler * +LLVMRustContextGetDiagnosticHandler(LLVMContextRef C) { + std::unique_ptr DH = unwrap(C)->getDiagnosticHandler(); + return DH.release(); +} + +// Sets unique_ptr to object of DiagnosticHandler to provide custom diagnostic +// handling. Ownership of the handler is moved to the LLVMContext. +extern "C" void LLVMRustContextSetDiagnosticHandler(LLVMContextRef C, + DiagnosticHandler *DH) { + unwrap(C)->setDiagnosticHandler(std::unique_ptr(DH)); +} + +using LLVMDiagnosticHandlerTy = DiagnosticHandler::DiagnosticHandlerTy; + +// Configures a diagnostic handler that invokes provided callback when a +// backend needs to emit a diagnostic. +// +// When RemarkAllPasses is true, remarks are enabled for all passes. Otherwise +// the RemarkPasses array specifies individual passes for which remarks will be +// enabled. +extern "C" void LLVMRustContextConfigureDiagnosticHandler( + LLVMContextRef C, LLVMDiagnosticHandlerTy DiagnosticHandlerCallback, + void *DiagnosticHandlerContext, bool RemarkAllPasses, + const char * const * RemarkPasses, size_t RemarkPassesLen) { + + class RustDiagnosticHandler final : public DiagnosticHandler { + public: + RustDiagnosticHandler(LLVMDiagnosticHandlerTy DiagnosticHandlerCallback, + void *DiagnosticHandlerContext, + bool RemarkAllPasses, + std::vector RemarkPasses) + : DiagnosticHandlerCallback(DiagnosticHandlerCallback), + DiagnosticHandlerContext(DiagnosticHandlerContext), + RemarkAllPasses(RemarkAllPasses), + RemarkPasses(RemarkPasses) {} + + virtual bool handleDiagnostics(const DiagnosticInfo &DI) override { + if (DiagnosticHandlerCallback) { + DiagnosticHandlerCallback(DI, DiagnosticHandlerContext); + return true; + } + return false; + } + + bool isAnalysisRemarkEnabled(StringRef PassName) const override { + return isRemarkEnabled(PassName); + } + + bool isMissedOptRemarkEnabled(StringRef PassName) const override { + return isRemarkEnabled(PassName); + } + + bool isPassedOptRemarkEnabled(StringRef PassName) const override { + return isRemarkEnabled(PassName); + } + + bool isAnyRemarkEnabled() const override { + return RemarkAllPasses || !RemarkPasses.empty(); + } + + private: + bool isRemarkEnabled(StringRef PassName) const { + if (RemarkAllPasses) + return true; + + for (auto &Pass : RemarkPasses) + if (Pass == PassName) + return true; + + return false; + } + + LLVMDiagnosticHandlerTy DiagnosticHandlerCallback = nullptr; + void *DiagnosticHandlerContext = nullptr; + + bool RemarkAllPasses = false; + std::vector RemarkPasses; + }; + + std::vector Passes; + for (size_t I = 0; I != RemarkPassesLen; ++I) + Passes.push_back(RemarkPasses[I]); + + unwrap(C)->setDiagnosticHandler(std::make_unique( + DiagnosticHandlerCallback, DiagnosticHandlerContext, RemarkAllPasses, Passes)); +} diff --git a/src/test/ui/optimization-remark.rs b/src/test/ui/optimization-remark.rs new file mode 100644 index 0000000000000..7aedb09928b64 --- /dev/null +++ b/src/test/ui/optimization-remark.rs @@ -0,0 +1,19 @@ +// build-pass +// ignore-pass +// no-system-llvm +// revisions: all inline +// compile-flags: --crate-type=lib -Cdebuginfo=1 -Copt-level=2 +// [all] compile-flags: -Cremark=all +// [inline] compile-flags: -Cremark=inline +// error-pattern: inline: f not inlined into g +// dont-check-compiler-stderr + +#[no_mangle] +#[inline(never)] +pub fn f() { +} + +#[no_mangle] +pub fn g() { + f(); +} From 8fa45295f44febfa7035caeb149b2adfaa58fc50 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tomasz=20Mi=C4=85sko?= Date: Fri, 12 Nov 2021 00:00:00 +0000 Subject: [PATCH 4/5] Recognize machine optimization remarks --- compiler/rustc_llvm/llvm-wrapper/RustWrapper.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/compiler/rustc_llvm/llvm-wrapper/RustWrapper.cpp b/compiler/rustc_llvm/llvm-wrapper/RustWrapper.cpp index e8b490fb019a7..f4b41de12e603 100644 --- a/compiler/rustc_llvm/llvm-wrapper/RustWrapper.cpp +++ b/compiler/rustc_llvm/llvm-wrapper/RustWrapper.cpp @@ -1162,10 +1162,13 @@ static LLVMRustDiagnosticKind toRust(DiagnosticKind Kind) { case DK_SampleProfile: return LLVMRustDiagnosticKind::SampleProfile; case DK_OptimizationRemark: + case DK_MachineOptimizationRemark: return LLVMRustDiagnosticKind::OptimizationRemark; case DK_OptimizationRemarkMissed: + case DK_MachineOptimizationRemarkMissed: return LLVMRustDiagnosticKind::OptimizationRemarkMissed; case DK_OptimizationRemarkAnalysis: + case DK_MachineOptimizationRemarkAnalysis: return LLVMRustDiagnosticKind::OptimizationRemarkAnalysis; case DK_OptimizationRemarkAnalysisFPCommute: return LLVMRustDiagnosticKind::OptimizationRemarkAnalysisFPCommute; From 4c3699f01a3d1cb51e5cd1c0e913a3739adc4fc9 Mon Sep 17 00:00:00 2001 From: Josh Stone Date: Fri, 12 Nov 2021 08:17:57 -0800 Subject: [PATCH 5/5] Add 1.57.0 release notes --- RELEASES.md | 114 ++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 114 insertions(+) diff --git a/RELEASES.md b/RELEASES.md index a38ab7cabf468..4b9b20f4cba60 100644 --- a/RELEASES.md +++ b/RELEASES.md @@ -1,3 +1,117 @@ +Version 1.57.0 (2021-12-02) +========================== + +Language +-------- + +- [Macro attributes may follow `#[derive]` and will see the original (pre-`cfg`) input.][87220] +- [Accept curly-brace macros in expressions, like `m!{ .. }.method()` and `m!{ .. }?`.][88690] +- [Allow panicking in constant evaluation.][89508] + +Compiler +-------- + +- [Create more accurate debuginfo for vtables.][89597] +- [Add `armv6k-nintendo-3ds` at Tier 3\*.][88529] +- [Add `armv7-unknown-linux-uclibceabihf` at Tier 3\*.][88952] +- [Add `m68k-unknown-linux-gnu` at Tier 3\*.][88321] +- [Add SOLID targets at Tier 3\*:][86191] `aarch64-kmc-solid_asp3`, `armv7a-kmc-solid_asp3-eabi`, `armv7a-kmc-solid_asp3-eabihf` + +\* Refer to Rust's [platform support page][platform-support-doc] for more + information on Rust's tiered platform support. + +Libraries +--------- + +- [Avoid allocations and copying in `Vec::leak`][89337] +- [Add `#[repr(i8)]` to `Ordering`][89507] +- [Optimize `File::read_to_end` and `read_to_string`][89582] +- [Update to Unicode 14.0][89614] +- [Many more functions are marked `#[must_use]`][89692], producing a warning + when ignoring their return value. This helps catch mistakes such as expecting + a function to mutate a value in place rather than return a new value. + +Stabilised APIs +--------------- + +- [`[T; N]::as_mut_slice`][`array::as_mut_slice`] +- [`[T; N]::as_slice`][`array::as_slice`] +- [`collections::TryReserveError`] +- [`HashMap::try_reserve`] +- [`HashSet::try_reserve`] +- [`String::try_reserve`] +- [`String::try_reserve_exact`] +- [`Vec::try_reserve`] +- [`Vec::try_reserve_exact`] +- [`VecDeque::try_reserve`] +- [`VecDeque::try_reserve_exact`] +- [`Iterator::map_while`] +- [`iter::MapWhile`] +- [`proc_macro::is_available`] +- [`Command::get_program`] +- [`Command::get_args`] +- [`Command::get_envs`] +- [`Command::get_current_dir`] +- [`CommandArgs`] +- [`CommandEnvs`] + +These APIs are now usable in const contexts: + +- [`hint::unreachable_unchecked`] + +Cargo +----- + +- [Stabilize custom profiles][cargo/9943] + +Compatibility notes +------------------- + +Internal changes +---------------- +These changes provide no direct user facing benefits, but represent significant +improvements to the internals and overall performance of rustc +and related tools. + +- [Added an experimental backend for codegen with `libgccjit`.][87260] + +[86191]: https://github.com/rust-lang/rust/pull/86191/ +[87220]: https://github.com/rust-lang/rust/pull/87220/ +[87260]: https://github.com/rust-lang/rust/pull/87260/ +[88243]: https://github.com/rust-lang/rust/pull/88243/ +[88321]: https://github.com/rust-lang/rust/pull/88321/ +[88529]: https://github.com/rust-lang/rust/pull/88529/ +[88690]: https://github.com/rust-lang/rust/pull/88690/ +[88952]: https://github.com/rust-lang/rust/pull/88952/ +[89337]: https://github.com/rust-lang/rust/pull/89337/ +[89507]: https://github.com/rust-lang/rust/pull/89507/ +[89508]: https://github.com/rust-lang/rust/pull/89508/ +[89582]: https://github.com/rust-lang/rust/pull/89582/ +[89597]: https://github.com/rust-lang/rust/pull/89597/ +[89614]: https://github.com/rust-lang/rust/pull/89614/ +[89692]: https://github.com/rust-lang/rust/issues/89692/ +[cargo/9943]: https://github.com/rust-lang/cargo/pull/9943/ +[`array::as_mut_slice`]: https://doc.rust-lang.org/std/primitive.array.html#method.as_mut_slice +[`array::as_slice`]: https://doc.rust-lang.org/std/primitive.array.html#method.as_slice +[`collections::TryReserveError`]: https://doc.rust-lang.org/std/collections/struct.TryReserveError.html +[`HashMap::try_reserve`]: https://doc.rust-lang.org/std/collections/hash_map/struct.HashMap.html#method.try_reserve +[`HashSet::try_reserve`]: https://doc.rust-lang.org/std/collections/hash_set/struct.HashSet.html#method.try_reserve +[`String::try_reserve`]: https://doc.rust-lang.org/alloc/string/struct.String.html#method.try_reserve +[`String::try_reserve_exact`]: https://doc.rust-lang.org/alloc/string/struct.String.html#method.try_reserve_exact +[`Vec::try_reserve`]: https://doc.rust-lang.org/std/vec/struct.Vec.html#method.try_reserve +[`Vec::try_reserve_exact`]: https://doc.rust-lang.org/std/vec/struct.Vec.html#method.try_reserve_exact +[`VecDeque::try_reserve`]: https://doc.rust-lang.org/std/collections/struct.VecDeque.html#method.try_reserve +[`VecDeque::try_reserve_exact`]: https://doc.rust-lang.org/std/collections/struct.VecDeque.html#method.try_reserve_exact +[`Iterator::map_while`]: https://doc.rust-lang.org/std/iter/trait.Iterator.html#method.map_while +[`iter::MapWhile`]: https://doc.rust-lang.org/std/iter/struct.MapWhile.html +[`proc_macro::is_available`]: https://doc.rust-lang.org/proc_macro/fn.is_available.html +[`Command::get_program`]: https://doc.rust-lang.org/std/process/struct.Command.html#method.get_program +[`Command::get_args`]: https://doc.rust-lang.org/std/process/struct.Command.html#method.get_args +[`Command::get_envs`]: https://doc.rust-lang.org/std/process/struct.Command.html#method.get_envs +[`Command::get_current_dir`]: https://doc.rust-lang.org/std/process/struct.Command.html#method.get_current_dir +[`CommandArgs`]: https://doc.rust-lang.org/std/process/struct.CommandArgs.html +[`CommandEnvs`]: https://doc.rust-lang.org/std/process/struct.CommandEnvs.html + Version 1.56.1 (2021-11-01) ===========================