Skip to content

Commit 408eacf

Browse files
committed
Auto merge of #146468 - Zalathar:rollup-6u3s44d, r=Zalathar
Rollup of 15 pull requests Successful merges: - #144549 (match clang's `va_arg` assembly on arm targets) - #145895 (thread parking: fix docs and examples) - #146308 (support integer literals in `${concat()}`) - #146323 (check before test for hardware capabilites in bits 32~63 of usize) - #146332 (tidy: make behavior of extra-checks more uniform) - #146374 (Update `browser-ui-test` version to `0.22.2`) - #146413 (Improve suggestion in case a bare URL is surrounded by brackets) - #146426 (Bump miow to 0.60.1) - #146432 (Implement `Socket::take_error` for Hermit) - #146433 (rwlock tests: fix miri macos test regression) - #146435 (Change the default value of `gcc.download-ci-gcc` to `true`) - #146439 (fix cfg for poison test macro) - #146448 ([rustdoc] Correctly handle literal search on paths) - #146449 (Fix `libgccjit` symlink when we build GCC locally) - #146455 (test: remove an outdated normalization for rustc versions) r? `@ghost` `@rustbot` modify labels: rollup
2 parents ac4495a + be33ef2 commit 408eacf

File tree

38 files changed

+502
-204
lines changed

38 files changed

+502
-204
lines changed

Cargo.lock

Lines changed: 3 additions & 69 deletions
Original file line numberDiff line numberDiff line change
@@ -2347,11 +2347,11 @@ dependencies = [
23472347

23482348
[[package]]
23492349
name = "miow"
2350-
version = "0.6.0"
2350+
version = "0.6.1"
23512351
source = "registry+https://github.com/rust-lang/crates.io-index"
2352-
checksum = "359f76430b20a79f9e20e115b3428614e654f04fab314482fc0fda0ebd3c6044"
2352+
checksum = "536bfad37a309d62069485248eeaba1e8d9853aaf951caaeaed0585a95346f08"
23532353
dependencies = [
2354-
"windows-sys 0.48.0",
2354+
"windows-sys 0.60.2",
23552355
]
23562356

23572357
[[package]]
@@ -6314,15 +6314,6 @@ dependencies = [
63146314
"windows-link",
63156315
]
63166316

6317-
[[package]]
6318-
name = "windows-sys"
6319-
version = "0.48.0"
6320-
source = "registry+https://github.com/rust-lang/crates.io-index"
6321-
checksum = "677d2418bec65e3338edb076e806bc1ec15693c5d0104683f2efe857f61056a9"
6322-
dependencies = [
6323-
"windows-targets 0.48.5",
6324-
]
6325-
63266317
[[package]]
63276318
name = "windows-sys"
63286319
version = "0.52.0"
@@ -6350,21 +6341,6 @@ dependencies = [
63506341
"windows-targets 0.53.3",
63516342
]
63526343

6353-
[[package]]
6354-
name = "windows-targets"
6355-
version = "0.48.5"
6356-
source = "registry+https://github.com/rust-lang/crates.io-index"
6357-
checksum = "9a2fa6e2155d7247be68c096456083145c183cbbbc2764150dda45a87197940c"
6358-
dependencies = [
6359-
"windows_aarch64_gnullvm 0.48.5",
6360-
"windows_aarch64_msvc 0.48.5",
6361-
"windows_i686_gnu 0.48.5",
6362-
"windows_i686_msvc 0.48.5",
6363-
"windows_x86_64_gnu 0.48.5",
6364-
"windows_x86_64_gnullvm 0.48.5",
6365-
"windows_x86_64_msvc 0.48.5",
6366-
]
6367-
63686344
[[package]]
63696345
name = "windows-targets"
63706346
version = "0.52.6"
@@ -6407,12 +6383,6 @@ dependencies = [
64076383
"windows-link",
64086384
]
64096385

6410-
[[package]]
6411-
name = "windows_aarch64_gnullvm"
6412-
version = "0.48.5"
6413-
source = "registry+https://github.com/rust-lang/crates.io-index"
6414-
checksum = "2b38e32f0abccf9987a4e3079dfb67dcd799fb61361e53e2882c3cbaf0d905d8"
6415-
64166386
[[package]]
64176387
name = "windows_aarch64_gnullvm"
64186388
version = "0.52.6"
@@ -6425,12 +6395,6 @@ version = "0.53.0"
64256395
source = "registry+https://github.com/rust-lang/crates.io-index"
64266396
checksum = "86b8d5f90ddd19cb4a147a5fa63ca848db3df085e25fee3cc10b39b6eebae764"
64276397

6428-
[[package]]
6429-
name = "windows_aarch64_msvc"
6430-
version = "0.48.5"
6431-
source = "registry+https://github.com/rust-lang/crates.io-index"
6432-
checksum = "dc35310971f3b2dbbf3f0690a219f40e2d9afcf64f9ab7cc1be722937c26b4bc"
6433-
64346398
[[package]]
64356399
name = "windows_aarch64_msvc"
64366400
version = "0.52.6"
@@ -6443,12 +6407,6 @@ version = "0.53.0"
64436407
source = "registry+https://github.com/rust-lang/crates.io-index"
64446408
checksum = "c7651a1f62a11b8cbd5e0d42526e55f2c99886c77e007179efff86c2b137e66c"
64456409

6446-
[[package]]
6447-
name = "windows_i686_gnu"
6448-
version = "0.48.5"
6449-
source = "registry+https://github.com/rust-lang/crates.io-index"
6450-
checksum = "a75915e7def60c94dcef72200b9a8e58e5091744960da64ec734a6c6e9b3743e"
6451-
64526410
[[package]]
64536411
name = "windows_i686_gnu"
64546412
version = "0.52.6"
@@ -6473,12 +6431,6 @@ version = "0.53.0"
64736431
source = "registry+https://github.com/rust-lang/crates.io-index"
64746432
checksum = "9ce6ccbdedbf6d6354471319e781c0dfef054c81fbc7cf83f338a4296c0cae11"
64756433

6476-
[[package]]
6477-
name = "windows_i686_msvc"
6478-
version = "0.48.5"
6479-
source = "registry+https://github.com/rust-lang/crates.io-index"
6480-
checksum = "8f55c233f70c4b27f66c523580f78f1004e8b5a8b659e05a4eb49d4166cca406"
6481-
64826434
[[package]]
64836435
name = "windows_i686_msvc"
64846436
version = "0.52.6"
@@ -6491,12 +6443,6 @@ version = "0.53.0"
64916443
source = "registry+https://github.com/rust-lang/crates.io-index"
64926444
checksum = "581fee95406bb13382d2f65cd4a908ca7b1e4c2f1917f143ba16efe98a589b5d"
64936445

6494-
[[package]]
6495-
name = "windows_x86_64_gnu"
6496-
version = "0.48.5"
6497-
source = "registry+https://github.com/rust-lang/crates.io-index"
6498-
checksum = "53d40abd2583d23e4718fddf1ebec84dbff8381c07cae67ff7768bbf19c6718e"
6499-
65006446
[[package]]
65016447
name = "windows_x86_64_gnu"
65026448
version = "0.52.6"
@@ -6509,12 +6455,6 @@ version = "0.53.0"
65096455
source = "registry+https://github.com/rust-lang/crates.io-index"
65106456
checksum = "2e55b5ac9ea33f2fc1716d1742db15574fd6fc8dadc51caab1c16a3d3b4190ba"
65116457

6512-
[[package]]
6513-
name = "windows_x86_64_gnullvm"
6514-
version = "0.48.5"
6515-
source = "registry+https://github.com/rust-lang/crates.io-index"
6516-
checksum = "0b7b52767868a23d5bab768e390dc5f5c55825b6d30b86c844ff2dc7414044cc"
6517-
65186458
[[package]]
65196459
name = "windows_x86_64_gnullvm"
65206460
version = "0.52.6"
@@ -6527,12 +6467,6 @@ version = "0.53.0"
65276467
source = "registry+https://github.com/rust-lang/crates.io-index"
65286468
checksum = "0a6e035dd0599267ce1ee132e51c27dd29437f63325753051e71dd9e42406c57"
65296469

6530-
[[package]]
6531-
name = "windows_x86_64_msvc"
6532-
version = "0.48.5"
6533-
source = "registry+https://github.com/rust-lang/crates.io-index"
6534-
checksum = "ed94fce61571a4006852b7389a063ab983c02eb1bb37b47f8272ce92d06d9538"
6535-
65366470
[[package]]
65376471
name = "windows_x86_64_msvc"
65386472
version = "0.52.6"

compiler/rustc_codegen_llvm/src/va_arg.rs

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -908,6 +908,21 @@ pub(super) fn emit_va_arg<'ll, 'tcx>(
908908
)
909909
}
910910
"aarch64" => emit_aapcs_va_arg(bx, addr, target_ty),
911+
"arm" => {
912+
// Types wider than 16 bytes are not currently supported. Clang has special logic for
913+
// such types, but `VaArgSafe` is not implemented for any type that is this large.
914+
assert!(bx.cx.size_of(target_ty).bytes() <= 16);
915+
916+
emit_ptr_va_arg(
917+
bx,
918+
addr,
919+
target_ty,
920+
PassMode::Direct,
921+
SlotSize::Bytes4,
922+
AllowHigherAlign::Yes,
923+
ForceRightAdjust::No,
924+
)
925+
}
911926
"s390x" => emit_s390x_va_arg(bx, addr, target_ty),
912927
"powerpc" => emit_powerpc_va_arg(bx, addr, target_ty),
913928
"powerpc64" | "powerpc64le" => emit_ptr_va_arg(

compiler/rustc_codegen_ssa/src/mir/block.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -520,7 +520,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
520520
LocalRef::Place(va_list) => {
521521
bx.va_end(va_list.val.llval);
522522

523-
// Explicitly end the lifetime of the `va_list`, this matters for LLVM.
523+
// Explicitly end the lifetime of the `va_list`, improves LLVM codegen.
524524
bx.lifetime_end(va_list.val.llval, va_list.layout.size);
525525
}
526526
_ => bug!("C-variadic function must have a `VaList` place"),

compiler/rustc_codegen_ssa/src/mir/mod.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -438,6 +438,10 @@ fn arg_local_refs<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>(
438438

439439
if fx.fn_abi.c_variadic && arg_index == fx.fn_abi.args.len() {
440440
let va_list = PlaceRef::alloca(bx, bx.layout_of(arg_ty));
441+
442+
// Explicitly start the lifetime of the `va_list`, improves LLVM codegen.
443+
bx.lifetime_start(va_list.val.llval, va_list.layout.size);
444+
441445
bx.va_start(va_list.val.llval);
442446

443447
return LocalRef::Place(va_list);

compiler/rustc_expand/src/mbe/transcribe.rs

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -940,11 +940,27 @@ fn extract_symbol_from_pnr<'a>(
940940
{
941941
Ok(*symbol)
942942
}
943+
ParseNtResult::Literal(expr)
944+
if let ExprKind::Lit(lit @ Lit { kind: LitKind::Integer, symbol, suffix }) =
945+
&expr.kind =>
946+
{
947+
if lit.is_semantic_float() {
948+
Err(dcx
949+
.struct_err("floats are not supported as metavariables of `${concat(..)}`")
950+
.with_span(span_err))
951+
} else if suffix.is_none() {
952+
Ok(*symbol)
953+
} else {
954+
Err(dcx
955+
.struct_err("integer metavariables of `${concat(..)}` must not be suffixed")
956+
.with_span(span_err))
957+
}
958+
}
943959
_ => Err(dcx
944960
.struct_err(
945961
"metavariables of `${concat(..)}` must be of type `ident`, `literal` or `tt`",
946962
)
947-
.with_note("currently only string literals are supported")
963+
.with_note("currently only string and integer literals are supported")
948964
.with_span(span_err)),
949965
}
950966
}

library/std/src/sys/net/connection/socket/hermit.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -304,7 +304,8 @@ impl Socket {
304304
}
305305

306306
pub fn take_error(&self) -> io::Result<Option<io::Error>> {
307-
unimplemented!()
307+
let raw: c_int = getsockopt(self, libc::SOL_SOCKET, libc::SO_ERROR)?;
308+
if raw == 0 { Ok(None) } else { Ok(Some(io::Error::from_raw_os_error(raw as i32))) }
308309
}
309310

310311
// This is used by sys_common code to abstract over Windows and Unix.

library/std/src/sys/pal/hermit/os.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ use crate::ffi::{OsStr, OsString};
33
use crate::marker::PhantomData;
44
use crate::path::{self, PathBuf};
55
use crate::sys::unsupported;
6-
use crate::{fmt, io, str};
6+
use crate::{fmt, io};
77

88
pub fn errno() -> i32 {
99
unsafe { hermit_abi::get_errno() }

library/std/src/sys/sync/once/queue.rs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -276,7 +276,9 @@ fn wait(
276276
// If the managing thread happens to signal and unpark us before we
277277
// can park ourselves, the result could be this thread never gets
278278
// unparked. Luckily `park` comes with the guarantee that if it got
279-
// an `unpark` just before on an unparked thread it does not park.
279+
// an `unpark` just before on an unparked thread it does not park. Crucially, we know
280+
// the `unpark` must have happened between the `compare_exchange_weak` above and here,
281+
// and there's no other `park` in that code that could steal our token.
280282
// SAFETY: we retrieved this handle on the current thread above.
281283
unsafe { node.thread.park() }
282284
}

library/std/src/thread/mod.rs

Lines changed: 52 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1021,13 +1021,23 @@ impl Drop for PanicGuard {
10211021
/// specifying a maximum time to block the thread for.
10221022
///
10231023
/// * The [`unpark`] method on a [`Thread`] atomically makes the token available
1024-
/// if it wasn't already. Because the token is initially absent, [`unpark`]
1025-
/// followed by [`park`] will result in the second call returning immediately.
1026-
///
1027-
/// The API is typically used by acquiring a handle to the current thread,
1028-
/// placing that handle in a shared data structure so that other threads can
1029-
/// find it, and then `park`ing in a loop. When some desired condition is met, another
1030-
/// thread calls [`unpark`] on the handle.
1024+
/// if it wasn't already. Because the token can be held by a thread even if it is currently not
1025+
/// parked, [`unpark`] followed by [`park`] will result in the second call returning immediately.
1026+
/// However, note that to rely on this guarantee, you need to make sure that your `unpark` happens
1027+
/// after all `park` that may be done by other data structures!
1028+
///
1029+
/// The API is typically used by acquiring a handle to the current thread, placing that handle in a
1030+
/// shared data structure so that other threads can find it, and then `park`ing in a loop. When some
1031+
/// desired condition is met, another thread calls [`unpark`] on the handle. The last bullet point
1032+
/// above guarantees that even if the `unpark` occurs before the thread is finished `park`ing, it
1033+
/// will be woken up properly.
1034+
///
1035+
/// Note that the coordination via the shared data structure is crucial: If you `unpark` a thread
1036+
/// without first establishing that it is about to be `park`ing within your code, that `unpark` may
1037+
/// get consumed by a *different* `park` in the same thread, leading to a deadlock. This also means
1038+
/// you must not call unknown code between setting up for parking and calling `park`; for instance,
1039+
/// if you invoke `println!`, that may itself call `park` and thus consume your `unpark` and cause a
1040+
/// deadlock.
10311041
///
10321042
/// The motivation for this design is twofold:
10331043
///
@@ -1058,33 +1068,47 @@ impl Drop for PanicGuard {
10581068
///
10591069
/// ```
10601070
/// use std::thread;
1061-
/// use std::sync::{Arc, atomic::{Ordering, AtomicBool}};
1071+
/// use std::sync::atomic::{Ordering, AtomicBool};
10621072
/// use std::time::Duration;
10631073
///
1064-
/// let flag = Arc::new(AtomicBool::new(false));
1065-
/// let flag2 = Arc::clone(&flag);
1074+
/// static QUEUED: AtomicBool = AtomicBool::new(false);
1075+
/// static FLAG: AtomicBool = AtomicBool::new(false);
10661076
///
10671077
/// let parked_thread = thread::spawn(move || {
1078+
/// println!("Thread spawned");
1079+
/// // Signal that we are going to `park`. Between this store and our `park`, there may
1080+
/// // be no other `park`, or else that `park` could consume our `unpark` token!
1081+
/// QUEUED.store(true, Ordering::Release);
10681082
/// // We want to wait until the flag is set. We *could* just spin, but using
10691083
/// // park/unpark is more efficient.
1070-
/// while !flag2.load(Ordering::Relaxed) {
1071-
/// println!("Parking thread");
1084+
/// while !FLAG.load(Ordering::Acquire) {
1085+
/// // We can *not* use `println!` here since that could use thread parking internally.
10721086
/// thread::park();
10731087
/// // We *could* get here spuriously, i.e., way before the 10ms below are over!
10741088
/// // But that is no problem, we are in a loop until the flag is set anyway.
1075-
/// println!("Thread unparked");
10761089
/// }
10771090
/// println!("Flag received");
10781091
/// });
10791092
///
10801093
/// // Let some time pass for the thread to be spawned.
10811094
/// thread::sleep(Duration::from_millis(10));
10821095
///
1096+
/// // Ensure the thread is about to park.
1097+
/// // This is crucial! It guarantees that the `unpark` below is not consumed
1098+
/// // by some other code in the parked thread (e.g. inside `println!`).
1099+
/// while !QUEUED.load(Ordering::Acquire) {
1100+
/// // Spinning is of course inefficient; in practice, this would more likely be
1101+
/// // a dequeue where we have no work to do if there's nobody queued.
1102+
/// std::hint::spin_loop();
1103+
/// }
1104+
///
10831105
/// // Set the flag, and let the thread wake up.
1084-
/// // There is no race condition here, if `unpark`
1106+
/// // There is no race condition here: if `unpark`
10851107
/// // happens first, `park` will return immediately.
1108+
/// // There is also no other `park` that could consume this token,
1109+
/// // since we waited until the other thread got queued.
10861110
/// // Hence there is no risk of a deadlock.
1087-
/// flag.store(true, Ordering::Relaxed);
1111+
/// FLAG.store(true, Ordering::Release);
10881112
/// println!("Unpark the thread");
10891113
/// parked_thread.thread().unpark();
10901114
///
@@ -1494,10 +1518,14 @@ impl Thread {
14941518
/// ```
14951519
/// use std::thread;
14961520
/// use std::time::Duration;
1521+
/// use std::sync::atomic::{AtomicBool, Ordering};
1522+
///
1523+
/// static QUEUED: AtomicBool = AtomicBool::new(false);
14971524
///
14981525
/// let parked_thread = thread::Builder::new()
14991526
/// .spawn(|| {
15001527
/// println!("Parking thread");
1528+
/// QUEUED.store(true, Ordering::Release);
15011529
/// thread::park();
15021530
/// println!("Thread unparked");
15031531
/// })
@@ -1506,6 +1534,15 @@ impl Thread {
15061534
/// // Let some time pass for the thread to be spawned.
15071535
/// thread::sleep(Duration::from_millis(10));
15081536
///
1537+
/// // Wait until the other thread is queued.
1538+
/// // This is crucial! It guarantees that the `unpark` below is not consumed
1539+
/// // by some other code in the parked thread (e.g. inside `println!`).
1540+
/// while !QUEUED.load(Ordering::Acquire) {
1541+
/// // Spinning is of course inefficient; in practice, this would more likely be
1542+
/// // a dequeue where we have no work to do if there's nobody queued.
1543+
/// std::hint::spin_loop();
1544+
/// }
1545+
///
15091546
/// println!("Unpark the thread");
15101547
/// parked_thread.thread().unpark();
15111548
///

library/std/src/thread/tests.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -287,6 +287,8 @@ fn test_park_unpark_called_other_thread() {
287287
for _ in 0..10 {
288288
let th = thread::current();
289289

290+
// Here we rely on `thread::spawn` (specifically the part that runs after spawning
291+
// the thread) to not consume the parking token.
290292
let _guard = thread::spawn(move || {
291293
super::sleep(Duration::from_millis(50));
292294
th.unpark();
@@ -316,6 +318,8 @@ fn test_park_timeout_unpark_called_other_thread() {
316318
for _ in 0..10 {
317319
let th = thread::current();
318320

321+
// Here we rely on `thread::spawn` (specifically the part that runs after spawning
322+
// the thread) to not consume the parking token.
319323
let _guard = thread::spawn(move || {
320324
super::sleep(Duration::from_millis(50));
321325
th.unpark();

0 commit comments

Comments
 (0)