diff --git a/compiler/rustc_hir_typeck/src/lib.rs b/compiler/rustc_hir_typeck/src/lib.rs index 5ccac9a69252d..3928520153c47 100644 --- a/compiler/rustc_hir_typeck/src/lib.rs +++ b/compiler/rustc_hir_typeck/src/lib.rs @@ -221,12 +221,6 @@ fn typeck_with_fallback<'tcx>( })) } else if let Node::AnonConst(_) = node { match tcx.hir().get(tcx.hir().parent_id(id)) { - Node::Expr(&hir::Expr { - kind: hir::ExprKind::ConstBlock(ref anon_const), .. - }) if anon_const.hir_id == id => Some(fcx.next_ty_var(TypeVariableOrigin { - kind: TypeVariableOriginKind::TypeInference, - span, - })), Node::Ty(&hir::Ty { kind: hir::TyKind::Typeof(ref anon_const), .. }) if anon_const.hir_id == id => { diff --git a/library/std/src/sys_common/thread_local_key.rs b/library/std/src/sys_common/thread_local_key.rs index 89360e45601a7..204834984a227 100644 --- a/library/std/src/sys_common/thread_local_key.rs +++ b/library/std/src/sys_common/thread_local_key.rs @@ -87,31 +87,6 @@ pub struct StaticKey { dtor: Option, } -/// A type for a safely managed OS-based TLS slot. -/// -/// This type allocates an OS TLS key when it is initialized and will deallocate -/// the key when it falls out of scope. When compared with `StaticKey`, this -/// type is entirely safe to use. -/// -/// Implementations will likely, however, contain unsafe code as this type only -/// operates on `*mut u8`, a raw pointer. -/// -/// # Examples -/// -/// ```ignore (cannot-doctest-private-modules) -/// use tls::os::Key; -/// -/// let key = Key::new(None); -/// assert!(key.get().is_null()); -/// key.set(1 as *mut u8); -/// assert!(!key.get().is_null()); -/// -/// drop(key); // deallocate this TLS slot. -/// ``` -pub struct Key { - key: imp::Key, -} - /// Constant initialization value for static TLS keys. /// /// This value specifies no destructor by default. @@ -194,39 +169,3 @@ impl StaticKey { } } } - -impl Key { - /// Creates a new managed OS TLS key. - /// - /// This key will be deallocated when the key falls out of scope. - /// - /// The argument provided is an optionally-specified destructor for the - /// value of this TLS key. When a thread exits and the value for this key - /// is non-null the destructor will be invoked. The TLS value will be reset - /// to null before the destructor is invoked. - /// - /// Note that the destructor will not be run when the `Key` goes out of - /// scope. - #[inline] - pub fn new(dtor: Option) -> Key { - Key { key: unsafe { imp::create(dtor) } } - } - - /// See StaticKey::get - #[inline] - pub fn get(&self) -> *mut u8 { - unsafe { imp::get(self.key) } - } - - /// See StaticKey::set - #[inline] - pub fn set(&self, val: *mut u8) { - unsafe { imp::set(self.key, val) } - } -} - -impl Drop for Key { - fn drop(&mut self) { - unsafe { imp::destroy(self.key) } - } -} diff --git a/library/std/src/sys_common/thread_local_key/tests.rs b/library/std/src/sys_common/thread_local_key/tests.rs index 6f32b858f0966..6a44c65d91869 100644 --- a/library/std/src/sys_common/thread_local_key/tests.rs +++ b/library/std/src/sys_common/thread_local_key/tests.rs @@ -1,24 +1,6 @@ -use super::{Key, StaticKey}; +use super::StaticKey; use core::ptr; -fn assert_sync() {} -fn assert_send() {} - -#[test] -fn smoke() { - assert_sync::(); - assert_send::(); - - let k1 = Key::new(None); - let k2 = Key::new(None); - assert!(k1.get().is_null()); - assert!(k2.get().is_null()); - k1.set(ptr::invalid_mut(1)); - k2.set(ptr::invalid_mut(2)); - assert_eq!(k1.get() as usize, 1); - assert_eq!(k2.get() as usize, 2); -} - #[test] fn statik() { static K1: StaticKey = StaticKey::new(None); diff --git a/library/std/src/thread/local.rs b/library/std/src/thread/local.rs index fa08fdc16530b..3b7c31826b962 100644 --- a/library/std/src/thread/local.rs +++ b/library/std/src/thread/local.rs @@ -134,10 +134,28 @@ impl fmt::Debug for LocalKey { /// thread_local! { /// pub static FOO: RefCell = RefCell::new(1); /// -/// #[allow(unused)] /// static BAR: RefCell = RefCell::new(1.0); /// } -/// # fn main() {} +/// +/// FOO.with(|foo| assert_eq!(*foo.borrow(), 1)); +/// BAR.with(|bar| assert_eq!(*bar.borrow(), 1.0)); +/// ``` +/// +/// This macro supports a special `const {}` syntax that can be used +/// when the initialization expression can be evaluated as a constant. +/// This can enable a more efficient thread local implementation that +/// can avoid lazy initialization. For types that do not +/// [need to be dropped][crate::mem::needs_drop], this can enable an +/// even more efficient implementation that does not need to +/// track any additional state. +/// +/// ``` +/// use std::cell::Cell; +/// thread_local! { +/// pub static FOO: Cell = const { Cell::new(1) }; +/// } +/// +/// FOO.with(|foo| assert_eq!(foo.get(), 1)); /// ``` /// /// See [`LocalKey` documentation][`std::thread::LocalKey`] for more diff --git a/src/bootstrap/bootstrap.py b/src/bootstrap/bootstrap.py index 680a8da6adf20..9c6c917ac4a2b 100644 --- a/src/bootstrap/bootstrap.py +++ b/src/bootstrap/bootstrap.py @@ -209,19 +209,25 @@ def default_build_triple(verbose): # install, use their preference. This fixes most issues with Windows builds # being detected as GNU instead of MSVC. default_encoding = sys.getdefaultencoding() - try: - version = subprocess.check_output(["rustc", "--version", "--verbose"], - stderr=subprocess.DEVNULL) - version = version.decode(default_encoding) - host = next(x for x in version.split('\n') if x.startswith("host: ")) - triple = host.split("host: ")[1] - if verbose: - print("detected default triple {} from pre-installed rustc".format(triple)) - return triple - except Exception as e: + + if sys.platform == 'darwin': if verbose: - print("pre-installed rustc not detected: {}".format(e)) + print("not using rustc detection as it is unreliable on macOS") print("falling back to auto-detect") + else: + try: + version = subprocess.check_output(["rustc", "--version", "--verbose"], + stderr=subprocess.DEVNULL) + version = version.decode(default_encoding) + host = next(x for x in version.split('\n') if x.startswith("host: ")) + triple = host.split("host: ")[1] + if verbose: + print("detected default triple {} from pre-installed rustc".format(triple)) + return triple + except Exception as e: + if verbose: + print("pre-installed rustc not detected: {}".format(e)) + print("falling back to auto-detect") required = sys.platform != 'win32' ostype = require(["uname", "-s"], exit=required) diff --git a/src/bootstrap/bootstrap_test.py b/src/bootstrap/bootstrap_test.py index 26bd80a008fb3..5ecda83ee66b1 100644 --- a/src/bootstrap/bootstrap_test.py +++ b/src/bootstrap/bootstrap_test.py @@ -112,6 +112,14 @@ def test_set_top_level(self): build = self.serialize_and_parse(["--set", "profile=compiler"]) self.assertEqual(build.get_toml("profile"), 'compiler') + def test_set_codegen_backends(self): + build = self.serialize_and_parse(["--set", "rust.codegen-backends=cranelift"]) + self.assertNotEqual(build.config_toml.find("codegen-backends = ['cranelift']"), -1) + build = self.serialize_and_parse(["--set", "rust.codegen-backends=cranelift,llvm"]) + self.assertNotEqual(build.config_toml.find("codegen-backends = ['cranelift', 'llvm']"), -1) + build = self.serialize_and_parse(["--enable-full-tools"]) + self.assertNotEqual(build.config_toml.find("codegen-backends = ['llvm']"), -1) + if __name__ == '__main__': SUITE = unittest.TestSuite() TEST_LOADER = unittest.TestLoader() diff --git a/src/bootstrap/configure.py b/src/bootstrap/configure.py index dd1851e29a930..571062a3a6fd0 100755 --- a/src/bootstrap/configure.py +++ b/src/bootstrap/configure.py @@ -153,8 +153,7 @@ def v(*args): "experimental LLVM targets to build") v("release-channel", "rust.channel", "the name of the release channel to build") v("release-description", "rust.description", "optional descriptive string for version output") -v("dist-compression-formats", None, - "comma-separated list of compression formats to use") +v("dist-compression-formats", None, "List of compression formats to use") # Used on systems where "cc" is unavailable v("default-linker", "rust.default-linker", "the default linker") @@ -168,8 +167,8 @@ def v(*args): v("tools", None, "List of extended tools will be installed") v("codegen-backends", None, "List of codegen backends to build") v("build", "build.build", "GNUs ./configure syntax LLVM build triple") -v("host", None, "GNUs ./configure syntax LLVM host triples") -v("target", None, "GNUs ./configure syntax LLVM target triples") +v("host", None, "List of GNUs ./configure syntax LLVM host triples") +v("target", None, "List of GNUs ./configure syntax LLVM target triples") v("set", None, "set arbitrary key/value pairs in TOML configuration") @@ -182,6 +181,11 @@ def err(msg): print("configure: error: " + msg) sys.exit(1) +def is_value_list(key): + for option in options: + if option.name == key and option.desc.startswith('List of'): + return True + return False if '--help' in sys.argv or '-h' in sys.argv: print('Usage: ./configure [options]') @@ -295,6 +299,8 @@ def set(key, value, config): parts = key.split('.') for i, part in enumerate(parts): if i == len(parts) - 1: + if is_value_list(part) and isinstance(value, str): + value = value.split(',') arr[part] = value else: if part not in arr: diff --git a/src/librustdoc/passes/collect_intra_doc_links.rs b/src/librustdoc/passes/collect_intra_doc_links.rs index f2486abaaa77e..7e173a171a83a 100644 --- a/src/librustdoc/passes/collect_intra_doc_links.rs +++ b/src/librustdoc/passes/collect_intra_doc_links.rs @@ -1295,7 +1295,8 @@ impl LinkCollector<'_, '_> { } } } - resolution_failure(self, diag, path_str, disambiguator, smallvec![err]) + resolution_failure(self, diag, path_str, disambiguator, smallvec![err]); + return vec![]; } } } @@ -1331,13 +1332,14 @@ impl LinkCollector<'_, '_> { .fold(0, |acc, res| if let Ok(res) = res { acc + res.len() } else { acc }); if len == 0 { - return resolution_failure( + resolution_failure( self, diag, path_str, disambiguator, candidates.into_iter().filter_map(|res| res.err()).collect(), ); + return vec![]; } else if len == 1 { candidates.into_iter().filter_map(|res| res.ok()).flatten().collect::>() } else { @@ -1642,9 +1644,8 @@ fn resolution_failure( path_str: &str, disambiguator: Option, kinds: SmallVec<[ResolutionFailure<'_>; 3]>, -) -> Vec<(Res, Option)> { +) { let tcx = collector.cx.tcx; - let mut recovered_res = None; report_diagnostic( tcx, BROKEN_INTRA_DOC_LINKS, @@ -1736,19 +1737,25 @@ fn resolution_failure( if !path_str.contains("::") { if disambiguator.map_or(true, |d| d.ns() == MacroNS) - && let Some(&res) = collector.cx.tcx.resolutions(()).all_macro_rules - .get(&Symbol::intern(path_str)) + && collector + .cx + .tcx + .resolutions(()) + .all_macro_rules + .get(&Symbol::intern(path_str)) + .is_some() { diag.note(format!( "`macro_rules` named `{path_str}` exists in this crate, \ but it is not in scope at this link's location" )); - recovered_res = res.try_into().ok().map(|res| (res, None)); } else { // If the link has `::` in it, assume it was meant to be an // intra-doc link. Otherwise, the `[]` might be unrelated. - diag.help("to escape `[` and `]` characters, \ - add '\\' before them like `\\[` or `\\]`"); + diag.help( + "to escape `[` and `]` characters, \ + add '\\' before them like `\\[` or `\\]`", + ); } } @@ -1854,11 +1861,6 @@ fn resolution_failure( } }, ); - - match recovered_res { - Some(r) => vec![r], - None => Vec::new(), - } } fn report_multiple_anchors(cx: &DocContext<'_>, diag_info: DiagnosticInfo<'_>) { diff --git a/tests/rustdoc/issue-106142.rs b/tests/rustdoc/issue-106142.rs new file mode 100644 index 0000000000000..41505e72405d3 --- /dev/null +++ b/tests/rustdoc/issue-106142.rs @@ -0,0 +1,14 @@ +// @has 'issue_106142/a/index.html' +// @count 'issue_106142/a/index.html' '//ul[@class="item-table"]//li//a' 1 + +#![allow(rustdoc::broken_intra_doc_links)] + +pub mod a { + /// [`m`] + pub fn f() {} + + #[macro_export] + macro_rules! m { + () => {}; + } +} diff --git a/tests/ui/panics/fmt-only-once.rs b/tests/ui/panics/fmt-only-once.rs new file mode 100644 index 0000000000000..6211bf961b3bc --- /dev/null +++ b/tests/ui/panics/fmt-only-once.rs @@ -0,0 +1,21 @@ +// run-fail +// check-run-results +// exec-env:RUST_BACKTRACE=0 + +// Test that we format the panic message only once. +// Regression test for https://github.com/rust-lang/rust/issues/110717 + +use std::fmt; + +struct PrintOnFmt; + +impl fmt::Display for PrintOnFmt { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + eprintln!("fmt"); + f.write_str("PrintOnFmt") + } +} + +fn main() { + panic!("{}", PrintOnFmt) +} diff --git a/tests/ui/panics/fmt-only-once.run.stderr b/tests/ui/panics/fmt-only-once.run.stderr new file mode 100644 index 0000000000000..39bd06881ad05 --- /dev/null +++ b/tests/ui/panics/fmt-only-once.run.stderr @@ -0,0 +1,3 @@ +fmt +thread 'main' panicked at 'PrintOnFmt', $DIR/fmt-only-once.rs:20:5 +note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace