Skip to content
Merged
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
24 changes: 12 additions & 12 deletions library/core/src/panic.rs
Original file line number Diff line number Diff line change
Expand Up @@ -28,13 +28,13 @@ pub macro panic_2015 {
$crate::panicking::panic($msg)
),
// Use `panic_str` instead of `panic_display::<&str>` for non_fmt_panic lint.
($msg:expr $(,)?) => (
$crate::panicking::panic_str($msg)
),
($msg:expr $(,)?) => ({
$crate::panicking::panic_str($msg);
}),
// Special-case the single-argument case for const_panic.
("{}", $arg:expr $(,)?) => (
$crate::panicking::panic_display(&$arg)
),
("{}", $arg:expr $(,)?) => ({
$crate::panicking::panic_display(&$arg);
}),
($fmt:expr, $($arg:tt)+) => ({
// Semicolon to prevent temporaries inside the formatting machinery from
// being considered alive in the caller after the panic_fmt call.
Expand All @@ -52,9 +52,9 @@ pub macro panic_2021 {
$crate::panicking::panic("explicit panic")
),
// Special-case the single-argument case for const_panic.
("{}", $arg:expr $(,)?) => (
$crate::panicking::panic_display(&$arg)
),
("{}", $arg:expr $(,)?) => ({
$crate::panicking::panic_display(&$arg);
}),
($($t:tt)+) => ({
// Semicolon to prevent temporaries inside the formatting machinery from
// being considered alive in the caller after the panic_fmt call.
Expand All @@ -73,9 +73,9 @@ pub macro unreachable_2015 {
),
// Use of `unreachable_display` for non_fmt_panic lint.
// NOTE: the message ("internal error ...") is embedded directly in unreachable_display
($msg:expr $(,)?) => (
$crate::panicking::unreachable_display(&$msg)
),
($msg:expr $(,)?) => ({
$crate::panicking::unreachable_display(&$msg);
}),
($fmt:expr, $($arg:tt)*) => (
$crate::panic!($crate::concat!("internal error: entered unreachable code: ", $fmt), $($arg)*)
),
Expand Down
4 changes: 2 additions & 2 deletions library/std/src/panic.rs
Original file line number Diff line number Diff line change
Expand Up @@ -19,11 +19,11 @@ pub macro panic_2015 {
$crate::rt::begin_panic("explicit panic")
}),
($msg:expr $(,)?) => ({
$crate::rt::begin_panic($msg)
$crate::rt::begin_panic($msg);
}),
// Special-case the single-argument case for const_panic.
("{}", $arg:expr $(,)?) => ({
$crate::rt::panic_display(&$arg)
$crate::rt::panic_display(&$arg);
}),
($fmt:expr, $($arg:tt)+) => ({
// Semicolon to prevent temporaries inside the formatting machinery from
Expand Down
55 changes: 55 additions & 0 deletions tests/ui/macros/panic-temporaries-2018.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
// check-pass
// edition:2018

#![allow(non_fmt_panics, unreachable_code)]

use std::fmt::{self, Display};
use std::marker::PhantomData;

struct NotSend {
marker: PhantomData<*const u8>,
}

const NOT_SEND: NotSend = NotSend { marker: PhantomData };

impl Display for NotSend {
fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
formatter.write_str("this value does not implement Send")
}
}

async fn f(_: u8) {}

// Exercises this matcher in panic_2015:
// ($fmt:expr, $($arg:tt)+) => $crate::panicking::panic_fmt(...)
async fn panic_fmt() {
// Panic returns `!`, so the await is never reached, and in particular the
// temporaries inside the formatting machinery are not still alive at the
// await point.
let todo = "...";
f(panic!("not yet implemented: {}", todo)).await;
}

// Exercises ("{}", $arg:expr) => $crate::panicking::panic_display(&$arg)
async fn panic_display() {
f(panic!("{}", NOT_SEND)).await;
}

// Exercises ($msg:expr) => $crate::panicking::panic_str($msg)
async fn panic_str() {
f(panic!((NOT_SEND, "...").1)).await;
}

// Exercises ($msg:expr) => $crate::panicking::unreachable_display(&$msg)
async fn unreachable_display() {
f(unreachable!(NOT_SEND)).await;
}

fn require_send(_: impl Send) {}

fn main() {
require_send(panic_fmt());
require_send(panic_display());
require_send(panic_str());
require_send(unreachable_display());
}
32 changes: 28 additions & 4 deletions tests/ui/macros/panic-temporaries.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,17 +3,41 @@

#![allow(unreachable_code)]

use std::fmt::{self, Display};
use std::marker::PhantomData;

struct NotSend {
marker: PhantomData<*const u8>,
}

const NOT_SEND: NotSend = NotSend { marker: PhantomData };

impl Display for NotSend {
fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
formatter.write_str("this value does not implement Send")
}
}

async fn f(_: u8) {}

async fn g() {
// Todo returns `!`, so the await is never reached, and in particular the
// Exercises this matcher in panic_2021:
// ($($t:tt)+) => $crate::panicking::panic_fmt(...)
async fn panic_fmt() {
// Panic returns `!`, so the await is never reached, and in particular the
// temporaries inside the formatting machinery are not still alive at the
// await point.
f(todo!("...")).await;
let todo = "...";
f(panic!("not yet implemented: {}", todo)).await;
}

// Exercises ("{}", $arg:expr) => $crate::panicking::panic_display(&$arg)
async fn panic_display() {
f(panic!("{}", NOT_SEND)).await;
}

fn require_send(_: impl Send) {}

fn main() {
require_send(g());
require_send(panic_fmt());
require_send(panic_display());
}