Skip to content

Commit 7942405

Browse files
committed
Auto merge of #123869 - matthiaskrgr:rollup-9kif9c9, r=matthiaskrgr
Rollup of 7 pull requests Successful merges: - #123654 (typeck: fix `?` suggestion span) - #123807 (Remove `sys_common::thread`) - #123834 (Don't do coroutine-closure-specific upvar analysis if tainted by errors) - #123847 (Suppress `let else` suggestion for uninitialized refutable `let`s) - #123857 (std::net: TcpListener shrinks the backlog argument to 32 for Haiku.) - #123858 (zkvm: fix path to cmath in zkvm module) - #123867 (Add `unsafe` to two functions with safety invariants) r? `@ghost` `@rustbot` modify labels: rollup
2 parents 22a2425 + 3026204 commit 7942405

23 files changed

+230
-145
lines changed

Diff for: compiler/rustc_hir_typeck/src/fn_ctxt/suggestions.rs

+3-12
Original file line numberDiff line numberDiff line change
@@ -1287,12 +1287,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
12871287
ty::TraitRef::new(self.tcx, into_def_id, [expr_ty, expected_ty]),
12881288
))
12891289
{
1290-
let mut span = expr.span;
1291-
while expr.span.eq_ctxt(span)
1292-
&& let Some(parent_callsite) = span.parent_callsite()
1293-
{
1294-
span = parent_callsite;
1295-
}
1290+
let span = expr.span.find_oldest_ancestor_in_same_ctxt();
12961291

12971292
let mut sugg = if expr.precedence().order() >= PREC_POSTFIX {
12981293
vec![(span.shrink_to_hi(), ".into()".to_owned())]
@@ -1897,12 +1892,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
18971892
None => sugg.to_string(),
18981893
};
18991894

1900-
err.span_suggestion_verbose(
1901-
expr.span.shrink_to_hi(),
1902-
msg,
1903-
sugg,
1904-
Applicability::HasPlaceholders,
1905-
);
1895+
let span = expr.span.find_oldest_ancestor_in_same_ctxt();
1896+
err.span_suggestion_verbose(span.shrink_to_hi(), msg, sugg, Applicability::HasPlaceholders);
19061897
return true;
19071898
}
19081899

Diff for: compiler/rustc_hir_typeck/src/upvar.rs

+6-2
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,8 @@ use rustc_middle::hir::place::{Place, PlaceBase, PlaceWithHirId, Projection, Pro
4343
use rustc_middle::mir::FakeReadCause;
4444
use rustc_middle::traits::ObligationCauseCode;
4545
use rustc_middle::ty::{
46-
self, ClosureSizeProfileData, Ty, TyCtxt, TypeckResults, UpvarArgs, UpvarCapture,
46+
self, ClosureSizeProfileData, Ty, TyCtxt, TypeVisitableExt as _, TypeckResults, UpvarArgs,
47+
UpvarCapture,
4748
};
4849
use rustc_session::lint;
4950
use rustc_span::sym;
@@ -191,6 +192,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
191192
);
192193
}
193194
};
195+
let args = self.resolve_vars_if_possible(args);
194196
let closure_def_id = closure_def_id.expect_local();
195197

196198
assert_eq!(self.tcx.hir().body_owner_def_id(body.id()), closure_def_id);
@@ -361,7 +363,9 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
361363
// For coroutine-closures, we additionally must compute the
362364
// `coroutine_captures_by_ref_ty` type, which is used to generate the by-ref
363365
// version of the coroutine-closure's output coroutine.
364-
if let UpvarArgs::CoroutineClosure(args) = args {
366+
if let UpvarArgs::CoroutineClosure(args) = args
367+
&& !args.references_error()
368+
{
365369
let closure_env_region: ty::Region<'_> = ty::Region::new_bound(
366370
self.tcx,
367371
ty::INNERMOST,

Diff for: compiler/rustc_middle/src/ty/sty.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -771,7 +771,7 @@ impl<'tcx> CoroutineArgs<'tcx> {
771771
}
772772
}
773773

774-
#[derive(Debug, Copy, Clone, HashStable)]
774+
#[derive(Debug, Copy, Clone, HashStable, TypeFoldable, TypeVisitable)]
775775
pub enum UpvarArgs<'tcx> {
776776
Closure(GenericArgsRef<'tcx>),
777777
Coroutine(GenericArgsRef<'tcx>),

Diff for: compiler/rustc_mir_build/src/thir/pattern/check_match.rs

+1
Original file line numberDiff line numberDiff line change
@@ -674,6 +674,7 @@ impl<'p, 'tcx> MatchVisitor<'p, 'tcx> {
674674
if let Some(span) = sp
675675
&& self.tcx.sess.source_map().is_span_accessible(span)
676676
&& interpreted_as_const.is_none()
677+
&& scrut.is_some()
677678
{
678679
let mut bindings = vec![];
679680
pat.each_binding(|name, _, _, _| bindings.push(name));

Diff for: compiler/rustc_span/src/lib.rs

+39
Original file line numberDiff line numberDiff line change
@@ -743,6 +743,45 @@ impl Span {
743743
Some(self)
744744
}
745745

746+
/// Recursively walk down the expansion ancestors to find the oldest ancestor span with the same
747+
/// [`SyntaxContext`] the initial span.
748+
///
749+
/// This method is suitable for peeling through *local* macro expansions to find the "innermost"
750+
/// span that is still local and shares the same [`SyntaxContext`]. For example, given
751+
///
752+
/// ```ignore (illustrative example, contains type error)
753+
/// macro_rules! outer {
754+
/// ($x: expr) => {
755+
/// inner!($x)
756+
/// }
757+
/// }
758+
///
759+
/// macro_rules! inner {
760+
/// ($x: expr) => {
761+
/// format!("error: {}", $x)
762+
/// //~^ ERROR mismatched types
763+
/// }
764+
/// }
765+
///
766+
/// fn bar(x: &str) -> Result<(), Box<dyn std::error::Error>> {
767+
/// Err(outer!(x))
768+
/// }
769+
/// ```
770+
///
771+
/// if provided the initial span of `outer!(x)` inside `bar`, this method will recurse
772+
/// the parent callsites until we reach `format!("error: {}", $x)`, at which point it is the
773+
/// oldest ancestor span that is both still local and shares the same [`SyntaxContext`] as the
774+
/// initial span.
775+
pub fn find_oldest_ancestor_in_same_ctxt(self) -> Span {
776+
let mut cur = self;
777+
while cur.eq_ctxt(self)
778+
&& let Some(parent_callsite) = cur.parent_callsite()
779+
{
780+
cur = parent_callsite;
781+
}
782+
cur
783+
}
784+
746785
/// Edition of the crate from which this span came.
747786
pub fn edition(self) -> edition::Edition {
748787
self.ctxt().edition()

Diff for: library/std/src/sys/pal/windows/thread.rs

+14-12
Original file line numberDiff line numberDiff line change
@@ -45,29 +45,31 @@ impl Thread {
4545
Err(io::Error::last_os_error())
4646
};
4747

48-
extern "system" fn thread_start(main: *mut c_void) -> c::DWORD {
49-
unsafe {
50-
// Next, reserve some stack space for if we otherwise run out of stack.
51-
stack_overflow::reserve_stack();
52-
// Finally, let's run some code.
53-
Box::from_raw(main as *mut Box<dyn FnOnce()>)();
54-
}
48+
unsafe extern "system" fn thread_start(main: *mut c_void) -> c::DWORD {
49+
// Next, reserve some stack space for if we otherwise run out of stack.
50+
stack_overflow::reserve_stack();
51+
// Finally, let's run some code.
52+
Box::from_raw(main as *mut Box<dyn FnOnce()>)();
5553
0
5654
}
5755
}
5856

5957
pub fn set_name(name: &CStr) {
6058
if let Ok(utf8) = name.to_str() {
6159
if let Ok(utf16) = to_u16s(utf8) {
62-
Self::set_name_wide(&utf16)
60+
unsafe {
61+
// SAFETY: the vec returned by `to_u16s` ends with a zero value
62+
Self::set_name_wide(&utf16)
63+
}
6364
};
6465
};
6566
}
6667

67-
pub fn set_name_wide(name: &[u16]) {
68-
unsafe {
69-
c::SetThreadDescription(c::GetCurrentThread(), name.as_ptr());
70-
};
68+
/// # Safety
69+
///
70+
/// `name` must end with a zero value
71+
pub unsafe fn set_name_wide(name: &[u16]) {
72+
c::SetThreadDescription(c::GetCurrentThread(), name.as_ptr());
7173
}
7274

7375
pub fn join(self) {

Diff for: library/std/src/sys/pal/zkvm/mod.rs

-2
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,6 @@ const WORD_SIZE: usize = core::mem::size_of::<u32>();
1212
pub mod alloc;
1313
#[path = "../zkvm/args.rs"]
1414
pub mod args;
15-
#[path = "../unix/cmath.rs"]
16-
pub mod cmath;
1715
pub mod env;
1816
#[path = "../unsupported/fs.rs"]
1917
pub mod fs;

Diff for: library/std/src/sys_common/mod.rs

-1
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,6 @@ pub mod fs;
2525
pub mod io;
2626
pub mod lazy_box;
2727
pub mod process;
28-
pub mod thread;
2928
pub mod thread_local_dtor;
3029
pub mod thread_parking;
3130
pub mod wstr;

Diff for: library/std/src/sys_common/net.rs

+4
Original file line numberDiff line numberDiff line change
@@ -417,6 +417,10 @@ impl TcpListener {
417417
// it allows up to about 37, but other times it doesn't even
418418
// accept 32. There may be a global limitation causing this.
419419
let backlog = 20;
420+
} else if #[cfg(target_os = "haiku")] {
421+
// Haiku does not support a queue length > 32
422+
// https://github.com/haiku/haiku/blob/979a0bc487864675517fb2fab28f87dc8bf43041/headers/posix/sys/socket.h#L81
423+
let backlog = 32;
420424
} else {
421425
// The default for all other platforms
422426
let backlog = 128;

Diff for: library/std/src/sys_common/thread.rs

-18
This file was deleted.

Diff for: library/std/src/thread/mod.rs

+22-5
Original file line numberDiff line numberDiff line change
@@ -160,6 +160,7 @@ mod tests;
160160

161161
use crate::any::Any;
162162
use crate::cell::{OnceCell, UnsafeCell};
163+
use crate::env;
163164
use crate::ffi::{CStr, CString};
164165
use crate::fmt;
165166
use crate::io;
@@ -171,9 +172,9 @@ use crate::panicking;
171172
use crate::pin::Pin;
172173
use crate::ptr::addr_of_mut;
173174
use crate::str;
175+
use crate::sync::atomic::{AtomicUsize, Ordering};
174176
use crate::sync::Arc;
175177
use crate::sys::thread as imp;
176-
use crate::sys_common::thread;
177178
use crate::sys_common::thread_parking::Parker;
178179
use crate::sys_common::{AsInner, IntoInner};
179180
use crate::time::{Duration, Instant};
@@ -468,7 +469,23 @@ impl Builder {
468469
{
469470
let Builder { name, stack_size } = self;
470471

471-
let stack_size = stack_size.unwrap_or_else(thread::min_stack);
472+
let stack_size = stack_size.unwrap_or_else(|| {
473+
static MIN: AtomicUsize = AtomicUsize::new(0);
474+
475+
match MIN.load(Ordering::Relaxed) {
476+
0 => {}
477+
n => return n - 1,
478+
}
479+
480+
let amt = env::var_os("RUST_MIN_STACK")
481+
.and_then(|s| s.to_str().and_then(|s| s.parse().ok()))
482+
.unwrap_or(imp::DEFAULT_MIN_STACK_SIZE);
483+
484+
// 0 is our sentinel value, so ensure that we'll never see 0 after
485+
// initialization has run
486+
MIN.store(amt + 1, Ordering::Relaxed);
487+
amt
488+
});
472489

473490
let my_thread = Thread::new(name.map(|name| {
474491
CString::new(name).expect("thread name may not contain interior null bytes")
@@ -1191,17 +1208,17 @@ impl ThreadId {
11911208

11921209
cfg_if::cfg_if! {
11931210
if #[cfg(target_has_atomic = "64")] {
1194-
use crate::sync::atomic::{AtomicU64, Ordering::Relaxed};
1211+
use crate::sync::atomic::AtomicU64;
11951212

11961213
static COUNTER: AtomicU64 = AtomicU64::new(0);
11971214

1198-
let mut last = COUNTER.load(Relaxed);
1215+
let mut last = COUNTER.load(Ordering::Relaxed);
11991216
loop {
12001217
let Some(id) = last.checked_add(1) else {
12011218
exhausted();
12021219
};
12031220

1204-
match COUNTER.compare_exchange_weak(last, id, Relaxed, Relaxed) {
1221+
match COUNTER.compare_exchange_weak(last, id, Ordering::Relaxed, Ordering::Relaxed) {
12051222
Ok(_) => return ThreadId(NonZero::new(id).unwrap()),
12061223
Err(id) => last = id,
12071224
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
//@ edition: 2021
2+
3+
#![feature(async_closure)]
4+
5+
struct DropMe;
6+
7+
trait Impossible {}
8+
fn trait_error<T: Impossible>() {}
9+
10+
pub fn main() {
11+
let b = DropMe;
12+
let async_closure = async move || {
13+
// Type error here taints the environment. This causes us to fallback all
14+
// variables to `Error`. This means that when we compute the upvars for the
15+
// *outer* coroutine-closure, we don't actually see any upvars since `MemCategorization`
16+
// and `ExprUseVisitor`` will bail early when it sees error. This means
17+
// that our underlying assumption that the parent and child captures are
18+
// compatible ends up being broken, previously leading to an ICE.
19+
trait_error::<()>();
20+
//~^ ERROR the trait bound `(): Impossible` is not satisfied
21+
let _b = b;
22+
};
23+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
error[E0277]: the trait bound `(): Impossible` is not satisfied
2+
--> $DIR/dont-ice-when-body-tainted-by-errors.rs:19:23
3+
|
4+
LL | trait_error::<()>();
5+
| ^^ the trait `Impossible` is not implemented for `()`
6+
|
7+
help: this trait has no implementations, consider adding one
8+
--> $DIR/dont-ice-when-body-tainted-by-errors.rs:7:1
9+
|
10+
LL | trait Impossible {}
11+
| ^^^^^^^^^^^^^^^^
12+
note: required by a bound in `trait_error`
13+
--> $DIR/dont-ice-when-body-tainted-by-errors.rs:8:19
14+
|
15+
LL | fn trait_error<T: Impossible>() {}
16+
| ^^^^^^^^^^ required by this bound in `trait_error`
17+
18+
error: aborting due to 1 previous error
19+
20+
For more information about this error, try `rustc --explain E0277`.

Diff for: tests/ui/half-open-range-patterns/half-open-range-pats-inclusive-dotdotdot-bad-syntax.stderr

-4
Original file line numberDiff line numberDiff line change
@@ -46,10 +46,6 @@ LL | mac!(0);
4646
= note: for more information, visit https://doc.rust-lang.org/book/ch18-02-refutability.html
4747
= note: the matched value is of type `i32`
4848
= note: this error originates in the macro `mac` (in Nightly builds, run with -Z macro-backtrace for more info)
49-
help: you might want to use `if let` to ignore the variant that isn't matched
50-
|
51-
LL | if let ...$e; { todo!() }
52-
| ++ +++++++++++
5349

5450
error: aborting due to 6 previous errors
5551

Diff for: tests/ui/half-open-range-patterns/half-open-range-pats-inclusive-no-end.stderr

-8
Original file line numberDiff line numberDiff line change
@@ -67,10 +67,6 @@ LL | mac!(0);
6767
= note: for more information, visit https://doc.rust-lang.org/book/ch18-02-refutability.html
6868
= note: the matched value is of type `i32`
6969
= note: this error originates in the macro `mac` (in Nightly builds, run with -Z macro-backtrace for more info)
70-
help: you might want to use `if let` to ignore the variant that isn't matched
71-
|
72-
LL | if let $e...; { todo!() }
73-
| ++ +++++++++++
7470

7571
error[E0005]: refutable pattern in local binding
7672
--> $DIR/half-open-range-pats-inclusive-no-end.rs:20:17
@@ -85,10 +81,6 @@ LL | mac!(0);
8581
= note: for more information, visit https://doc.rust-lang.org/book/ch18-02-refutability.html
8682
= note: the matched value is of type `i32`
8783
= note: this error originates in the macro `mac` (in Nightly builds, run with -Z macro-backtrace for more info)
88-
help: you might want to use `if let` to ignore the variant that isn't matched
89-
|
90-
LL | if let $e..=; { todo!() }
91-
| ++ +++++++++++
9284

9385
error: aborting due to 8 previous errors
9486

Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
// https://github.com/rust-lang/rust/issues/123844
2+
// An uninitialized refutable let should not suggest `let else`, as it can't be used with deferred
3+
// initialization.
4+
5+
fn main() {
6+
let Some(x); //~ ERROR refutable pattern in local binding
7+
x = 1;
8+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
error[E0005]: refutable pattern in local binding
2+
--> $DIR/uninitialized-refutable-let-issue-123844.rs:6:9
3+
|
4+
LL | let Some(x);
5+
| ^^^^^^^ pattern `None` not covered
6+
|
7+
= note: `let` bindings require an "irrefutable pattern", like a `struct` or an `enum` with only one variant
8+
= note: for more information, visit https://doc.rust-lang.org/book/ch18-02-refutability.html
9+
= note: the matched value is of type `Option<i32>`
10+
11+
error: aborting due to 1 previous error
12+
13+
For more information about this error, try `rustc --explain E0005`.

0 commit comments

Comments
 (0)