Skip to content

Commit 39323a5

Browse files
committed
Auto merge of #102586 - Dylan-DPC:rollup-g107h6z, r=Dylan-DPC
Rollup of 5 pull requests Successful merges: - #100451 (Do not panic when a test function returns Result::Err.) - #102098 (Use fetch_update in sync::Weak::upgrade) - #102538 (Give `def_span` the same SyntaxContext as `span_with_body`.) - #102556 (Make `feature(const_btree_len)` implied by `feature(const_btree_new)`) - #102566 (Add a known-bug test for #102498) Failed merges: r? `@ghost` `@rustbot` modify labels: rollup
2 parents 91931ec + 0b25967 commit 39323a5

File tree

14 files changed

+239
-94
lines changed

14 files changed

+239
-94
lines changed

compiler/rustc_middle/src/hir/map/mod.rs

+26-6
Original file line numberDiff line numberDiff line change
@@ -941,9 +941,19 @@ impl<'hir> Map<'hir> {
941941

942942
let span = match self.find(hir_id)? {
943943
// Function-like.
944-
Node::Item(Item { kind: ItemKind::Fn(sig, ..), .. })
945-
| Node::TraitItem(TraitItem { kind: TraitItemKind::Fn(sig, ..), .. })
946-
| Node::ImplItem(ImplItem { kind: ImplItemKind::Fn(sig, ..), .. }) => sig.span,
944+
Node::Item(Item { kind: ItemKind::Fn(sig, ..), span: outer_span, .. })
945+
| Node::TraitItem(TraitItem {
946+
kind: TraitItemKind::Fn(sig, ..),
947+
span: outer_span,
948+
..
949+
})
950+
| Node::ImplItem(ImplItem {
951+
kind: ImplItemKind::Fn(sig, ..), span: outer_span, ..
952+
}) => {
953+
// Ensure that the returned span has the item's SyntaxContext, and not the
954+
// SyntaxContext of the visibility.
955+
sig.span.find_ancestor_in_same_ctxt(*outer_span).unwrap_or(*outer_span)
956+
}
947957
// Constants and Statics.
948958
Node::Item(Item {
949959
kind:
@@ -985,7 +995,11 @@ impl<'hir> Map<'hir> {
985995
}
986996
// Other cases.
987997
Node::Item(item) => match &item.kind {
988-
ItemKind::Use(path, _) => path.span,
998+
ItemKind::Use(path, _) => {
999+
// Ensure that the returned span has the item's SyntaxContext, and not the
1000+
// SyntaxContext of the path.
1001+
path.span.find_ancestor_in_same_ctxt(item.span).unwrap_or(item.span)
1002+
}
9891003
_ => named_span(item.span, item.ident, item.kind.generics()),
9901004
},
9911005
Node::Variant(variant) => named_span(variant.span, variant.ident, None),
@@ -995,11 +1009,17 @@ impl<'hir> Map<'hir> {
9951009
_ => named_span(item.span, item.ident, None),
9961010
},
9971011
Node::Ctor(_) => return self.opt_span(self.get_parent_node(hir_id)),
998-
Node::Expr(Expr { kind: ExprKind::Closure(Closure { fn_decl_span, .. }), .. }) => {
999-
*fn_decl_span
1012+
Node::Expr(Expr {
1013+
kind: ExprKind::Closure(Closure { fn_decl_span, .. }),
1014+
span,
1015+
..
1016+
}) => {
1017+
// Ensure that the returned span has the item's SyntaxContext.
1018+
fn_decl_span.find_ancestor_in_same_ctxt(*span).unwrap_or(*span)
10001019
}
10011020
_ => self.span_with_body(hir_id),
10021021
};
1022+
debug_assert_eq!(span.ctxt(), self.span_with_body(hir_id).ctxt());
10031023
Some(span)
10041024
}
10051025

library/alloc/src/collections/btree/map.rs

+10-2
Original file line numberDiff line numberDiff line change
@@ -2392,7 +2392,11 @@ impl<K, V, A: Allocator + Clone> BTreeMap<K, V, A> {
23922392
/// ```
23932393
#[must_use]
23942394
#[stable(feature = "rust1", since = "1.0.0")]
2395-
#[rustc_const_unstable(feature = "const_btree_len", issue = "71835")]
2395+
#[rustc_const_unstable(
2396+
feature = "const_btree_len",
2397+
issue = "71835",
2398+
implied_by = "const_btree_new"
2399+
)]
23962400
pub const fn len(&self) -> usize {
23972401
self.length
23982402
}
@@ -2413,7 +2417,11 @@ impl<K, V, A: Allocator + Clone> BTreeMap<K, V, A> {
24132417
/// ```
24142418
#[must_use]
24152419
#[stable(feature = "rust1", since = "1.0.0")]
2416-
#[rustc_const_unstable(feature = "const_btree_len", issue = "71835")]
2420+
#[rustc_const_unstable(
2421+
feature = "const_btree_len",
2422+
issue = "71835",
2423+
implied_by = "const_btree_new"
2424+
)]
24172425
pub const fn is_empty(&self) -> bool {
24182426
self.len() == 0
24192427
}

library/alloc/src/collections/btree/set.rs

+10-2
Original file line numberDiff line numberDiff line change
@@ -1174,7 +1174,11 @@ impl<T, A: Allocator + Clone> BTreeSet<T, A> {
11741174
/// ```
11751175
#[must_use]
11761176
#[stable(feature = "rust1", since = "1.0.0")]
1177-
#[rustc_const_unstable(feature = "const_btree_len", issue = "71835")]
1177+
#[rustc_const_unstable(
1178+
feature = "const_btree_len",
1179+
issue = "71835",
1180+
implied_by = "const_btree_new"
1181+
)]
11781182
pub const fn len(&self) -> usize {
11791183
self.map.len()
11801184
}
@@ -1193,7 +1197,11 @@ impl<T, A: Allocator + Clone> BTreeSet<T, A> {
11931197
/// ```
11941198
#[must_use]
11951199
#[stable(feature = "rust1", since = "1.0.0")]
1196-
#[rustc_const_unstable(feature = "const_btree_len", issue = "71835")]
1200+
#[rustc_const_unstable(
1201+
feature = "const_btree_len",
1202+
issue = "71835",
1203+
implied_by = "const_btree_new"
1204+
)]
11971205
pub const fn is_empty(&self) -> bool {
11981206
self.len() == 0
11991207
}

library/alloc/src/sync.rs

+16-23
Original file line numberDiff line numberDiff line change
@@ -1980,33 +1980,26 @@ impl<T: ?Sized> Weak<T> {
19801980
// We use a CAS loop to increment the strong count instead of a
19811981
// fetch_add as this function should never take the reference count
19821982
// from zero to one.
1983-
let inner = self.inner()?;
1984-
1985-
// Relaxed load because any write of 0 that we can observe
1986-
// leaves the field in a permanently zero state (so a
1987-
// "stale" read of 0 is fine), and any other value is
1988-
// confirmed via the CAS below.
1989-
let mut n = inner.strong.load(Relaxed);
1990-
1991-
loop {
1992-
if n == 0 {
1993-
return None;
1994-
}
1995-
1996-
// See comments in `Arc::clone` for why we do this (for `mem::forget`).
1997-
if n > MAX_REFCOUNT {
1998-
abort();
1999-
}
2000-
1983+
self.inner()?
1984+
.strong
20011985
// Relaxed is fine for the failure case because we don't have any expectations about the new state.
20021986
// Acquire is necessary for the success case to synchronise with `Arc::new_cyclic`, when the inner
20031987
// value can be initialized after `Weak` references have already been created. In that case, we
20041988
// expect to observe the fully initialized value.
2005-
match inner.strong.compare_exchange_weak(n, n + 1, Acquire, Relaxed) {
2006-
Ok(_) => return Some(unsafe { Arc::from_inner(self.ptr) }), // null checked above
2007-
Err(old) => n = old,
2008-
}
2009-
}
1989+
.fetch_update(Acquire, Relaxed, |n| {
1990+
// Any write of 0 we can observe leaves the field in permanently zero state.
1991+
if n == 0 {
1992+
return None;
1993+
}
1994+
// See comments in `Arc::clone` for why we do this (for `mem::forget`).
1995+
if n > MAX_REFCOUNT {
1996+
abort();
1997+
}
1998+
Some(n + 1)
1999+
})
2000+
.ok()
2001+
// null checked above
2002+
.map(|_| unsafe { Arc::from_inner(self.ptr) })
20102003
}
20112004

20122005
/// Gets the number of strong (`Arc`) pointers pointing to this allocation.

library/test/src/bench.rs

+11-10
Original file line numberDiff line numberDiff line change
@@ -49,12 +49,12 @@ impl Bencher {
4949
self.summary = Some(iter(&mut inner));
5050
}
5151

52-
pub fn bench<F>(&mut self, mut f: F) -> Option<stats::Summary>
52+
pub fn bench<F>(&mut self, mut f: F) -> Result<Option<stats::Summary>, String>
5353
where
54-
F: FnMut(&mut Bencher),
54+
F: FnMut(&mut Bencher) -> Result<(), String>,
5555
{
56-
f(self);
57-
self.summary
56+
let result = f(self);
57+
result.map(|_| self.summary)
5858
}
5959
}
6060

@@ -195,7 +195,7 @@ pub fn benchmark<F>(
195195
nocapture: bool,
196196
f: F,
197197
) where
198-
F: FnMut(&mut Bencher),
198+
F: FnMut(&mut Bencher) -> Result<(), String>,
199199
{
200200
let mut bs = Bencher { mode: BenchMode::Auto, summary: None, bytes: 0 };
201201

@@ -211,32 +211,33 @@ pub fn benchmark<F>(
211211

212212
let test_result = match result {
213213
//bs.bench(f) {
214-
Ok(Some(ns_iter_summ)) => {
214+
Ok(Ok(Some(ns_iter_summ))) => {
215215
let ns_iter = cmp::max(ns_iter_summ.median as u64, 1);
216216
let mb_s = bs.bytes * 1000 / ns_iter;
217217

218218
let bs = BenchSamples { ns_iter_summ, mb_s: mb_s as usize };
219219
TestResult::TrBench(bs)
220220
}
221-
Ok(None) => {
221+
Ok(Ok(None)) => {
222222
// iter not called, so no data.
223223
// FIXME: error in this case?
224224
let samples: &mut [f64] = &mut [0.0_f64; 1];
225225
let bs = BenchSamples { ns_iter_summ: stats::Summary::new(samples), mb_s: 0 };
226226
TestResult::TrBench(bs)
227227
}
228228
Err(_) => TestResult::TrFailed,
229+
Ok(Err(_)) => TestResult::TrFailed,
229230
};
230231

231232
let stdout = data.lock().unwrap().to_vec();
232233
let message = CompletedTest::new(id, desc, test_result, None, stdout);
233234
monitor_ch.send(message).unwrap();
234235
}
235236

236-
pub fn run_once<F>(f: F)
237+
pub fn run_once<F>(f: F) -> Result<(), String>
237238
where
238-
F: FnMut(&mut Bencher),
239+
F: FnMut(&mut Bencher) -> Result<(), String>,
239240
{
240241
let mut bs = Bencher { mode: BenchMode::Single, summary: None, bytes: 0 };
241-
bs.bench(f);
242+
bs.bench(f).map(|_| ())
242243
}

library/test/src/lib.rs

+42-19
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,8 @@
66
//! benchmarks themselves) should be done via the `#[test]` and
77
//! `#[bench]` attributes.
88
//!
9-
//! See the [Testing Chapter](../book/ch11-00-testing.html) of the book for more details.
9+
//! See the [Testing Chapter](../book/ch11-00-testing.html) of the book for more
10+
//! details.
1011
1112
// Currently, not much of this is meant for users. It is intended to
1213
// support the simplest interface possible for representing and
@@ -76,6 +77,7 @@ mod types;
7677
#[cfg(test)]
7778
mod tests;
7879

80+
use core::any::Any;
7981
use event::{CompletedTest, TestEvent};
8082
use helpers::concurrency::get_concurrency;
8183
use helpers::exit_code::get_exit_code;
@@ -175,17 +177,20 @@ fn make_owned_test(test: &&TestDescAndFn) -> TestDescAndFn {
175177
}
176178
}
177179

178-
/// Invoked when unit tests terminate. Should panic if the unit
179-
/// Tests is considered a failure. By default, invokes `report()`
180-
/// and checks for a `0` result.
181-
pub fn assert_test_result<T: Termination>(result: T) {
180+
/// Invoked when unit tests terminate. Returns `Result::Err` if the test is
181+
/// considered a failure. By default, invokes `report() and checks for a `0`
182+
/// result.
183+
pub fn assert_test_result<T: Termination>(result: T) -> Result<(), String> {
182184
let code = result.report().to_i32();
183-
assert_eq!(
184-
code, 0,
185-
"the test returned a termination value with a non-zero status code ({}) \
186-
which indicates a failure",
187-
code
188-
);
185+
if code == 0 {
186+
Ok(())
187+
} else {
188+
Err(format!(
189+
"the test returned a termination value with a non-zero status code \
190+
({}) which indicates a failure",
191+
code
192+
))
193+
}
189194
}
190195

191196
pub fn run_tests<F>(
@@ -478,7 +483,7 @@ pub fn run_test(
478483
id: TestId,
479484
desc: TestDesc,
480485
monitor_ch: Sender<CompletedTest>,
481-
testfn: Box<dyn FnOnce() + Send>,
486+
testfn: Box<dyn FnOnce() -> Result<(), String> + Send>,
482487
opts: TestRunOpts,
483488
) -> Option<thread::JoinHandle<()>> {
484489
let concurrency = opts.concurrency;
@@ -567,19 +572,19 @@ pub fn run_test(
567572

568573
/// Fixed frame used to clean the backtrace with `RUST_BACKTRACE=1`.
569574
#[inline(never)]
570-
fn __rust_begin_short_backtrace<F: FnOnce()>(f: F) {
571-
f();
575+
fn __rust_begin_short_backtrace<T, F: FnOnce() -> T>(f: F) -> T {
576+
let result = f();
572577

573578
// prevent this frame from being tail-call optimised away
574-
black_box(());
579+
black_box(result)
575580
}
576581

577582
fn run_test_in_process(
578583
id: TestId,
579584
desc: TestDesc,
580585
nocapture: bool,
581586
report_time: bool,
582-
testfn: Box<dyn FnOnce() + Send>,
587+
testfn: Box<dyn FnOnce() -> Result<(), String> + Send>,
583588
monitor_ch: Sender<CompletedTest>,
584589
time_opts: Option<time::TestTimeOptions>,
585590
) {
@@ -591,7 +596,7 @@ fn run_test_in_process(
591596
}
592597

593598
let start = report_time.then(Instant::now);
594-
let result = catch_unwind(AssertUnwindSafe(testfn));
599+
let result = fold_err(catch_unwind(AssertUnwindSafe(testfn)));
595600
let exec_time = start.map(|start| {
596601
let duration = start.elapsed();
597602
TestExecTime(duration)
@@ -608,6 +613,19 @@ fn run_test_in_process(
608613
monitor_ch.send(message).unwrap();
609614
}
610615

616+
fn fold_err<T, E>(
617+
result: Result<Result<T, E>, Box<dyn Any + Send>>,
618+
) -> Result<T, Box<dyn Any + Send>>
619+
where
620+
E: Send + 'static,
621+
{
622+
match result {
623+
Ok(Err(e)) => Err(Box::new(e)),
624+
Ok(Ok(v)) => Ok(v),
625+
Err(e) => Err(e),
626+
}
627+
}
628+
611629
fn spawn_test_subprocess(
612630
id: TestId,
613631
desc: TestDesc,
@@ -663,7 +681,10 @@ fn spawn_test_subprocess(
663681
monitor_ch.send(message).unwrap();
664682
}
665683

666-
fn run_test_in_spawned_subprocess(desc: TestDesc, testfn: Box<dyn FnOnce() + Send>) -> ! {
684+
fn run_test_in_spawned_subprocess(
685+
desc: TestDesc,
686+
testfn: Box<dyn FnOnce() -> Result<(), String> + Send>,
687+
) -> ! {
667688
let builtin_panic_hook = panic::take_hook();
668689
let record_result = Arc::new(move |panic_info: Option<&'_ PanicInfo<'_>>| {
669690
let test_result = match panic_info {
@@ -689,7 +710,9 @@ fn run_test_in_spawned_subprocess(desc: TestDesc, testfn: Box<dyn FnOnce() + Sen
689710
});
690711
let record_result2 = record_result.clone();
691712
panic::set_hook(Box::new(move |info| record_result2(Some(&info))));
692-
testfn();
713+
if let Err(message) = testfn() {
714+
panic!("{}", message);
715+
}
693716
record_result(None);
694717
unreachable!("panic=abort callback should have exited the process")
695718
}

0 commit comments

Comments
 (0)