From ee4b0445d37dcd236e122303dea345b6891b7778 Mon Sep 17 00:00:00 2001 From: Tshepang Mbambo Date: Tue, 29 Oct 2024 23:14:00 +0200 Subject: [PATCH 01/16] rust_analyzer_helix.toml: add library/ manifest Also, sort list --- src/etc/rust_analyzer_helix.toml | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src/etc/rust_analyzer_helix.toml b/src/etc/rust_analyzer_helix.toml index 642350cad34..9998ebcc03c 100644 --- a/src/etc/rust_analyzer_helix.toml +++ b/src/etc/rust_analyzer_helix.toml @@ -1,11 +1,12 @@ [language-server.rust-analyzer.config] linkedProjects = [ "Cargo.toml", - "src/tools/x/Cargo.toml", + "compiler/rustc_codegen_cranelift/Cargo.toml", + "compiler/rustc_codegen_gcc/Cargo.toml", + "library/Cargo.toml", "src/bootstrap/Cargo.toml", "src/tools/rust-analyzer/Cargo.toml", - "compiler/rustc_codegen_cranelift/Cargo.toml", - "compiler/rustc_codegen_gcc/Cargo.toml" + "src/tools/x/Cargo.toml", ] [language-server.rust-analyzer.config.check] From df8c20d7a5ddb84eb1e5fd2c366f51d357306f34 Mon Sep 17 00:00:00 2001 From: Arthur Carcano Date: Wed, 30 Oct 2024 16:40:55 +0100 Subject: [PATCH 02/16] Add intra-doc link in str::xxx_prefix --- library/core/src/str/mod.rs | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/library/core/src/str/mod.rs b/library/core/src/str/mod.rs index 89addc4cb74..4c2d43b9ede 100644 --- a/library/core/src/str/mod.rs +++ b/library/core/src/str/mod.rs @@ -2169,7 +2169,7 @@ impl str { /// Returns a string slice with the prefix removed. /// /// If the string starts with the pattern `prefix`, returns the substring after the prefix, - /// wrapped in `Some`. Unlike `trim_start_matches`, this method removes the prefix exactly once. + /// wrapped in `Some`. Unlike [`trim_start_matches`], this method removes the prefix exactly once. /// /// If the string does not start with `prefix`, returns `None`. /// @@ -2178,6 +2178,7 @@ impl str { /// /// [`char`]: prim@char /// [pattern]: self::pattern + /// [`trim_start_matches`]: Self::trim_start_matches /// /// # Examples /// @@ -2196,7 +2197,7 @@ impl str { /// Returns a string slice with the suffix removed. /// /// If the string ends with the pattern `suffix`, returns the substring before the suffix, - /// wrapped in `Some`. Unlike `trim_end_matches`, this method removes the suffix exactly once. + /// wrapped in `Some`. Unlike [`trim_end_matches`], this method removes the suffix exactly once. /// /// If the string does not end with `suffix`, returns `None`. /// @@ -2205,6 +2206,7 @@ impl str { /// /// [`char`]: prim@char /// [pattern]: self::pattern + /// [`trim_end_matches`]: Self::trim_end_matches /// /// # Examples /// From df445264b3e97cb3e2845f6fbb9ae541225f86cf Mon Sep 17 00:00:00 2001 From: Arthur Carcano Date: Wed, 30 Oct 2024 16:50:55 +0100 Subject: [PATCH 03/16] Add intra-doc link in str::xxx_char_boundary --- library/core/src/str/mod.rs | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/library/core/src/str/mod.rs b/library/core/src/str/mod.rs index 4c2d43b9ede..208ad9e7e5f 100644 --- a/library/core/src/str/mod.rs +++ b/library/core/src/str/mod.rs @@ -211,7 +211,7 @@ impl str { } } - /// Finds the closest `x` not exceeding `index` where `is_char_boundary(x)` is `true`. + /// Finds the closest `x` not exceeding `index` where [`is_char_boundary(x)`] is `true`. /// /// This method can help you truncate a string so that it's still valid UTF-8, but doesn't /// exceed a given number of bytes. Note that this is done purely at the character level @@ -219,6 +219,8 @@ impl str { /// split. For example, the emoji 🧑‍🔬 (scientist) could be split so that the string only /// includes 🧑 (person) instead. /// + /// [`is_char_boundary(x)`]: Self::is_char_boundary + /// /// # Examples /// /// ``` @@ -247,7 +249,7 @@ impl str { } } - /// Finds the closest `x` not below `index` where `is_char_boundary(x)` is `true`. + /// Finds the closest `x` not below `index` where [`is_char_boundary(x)`] is `true`. /// /// If `index` is greater than the length of the string, this returns the length of the string. /// @@ -255,7 +257,7 @@ impl str { /// for more details. /// /// [`floor_char_boundary`]: str::floor_char_boundary - /// + /// [`is_char_boundary(x)`]: Self::is_char_boundary /// /// # Examples /// From 57673dd6463856c8bad426dc7508c69fa3369122 Mon Sep 17 00:00:00 2001 From: Taiki Endo Date: Fri, 1 Nov 2024 22:39:08 +0900 Subject: [PATCH 04/16] Remove needless #![feature(asm_experimental_arch)] from loongarch64 inline assembly test --- tests/assembly/asm/loongarch-type.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/assembly/asm/loongarch-type.rs b/tests/assembly/asm/loongarch-type.rs index 1b097f41105..c51d35876d9 100644 --- a/tests/assembly/asm/loongarch-type.rs +++ b/tests/assembly/asm/loongarch-type.rs @@ -3,7 +3,7 @@ //@ compile-flags: -Zmerge-functions=disabled //@ needs-llvm-components: loongarch -#![feature(no_core, lang_items, rustc_attrs, asm_experimental_arch)] +#![feature(no_core, lang_items, rustc_attrs)] #![crate_type = "rlib"] #![no_core] #![allow(asm_sub_register, non_camel_case_types)] From 37db36594838d85f72e2282e73707071e80e31c0 Mon Sep 17 00:00:00 2001 From: Urgau Date: Fri, 1 Nov 2024 12:44:55 +0100 Subject: [PATCH 05/16] Also treat `impl` definition parent as transparent regarding modules --- compiler/rustc_lint/src/non_local_def.rs | 10 ++- .../convoluted-locals-132427.rs | 64 +++++++++++++++++++ 2 files changed, 72 insertions(+), 2 deletions(-) create mode 100644 tests/ui/lint/non-local-defs/convoluted-locals-132427.rs diff --git a/compiler/rustc_lint/src/non_local_def.rs b/compiler/rustc_lint/src/non_local_def.rs index 3c31b879bd6..3c33b2dd478 100644 --- a/compiler/rustc_lint/src/non_local_def.rs +++ b/compiler/rustc_lint/src/non_local_def.rs @@ -151,9 +151,15 @@ impl<'tcx> LateLintPass<'tcx> for NonLocalDefinitions { // }; // }; // ``` + // + // It isn't possible to mix a impl in a module with const-anon, but an item can + // be put inside a module and referenced by a impl so we also have to treat the + // item parent as transparent to module and for consistency we have to do the same + // for impl, otherwise the item-def and impl-def won't have the same parent. let outermost_impl_parent = peel_parent_while(cx.tcx, parent, |tcx, did| { - tcx.def_kind(did) == DefKind::Const - && tcx.opt_item_name(did) == Some(kw::Underscore) + tcx.def_kind(did) == DefKind::Mod + || (tcx.def_kind(did) == DefKind::Const + && tcx.opt_item_name(did) == Some(kw::Underscore)) }); // 2. We check if any of the paths reference a the `impl`-parent. diff --git a/tests/ui/lint/non-local-defs/convoluted-locals-132427.rs b/tests/ui/lint/non-local-defs/convoluted-locals-132427.rs new file mode 100644 index 00000000000..5732e048ae3 --- /dev/null +++ b/tests/ui/lint/non-local-defs/convoluted-locals-132427.rs @@ -0,0 +1,64 @@ +// Regression tests for https://github.com/rust-lang/rust/issues/132427 + +//@ check-pass + +// original +mod auth { + const _: () = { + pub enum ArbitraryContext {} + + const _: () = { + impl ArbitraryContext {} + }; + }; +} + +mod z { + pub enum ArbitraryContext {} + + const _: () = { + const _: () = { + impl ArbitraryContext {} + }; + }; +} + +const _: () = { + mod auth { + const _: () = { + pub enum ArbitraryContext {} + + const _: () = { + impl ArbitraryContext {} + }; + }; + } +}; + +mod a { + mod b { + const _: () = { + pub enum ArbitraryContext {} + + const _: () = { + impl ArbitraryContext {} + }; + }; + } +} + +mod foo { + const _: () = { + mod auth { + const _: () = { + pub enum ArbitraryContext {} + + const _: () = { + impl ArbitraryContext {} + }; + }; + } + }; +} + +fn main() {} From e1233153ac2dcc68013f9698430ac27c7abec099 Mon Sep 17 00:00:00 2001 From: Mads Marquart Date: Fri, 1 Nov 2024 17:07:18 +0100 Subject: [PATCH 06/16] Move versioned LLVM target creation to rustc_codegen_ssa The OS version depends on the deployment target environment variables, the access of which we want to move to later in the compilation pipeline that has access to more information, for example `env_depinfo`. --- compiler/rustc_codegen_cranelift/src/lib.rs | 5 +- compiler/rustc_codegen_llvm/src/back/write.rs | 3 +- compiler/rustc_codegen_llvm/src/context.rs | 3 +- compiler/rustc_codegen_ssa/src/back/apple.rs | 127 ++++++++++++++++++ .../rustc_codegen_ssa/src/back/apple/tests.rs | 21 +++ compiler/rustc_codegen_ssa/src/back/link.rs | 13 +- .../rustc_codegen_ssa/src/back/metadata.rs | 10 +- compiler/rustc_codegen_ssa/src/back/mod.rs | 21 +++ compiler/rustc_driver_impl/src/lib.rs | 5 +- .../rustc_target/src/spec/base/apple/mod.rs | 123 ++--------------- .../rustc_target/src/spec/base/apple/tests.rs | 9 -- compiler/rustc_target/src/spec/mod.rs | 12 +- 12 files changed, 208 insertions(+), 144 deletions(-) create mode 100644 compiler/rustc_codegen_ssa/src/back/apple.rs create mode 100644 compiler/rustc_codegen_ssa/src/back/apple/tests.rs diff --git a/compiler/rustc_codegen_cranelift/src/lib.rs b/compiler/rustc_codegen_cranelift/src/lib.rs index 602b1b98200..fc3bd0abd78 100644 --- a/compiler/rustc_codegen_cranelift/src/lib.rs +++ b/compiler/rustc_codegen_cranelift/src/lib.rs @@ -40,6 +40,7 @@ use std::sync::Arc; use cranelift_codegen::isa::TargetIsa; use cranelift_codegen::settings::{self, Configurable}; use rustc_codegen_ssa::CodegenResults; +use rustc_codegen_ssa::back::versioned_llvm_target; use rustc_codegen_ssa::traits::CodegenBackend; use rustc_data_structures::profiling::SelfProfilerRef; use rustc_errors::ErrorGuaranteed; @@ -260,7 +261,9 @@ impl CodegenBackend for CraneliftCodegenBackend { } fn target_triple(sess: &Session) -> target_lexicon::Triple { - match sess.target.llvm_target.parse() { + // FIXME(madsmtm): Use `sess.target.llvm_target` once target-lexicon supports unversioned macOS. + // See + match versioned_llvm_target(sess).parse() { Ok(triple) => triple, Err(err) => sess.dcx().fatal(format!("target not recognized: {}", err)), } diff --git a/compiler/rustc_codegen_llvm/src/back/write.rs b/compiler/rustc_codegen_llvm/src/back/write.rs index bfa9e8b82a0..6b0cf95eb85 100644 --- a/compiler/rustc_codegen_llvm/src/back/write.rs +++ b/compiler/rustc_codegen_llvm/src/back/write.rs @@ -9,6 +9,7 @@ use llvm::{ LLVMRustLLVMHasZlibCompressionForDebugSymbols, LLVMRustLLVMHasZstdCompressionForDebugSymbols, }; use rustc_codegen_ssa::back::link::ensure_removed; +use rustc_codegen_ssa::back::versioned_llvm_target; use rustc_codegen_ssa::back::write::{ BitcodeSection, CodegenContext, EmitObj, ModuleConfig, TargetMachineFactoryConfig, TargetMachineFactoryFn, @@ -211,7 +212,7 @@ pub(crate) fn target_machine_factory( singlethread = false; } - let triple = SmallCStr::new(&sess.target.llvm_target); + let triple = SmallCStr::new(&versioned_llvm_target(sess)); let cpu = SmallCStr::new(llvm_util::target_cpu(sess)); let features = CString::new(target_features.join(",")).unwrap(); let abi = SmallCStr::new(&sess.target.llvm_abiname); diff --git a/compiler/rustc_codegen_llvm/src/context.rs b/compiler/rustc_codegen_llvm/src/context.rs index 313957dda96..97a9f9c60e3 100644 --- a/compiler/rustc_codegen_llvm/src/context.rs +++ b/compiler/rustc_codegen_llvm/src/context.rs @@ -3,6 +3,7 @@ use std::cell::{Cell, RefCell}; use std::ffi::{CStr, c_uint}; use std::str; +use rustc_codegen_ssa::back::versioned_llvm_target; use rustc_codegen_ssa::base::{wants_msvc_seh, wants_wasm_eh}; use rustc_codegen_ssa::errors as ssa_errors; use rustc_codegen_ssa::traits::*; @@ -177,7 +178,7 @@ pub(crate) unsafe fn create_module<'ll>( llvm::LLVMSetDataLayout(llmod, data_layout.as_ptr()); } - let llvm_target = SmallCStr::new(&sess.target.llvm_target); + let llvm_target = SmallCStr::new(&versioned_llvm_target(sess)); unsafe { llvm::LLVMRustSetNormalizedTarget(llmod, llvm_target.as_ptr()); } diff --git a/compiler/rustc_codegen_ssa/src/back/apple.rs b/compiler/rustc_codegen_ssa/src/back/apple.rs new file mode 100644 index 00000000000..939ce2e1a03 --- /dev/null +++ b/compiler/rustc_codegen_ssa/src/back/apple.rs @@ -0,0 +1,127 @@ +use std::env; +use std::num::ParseIntError; + +use rustc_session::Session; +use rustc_target::spec::Target; + +#[cfg(test)] +mod tests; + +/// Deployment target or SDK version. +/// +/// The size of the numbers in here are limited by Mach-O's `LC_BUILD_VERSION`. +type OSVersion = (u16, u8, u8); + +/// Parse an OS version triple (SDK version or deployment target). +fn parse_version(version: &str) -> Result { + if let Some((major, minor)) = version.split_once('.') { + let major = major.parse()?; + if let Some((minor, patch)) = minor.split_once('.') { + Ok((major, minor.parse()?, patch.parse()?)) + } else { + Ok((major, minor.parse()?, 0)) + } + } else { + Ok((version.parse()?, 0, 0)) + } +} + +/// Minimum operating system versions currently supported by `rustc`. +fn os_minimum_deployment_target(os: &str) -> OSVersion { + // When bumping a version in here, remember to update the platform-support docs too. + // + // NOTE: The defaults may change in future `rustc` versions, so if you are looking for the + // default deployment target, prefer: + // ``` + // $ rustc --print deployment-target + // ``` + match os { + "macos" => (10, 12, 0), + "ios" => (10, 0, 0), + "tvos" => (10, 0, 0), + "watchos" => (5, 0, 0), + "visionos" => (1, 0, 0), + _ => unreachable!("tried to get deployment target for non-Apple platform"), + } +} + +/// The deployment target for the given target. +/// +/// This is similar to `os_minimum_deployment_target`, except that on certain targets it makes sense +/// to raise the minimum OS version. +/// +/// This matches what LLVM does, see in part: +/// +fn minimum_deployment_target(target: &Target) -> OSVersion { + match (&*target.os, &*target.arch, &*target.abi) { + ("macos", "aarch64", _) => (11, 0, 0), + ("ios", "aarch64", "macabi") => (14, 0, 0), + ("ios", "aarch64", "sim") => (14, 0, 0), + ("ios", _, _) if target.llvm_target.starts_with("arm64e") => (14, 0, 0), + // Mac Catalyst defaults to 13.1 in Clang. + ("ios", _, "macabi") => (13, 1, 0), + ("tvos", "aarch64", "sim") => (14, 0, 0), + ("watchos", "aarch64", "sim") => (7, 0, 0), + (os, _, _) => os_minimum_deployment_target(os), + } +} + +/// Name of the environment variable used to fetch the deployment target on the given OS. +fn deployment_target_env_var(os: &str) -> &'static str { + match os { + "macos" => "MACOSX_DEPLOYMENT_TARGET", + "ios" => "IPHONEOS_DEPLOYMENT_TARGET", + "watchos" => "WATCHOS_DEPLOYMENT_TARGET", + "tvos" => "TVOS_DEPLOYMENT_TARGET", + "visionos" => "XROS_DEPLOYMENT_TARGET", + _ => unreachable!("tried to get deployment target env var for non-Apple platform"), + } +} + +/// Get the deployment target based on the standard environment variables, or fall back to the +/// minimum version supported by `rustc`. +pub fn deployment_target(sess: &Session) -> OSVersion { + let min = minimum_deployment_target(&sess.target); + + if let Ok(deployment_target) = env::var(deployment_target_env_var(&sess.target.os)) { + match parse_version(&deployment_target) { + // It is common that the deployment target is set too low, e.g. on macOS Aarch64 to also + // target older x86_64, the user may set a lower deployment target than supported. + // + // To avoid such issues, we silently raise the deployment target here. + // FIXME: We want to show a warning when `version < os_min`. + Ok(version) => version.max(min), + // FIXME: Report erroneous environment variable to user. + Err(_) => min, + } + } else { + // If no deployment target variable is set, default to the minimum found above. + min + } +} + +pub(super) fn add_version_to_llvm_target( + llvm_target: &str, + deployment_target: OSVersion, +) -> String { + let mut components = llvm_target.split("-"); + let arch = components.next().expect("apple target should have arch"); + let vendor = components.next().expect("apple target should have vendor"); + let os = components.next().expect("apple target should have os"); + let environment = components.next(); + assert_eq!(components.next(), None, "too many LLVM triple components"); + + let (major, minor, patch) = deployment_target; + + assert!( + !os.contains(|c: char| c.is_ascii_digit()), + "LLVM target must not already be versioned" + ); + + if let Some(env) = environment { + // Insert version into OS, before environment + format!("{arch}-{vendor}-{os}{major}.{minor}.{patch}-{env}") + } else { + format!("{arch}-{vendor}-{os}{major}.{minor}.{patch}") + } +} diff --git a/compiler/rustc_codegen_ssa/src/back/apple/tests.rs b/compiler/rustc_codegen_ssa/src/back/apple/tests.rs new file mode 100644 index 00000000000..7ccda5a8190 --- /dev/null +++ b/compiler/rustc_codegen_ssa/src/back/apple/tests.rs @@ -0,0 +1,21 @@ +use super::{add_version_to_llvm_target, parse_version}; + +#[test] +fn test_add_version_to_llvm_target() { + assert_eq!( + add_version_to_llvm_target("aarch64-apple-macosx", (10, 14, 1)), + "aarch64-apple-macosx10.14.1" + ); + assert_eq!( + add_version_to_llvm_target("aarch64-apple-ios-simulator", (16, 1, 0)), + "aarch64-apple-ios16.1.0-simulator" + ); +} + +#[test] +fn test_parse_version() { + assert_eq!(parse_version("10"), Ok((10, 0, 0))); + assert_eq!(parse_version("10.12"), Ok((10, 12, 0))); + assert_eq!(parse_version("10.12.6"), Ok((10, 12, 6))); + assert_eq!(parse_version("9999.99.99"), Ok((9999, 99, 99))); +} diff --git a/compiler/rustc_codegen_ssa/src/back/link.rs b/compiler/rustc_codegen_ssa/src/back/link.rs index 34dc599e4fd..b01a62b394b 100644 --- a/compiler/rustc_codegen_ssa/src/back/link.rs +++ b/compiler/rustc_codegen_ssa/src/back/link.rs @@ -40,7 +40,7 @@ use rustc_target::spec::crt_objects::CrtObjects; use rustc_target::spec::{ Cc, LinkOutputKind, LinkSelfContainedComponents, LinkSelfContainedDefault, LinkerFeatures, LinkerFlavor, LinkerFlavorCli, Lld, PanicStrategy, RelocModel, RelroLevel, SanitizerSet, - SplitDebuginfo, current_apple_deployment_target, + SplitDebuginfo, }; use tempfile::Builder as TempFileBuilder; use tracing::{debug, info, warn}; @@ -50,6 +50,7 @@ use super::command::Command; use super::linker::{self, Linker}; use super::metadata::{MetadataPosition, create_wrapper_file}; use super::rpath::{self, RPathConfig}; +use super::{apple, versioned_llvm_target}; use crate::{ CodegenResults, CompiledModule, CrateInfo, NativeLib, common, errors, looks_like_rust_object_file, @@ -2447,7 +2448,7 @@ fn add_order_independent_options( if flavor == LinkerFlavor::Llbc { cmd.link_args(&[ "--target", - sess.target.llvm_target.as_ref(), + &versioned_llvm_target(sess), "--target-cpu", &codegen_results.crate_info.target_cpu, ]); @@ -3039,7 +3040,7 @@ fn add_apple_link_args(cmd: &mut dyn Linker, sess: &Session, flavor: LinkerFlavo _ => bug!("invalid OS/ABI combination for Apple target: {target_os}, {target_abi}"), }; - let (major, minor, patch) = current_apple_deployment_target(&sess.target); + let (major, minor, patch) = apple::deployment_target(sess); let min_version = format!("{major}.{minor}.{patch}"); // The SDK version is used at runtime when compiling with a newer SDK / version of Xcode: @@ -3109,7 +3110,7 @@ fn add_apple_link_args(cmd: &mut dyn Linker, sess: &Session, flavor: LinkerFlavo // The presence of `-mmacosx-version-min` makes CC default to // macOS, and it sets the deployment target. - let (major, minor, patch) = current_apple_deployment_target(&sess.target); + let (major, minor, patch) = apple::deployment_target(sess); // Intentionally pass this as a single argument, Clang doesn't // seem to like it otherwise. cmd.cc_arg(&format!("-mmacosx-version-min={major}.{minor}.{patch}")); @@ -3119,7 +3120,7 @@ fn add_apple_link_args(cmd: &mut dyn Linker, sess: &Session, flavor: LinkerFlavo // // We avoid `-m32`/`-m64`, as this is already encoded by `-arch`. } else { - cmd.cc_args(&["-target", &sess.target.llvm_target]); + cmd.cc_args(&["-target", &versioned_llvm_target(sess)]); } } } @@ -3345,7 +3346,7 @@ fn add_lld_args( // targeting a different linker flavor on macOS, and that's also always // the case when targeting WASM. if sess.target.linker_flavor != sess.host.linker_flavor { - cmd.cc_arg(format!("--target={}", sess.target.llvm_target)); + cmd.cc_arg(format!("--target={}", versioned_llvm_target(sess))); } } } diff --git a/compiler/rustc_codegen_ssa/src/back/metadata.rs b/compiler/rustc_codegen_ssa/src/back/metadata.rs index 4c25c85569b..1b11fe661db 100644 --- a/compiler/rustc_codegen_ssa/src/back/metadata.rs +++ b/compiler/rustc_codegen_ssa/src/back/metadata.rs @@ -22,6 +22,8 @@ use rustc_span::sym; use rustc_target::abi::Endian; use rustc_target::spec::{RelocModel, Target, ef_avr_arch}; +use super::apple; + /// The default metadata loader. This is used by cg_llvm and cg_clif. /// /// # Metadata location @@ -238,7 +240,7 @@ pub(crate) fn create_object_file(sess: &Session) -> Option Option object::write::MachOBuildVersion { +fn macho_object_build_version_for_target(sess: &Session) -> object::write::MachOBuildVersion { /// The `object` crate demands "X.Y.Z encoded in nibbles as xxxx.yy.zz" /// e.g. minOS 14.0 = 0x000E0000, or SDK 16.2 = 0x00100200 fn pack_version((major, minor, patch): (u16, u8, u8)) -> u32 { @@ -401,8 +403,8 @@ fn macho_object_build_version_for_target(target: &Target) -> object::write::Mach } let platform = - rustc_target::spec::current_apple_platform(target).expect("unknown Apple target OS"); - let min_os = rustc_target::spec::current_apple_deployment_target(target); + rustc_target::spec::current_apple_platform(&sess.target).expect("unknown Apple target OS"); + let min_os = apple::deployment_target(sess); let mut build_version = object::write::MachOBuildVersion::default(); build_version.platform = platform; diff --git a/compiler/rustc_codegen_ssa/src/back/mod.rs b/compiler/rustc_codegen_ssa/src/back/mod.rs index 2b3a2e3a369..64b5d4569ec 100644 --- a/compiler/rustc_codegen_ssa/src/back/mod.rs +++ b/compiler/rustc_codegen_ssa/src/back/mod.rs @@ -1,3 +1,8 @@ +use std::borrow::Cow; + +use rustc_session::Session; + +pub mod apple; pub mod archive; pub(crate) mod command; pub mod link; @@ -7,3 +12,19 @@ pub mod metadata; pub(crate) mod rpath; pub mod symbol_export; pub mod write; + +/// The target triple depends on the deployment target, and is required to +/// enable features such as cross-language LTO, and for picking the right +/// Mach-O commands. +/// +/// Certain optimizations also depend on the deployment target. +pub fn versioned_llvm_target(sess: &Session) -> Cow<'_, str> { + if sess.target.is_like_osx { + apple::add_version_to_llvm_target(&sess.target.llvm_target, apple::deployment_target(sess)) + .into() + } else { + // FIXME(madsmtm): Certain other targets also include a version, + // we might want to move that here as well. + Cow::Borrowed(&sess.target.llvm_target) + } +} diff --git a/compiler/rustc_driver_impl/src/lib.rs b/compiler/rustc_driver_impl/src/lib.rs index e2585c02388..06b4c89946d 100644 --- a/compiler/rustc_driver_impl/src/lib.rs +++ b/compiler/rustc_driver_impl/src/lib.rs @@ -33,6 +33,7 @@ use std::time::{Instant, SystemTime}; use std::{env, str}; use rustc_ast as ast; +use rustc_codegen_ssa::back::apple; use rustc_codegen_ssa::traits::CodegenBackend; use rustc_codegen_ssa::{CodegenErrors, CodegenResults}; use rustc_data_structures::profiling::{ @@ -855,10 +856,8 @@ fn print_crate_info( } } DeploymentTarget => { - use rustc_target::spec::current_apple_deployment_target; - if sess.target.is_like_osx { - let (major, minor, patch) = current_apple_deployment_target(&sess.target); + let (major, minor, patch) = apple::deployment_target(sess); let patch = if patch != 0 { format!(".{patch}") } else { String::new() }; println_info!("deployment_target={major}.{minor}{patch}") } else { diff --git a/compiler/rustc_target/src/spec/base/apple/mod.rs b/compiler/rustc_target/src/spec/base/apple/mod.rs index 73763cf034c..837af954a07 100644 --- a/compiler/rustc_target/src/spec/base/apple/mod.rs +++ b/compiler/rustc_target/src/spec/base/apple/mod.rs @@ -1,6 +1,5 @@ use std::borrow::Cow; use std::env; -use std::num::ParseIntError; use crate::spec::{ Cc, DebuginfoKind, FramePointer, LinkerFlavor, Lld, SplitDebuginfo, StackProbeType, StaticCow, @@ -97,9 +96,8 @@ impl TargetAbi { } } -/// Get the base target options, LLVM target and `target_arch` from the three -/// things that uniquely identify Rust's Apple targets: The OS, the -/// architecture, and the ABI. +/// Get the base target options, unversioned LLVM target and `target_arch` from the three +/// things that uniquely identify Rust's Apple targets: The OS, the architecture, and the ABI. pub(crate) fn base( os: &'static str, arch: Arch, @@ -155,7 +153,7 @@ pub(crate) fn base( ..Default::default() }; - (opts, llvm_target(os, arch, abi), arch.target_arch()) + (opts, unversioned_llvm_target(os, arch, abi), arch.target_arch()) } pub fn platform(target: &Target) -> Option { @@ -175,97 +173,11 @@ pub fn platform(target: &Target) -> Option { }) } -/// Hack for calling `deployment_target` outside of this module. -pub fn deployment_target_for_target(target: &Target) -> (u16, u8, u8) { - let arch = if target.llvm_target.starts_with("arm64e") { - Arch::Arm64e - } else if target.arch == "aarch64" { - Arch::Arm64 - } else { - // Dummy architecture, only used by `deployment_target` anyhow - Arch::X86_64 - }; - let abi = match &*target.abi { - "macabi" => TargetAbi::MacCatalyst, - "sim" => TargetAbi::Simulator, - "" => TargetAbi::Normal, - abi => unreachable!("invalid abi '{abi}' for Apple target"), - }; - deployment_target(&target.os, arch, abi) -} - -/// Get the deployment target based on the standard environment variables, or -/// fall back to a sane default. -fn deployment_target(os: &str, arch: Arch, abi: TargetAbi) -> (u16, u8, u8) { - // When bumping a version in here, remember to update the platform-support - // docs too. - // - // NOTE: If you are looking for the default deployment target, prefer - // `rustc --print deployment-target`, as the default here may change in - // future `rustc` versions. - - // Minimum operating system versions currently supported by `rustc`. - let os_min = match os { - "macos" => (10, 12, 0), - "ios" => (10, 0, 0), - "tvos" => (10, 0, 0), - "watchos" => (5, 0, 0), - "visionos" => (1, 0, 0), - _ => unreachable!("tried to get deployment target for non-Apple platform"), - }; - - // On certain targets it makes sense to raise the minimum OS version. - // - // This matches what LLVM does, see: - // - let min = match (os, arch, abi) { - ("macos", Arch::Arm64 | Arch::Arm64e, _) => (11, 0, 0), - ("ios", Arch::Arm64 | Arch::Arm64e, TargetAbi::MacCatalyst) => (14, 0, 0), - ("ios", Arch::Arm64 | Arch::Arm64e, TargetAbi::Simulator) => (14, 0, 0), - ("ios", Arch::Arm64e, TargetAbi::Normal) => (14, 0, 0), - // Mac Catalyst defaults to 13.1 in Clang. - ("ios", _, TargetAbi::MacCatalyst) => (13, 1, 0), - ("tvos", Arch::Arm64 | Arch::Arm64e, TargetAbi::Simulator) => (14, 0, 0), - ("watchos", Arch::Arm64 | Arch::Arm64e, TargetAbi::Simulator) => (7, 0, 0), - _ => os_min, - }; - - // The environment variable used to fetch the deployment target. - let env_var = match os { - "macos" => "MACOSX_DEPLOYMENT_TARGET", - "ios" => "IPHONEOS_DEPLOYMENT_TARGET", - "watchos" => "WATCHOS_DEPLOYMENT_TARGET", - "tvos" => "TVOS_DEPLOYMENT_TARGET", - "visionos" => "XROS_DEPLOYMENT_TARGET", - _ => unreachable!("tried to get deployment target env var for non-Apple platform"), - }; - - if let Ok(deployment_target) = env::var(env_var) { - match parse_version(&deployment_target) { - // It is common that the deployment target is set too low, e.g. on - // macOS Aarch64 to also target older x86_64, the user may set a - // lower deployment target than supported. - // - // To avoid such issues, we silently raise the deployment target - // here. - // FIXME: We want to show a warning when `version < os_min`. - Ok(version) => version.max(min), - // FIXME: Report erroneous environment variable to user. - Err(_) => min, - } - } else { - min - } -} - -/// Generate the target triple that we need to pass to LLVM and/or Clang. -fn llvm_target(os: &str, arch: Arch, abi: TargetAbi) -> StaticCow { - // The target triple depends on the deployment target, and is required to - // enable features such as cross-language LTO, and for picking the right - // Mach-O commands. - // - // Certain optimizations also depend on the deployment target. - let (major, minor, patch) = deployment_target(os, arch, abi); +/// Generate part of the LLVM target triple. +/// +/// See `rustc_codegen_ssa::back::versioned_llvm_target` for the full triple passed to LLVM and +/// Clang. +fn unversioned_llvm_target(os: &str, arch: Arch, abi: TargetAbi) -> StaticCow { let arch = arch.target_name(); // Convert to the "canonical" OS name used by LLVM: // https://github.com/llvm/llvm-project/blob/llvmorg-18.1.8/llvm/lib/TargetParser/Triple.cpp#L236-L282 @@ -282,7 +194,7 @@ fn llvm_target(os: &str, arch: Arch, abi: TargetAbi) -> StaticCow { TargetAbi::MacCatalyst => "-macabi", TargetAbi::Simulator => "-simulator", }; - format!("{arch}-apple-{os}{major}.{minor}.{patch}{environment}").into() + format!("{arch}-apple-{os}{environment}").into() } fn link_env_remove(os: &'static str) -> StaticCow<[StaticCow]> { @@ -321,20 +233,3 @@ fn link_env_remove(os: &'static str) -> StaticCow<[StaticCow]> { cvs!["MACOSX_DEPLOYMENT_TARGET"] } } - -/// Parse an OS version triple (SDK version or deployment target). -/// -/// The size of the returned numbers here are limited by Mach-O's -/// `LC_BUILD_VERSION`. -fn parse_version(version: &str) -> Result<(u16, u8, u8), ParseIntError> { - if let Some((major, minor)) = version.split_once('.') { - let major = major.parse()?; - if let Some((minor, patch)) = minor.split_once('.') { - Ok((major, minor.parse()?, patch.parse()?)) - } else { - Ok((major, minor.parse()?, 0)) - } - } else { - Ok((version.parse()?, 0, 0)) - } -} diff --git a/compiler/rustc_target/src/spec/base/apple/tests.rs b/compiler/rustc_target/src/spec/base/apple/tests.rs index 9435b9a5bad..a7335c9bcae 100644 --- a/compiler/rustc_target/src/spec/base/apple/tests.rs +++ b/compiler/rustc_target/src/spec/base/apple/tests.rs @@ -1,4 +1,3 @@ -use super::parse_version; use crate::spec::targets::{ aarch64_apple_darwin, aarch64_apple_ios_sim, aarch64_apple_visionos_sim, aarch64_apple_watchos_sim, i686_apple_darwin, x86_64_apple_darwin, x86_64_apple_ios, @@ -40,11 +39,3 @@ fn macos_link_environment_unmodified() { ],); } } - -#[test] -fn test_parse_version() { - assert_eq!(parse_version("10"), Ok((10, 0, 0))); - assert_eq!(parse_version("10.12"), Ok((10, 12, 0))); - assert_eq!(parse_version("10.12.6"), Ok((10, 12, 6))); - assert_eq!(parse_version("9999.99.99"), Ok((9999, 99, 99))); -} diff --git a/compiler/rustc_target/src/spec/mod.rs b/compiler/rustc_target/src/spec/mod.rs index f4cbe47e0f3..1265cc34549 100644 --- a/compiler/rustc_target/src/spec/mod.rs +++ b/compiler/rustc_target/src/spec/mod.rs @@ -59,10 +59,7 @@ pub mod abi; pub mod crt_objects; mod base; -pub use base::apple::{ - deployment_target_for_target as current_apple_deployment_target, - platform as current_apple_platform, -}; +pub use base::apple::platform as current_apple_platform; pub use base::avr_gnu::ef_avr_arch; /// Linker is called through a C/C++ compiler. @@ -2003,7 +2000,12 @@ impl TargetWarnings { /// Every field here must be specified, and has no default value. #[derive(PartialEq, Clone, Debug)] pub struct Target { - /// Target triple to pass to LLVM. + /// Unversioned target triple to pass to LLVM. + /// + /// Target triples can optionally contain an OS version (notably Apple targets), which rustc + /// cannot know without querying the environment. + /// + /// Use `rustc_codegen_ssa::back::versioned_llvm_target` if you need the full LLVM target. pub llvm_target: StaticCow, /// Metadata about a target, for example the description or tier. /// Used for generating target documentation. From e75a7ddad37feea205df1e4b568a5316b31da641 Mon Sep 17 00:00:00 2001 From: Mads Marquart Date: Fri, 1 Nov 2024 17:05:10 +0100 Subject: [PATCH 07/16] Move Mach-O platform information to rustc_codegen_ssa::back::apple To align with the general decision to have this sort of information there instead. Also use the visionOS values added in newer `object` release. --- compiler/rustc_codegen_ssa/src/back/apple.rs | 16 ++++++++++++++++ .../rustc_codegen_ssa/src/back/metadata.rs | 3 +-- .../rustc_target/src/spec/base/apple/mod.rs | 19 +------------------ compiler/rustc_target/src/spec/mod.rs | 1 - 4 files changed, 18 insertions(+), 21 deletions(-) diff --git a/compiler/rustc_codegen_ssa/src/back/apple.rs b/compiler/rustc_codegen_ssa/src/back/apple.rs index 939ce2e1a03..23460ae9e1e 100644 --- a/compiler/rustc_codegen_ssa/src/back/apple.rs +++ b/compiler/rustc_codegen_ssa/src/back/apple.rs @@ -7,6 +7,22 @@ use rustc_target::spec::Target; #[cfg(test)] mod tests; +pub(super) fn macho_platform(target: &Target) -> u32 { + match (&*target.os, &*target.abi) { + ("macos", _) => object::macho::PLATFORM_MACOS, + ("ios", "macabi") => object::macho::PLATFORM_MACCATALYST, + ("ios", "sim") => object::macho::PLATFORM_IOSSIMULATOR, + ("ios", _) => object::macho::PLATFORM_IOS, + ("watchos", "sim") => object::macho::PLATFORM_WATCHOSSIMULATOR, + ("watchos", _) => object::macho::PLATFORM_WATCHOS, + ("tvos", "sim") => object::macho::PLATFORM_TVOSSIMULATOR, + ("tvos", _) => object::macho::PLATFORM_TVOS, + ("visionos", "sim") => object::macho::PLATFORM_XROSSIMULATOR, + ("visionos", _) => object::macho::PLATFORM_XROS, + _ => unreachable!("tried to get Mach-O platform for non-Apple target"), + } +} + /// Deployment target or SDK version. /// /// The size of the numbers in here are limited by Mach-O's `LC_BUILD_VERSION`. diff --git a/compiler/rustc_codegen_ssa/src/back/metadata.rs b/compiler/rustc_codegen_ssa/src/back/metadata.rs index 1b11fe661db..5544f8d40c9 100644 --- a/compiler/rustc_codegen_ssa/src/back/metadata.rs +++ b/compiler/rustc_codegen_ssa/src/back/metadata.rs @@ -402,8 +402,7 @@ fn macho_object_build_version_for_target(sess: &Session) -> object::write::MachO (major << 16) | (minor << 8) | patch } - let platform = - rustc_target::spec::current_apple_platform(&sess.target).expect("unknown Apple target OS"); + let platform = apple::macho_platform(&sess.target); let min_os = apple::deployment_target(sess); let mut build_version = object::write::MachOBuildVersion::default(); diff --git a/compiler/rustc_target/src/spec/base/apple/mod.rs b/compiler/rustc_target/src/spec/base/apple/mod.rs index 837af954a07..f45c8664093 100644 --- a/compiler/rustc_target/src/spec/base/apple/mod.rs +++ b/compiler/rustc_target/src/spec/base/apple/mod.rs @@ -3,7 +3,7 @@ use std::env; use crate::spec::{ Cc, DebuginfoKind, FramePointer, LinkerFlavor, Lld, SplitDebuginfo, StackProbeType, StaticCow, - Target, TargetOptions, cvs, + TargetOptions, cvs, }; #[cfg(test)] @@ -156,23 +156,6 @@ pub(crate) fn base( (opts, unversioned_llvm_target(os, arch, abi), arch.target_arch()) } -pub fn platform(target: &Target) -> Option { - Some(match (&*target.os, &*target.abi) { - ("macos", _) => object::macho::PLATFORM_MACOS, - ("ios", "macabi") => object::macho::PLATFORM_MACCATALYST, - ("ios", "sim") => object::macho::PLATFORM_IOSSIMULATOR, - ("ios", _) => object::macho::PLATFORM_IOS, - ("watchos", "sim") => object::macho::PLATFORM_WATCHOSSIMULATOR, - ("watchos", _) => object::macho::PLATFORM_WATCHOS, - ("tvos", "sim") => object::macho::PLATFORM_TVOSSIMULATOR, - ("tvos", _) => object::macho::PLATFORM_TVOS, - // FIXME: Upgrade to `object-rs` 0.33+ implementation with visionOS platform definition - ("visionos", "sim") => 12, - ("visionos", _) => 11, - _ => return None, - }) -} - /// Generate part of the LLVM target triple. /// /// See `rustc_codegen_ssa::back::versioned_llvm_target` for the full triple passed to LLVM and diff --git a/compiler/rustc_target/src/spec/mod.rs b/compiler/rustc_target/src/spec/mod.rs index 1265cc34549..a5bc90477b3 100644 --- a/compiler/rustc_target/src/spec/mod.rs +++ b/compiler/rustc_target/src/spec/mod.rs @@ -59,7 +59,6 @@ pub mod abi; pub mod crt_objects; mod base; -pub use base::apple::platform as current_apple_platform; pub use base::avr_gnu::ef_avr_arch; /// Linker is called through a C/C++ compiler. From 1ef1af1c607fe268b5622041ff586ca603b8ec8d Mon Sep 17 00:00:00 2001 From: Mads Marquart Date: Sun, 29 Sep 2024 22:14:55 +0200 Subject: [PATCH 08/16] Emit diagnostics for incorrect deployment targets --- compiler/rustc_codegen_ssa/messages.ftl | 6 +++ compiler/rustc_codegen_ssa/src/back/apple.rs | 46 ++++++++++++++++---- compiler/rustc_codegen_ssa/src/errors.rs | 9 ++++ compiler/rustc_codegen_ssa/src/lib.rs | 1 + compiler/rustc_driver_impl/src/lib.rs | 7 +-- 5 files changed, 57 insertions(+), 12 deletions(-) diff --git a/compiler/rustc_codegen_ssa/messages.ftl b/compiler/rustc_codegen_ssa/messages.ftl index d07274920fe..3b34eb063ec 100644 --- a/compiler/rustc_codegen_ssa/messages.ftl +++ b/compiler/rustc_codegen_ssa/messages.ftl @@ -2,6 +2,12 @@ codegen_ssa_L4Bender_exporting_symbols_unimplemented = exporting symbols not imp codegen_ssa_add_native_library = failed to add native library {$library_path}: {$error} +codegen_ssa_apple_deployment_target_invalid = + failed to parse deployment target specified in {$env_var}: {$error} + +codegen_ssa_apple_deployment_target_too_low = + deployment target in {$env_var} was set to {$version}, but the minimum supported by `rustc` is {$os_min} + codegen_ssa_apple_sdk_error_sdk_path = failed to get {$sdk_name} SDK path: {$error} codegen_ssa_archive_build_failure = failed to build archive at `{$path}`: {$error} diff --git a/compiler/rustc_codegen_ssa/src/back/apple.rs b/compiler/rustc_codegen_ssa/src/back/apple.rs index 23460ae9e1e..93d90cd16b2 100644 --- a/compiler/rustc_codegen_ssa/src/back/apple.rs +++ b/compiler/rustc_codegen_ssa/src/back/apple.rs @@ -1,9 +1,12 @@ use std::env; +use std::fmt::{Display, from_fn}; use std::num::ParseIntError; use rustc_session::Session; use rustc_target::spec::Target; +use crate::errors::AppleDeploymentTarget; + #[cfg(test)] mod tests; @@ -42,6 +45,17 @@ fn parse_version(version: &str) -> Result { } } +pub fn pretty_version(version: OSVersion) -> impl Display { + let (major, minor, patch) = version; + from_fn(move |f| { + write!(f, "{major}.{minor}")?; + if patch != 0 { + write!(f, ".{patch}")?; + } + Ok(()) + }) +} + /// Minimum operating system versions currently supported by `rustc`. fn os_minimum_deployment_target(os: &str) -> OSVersion { // When bumping a version in here, remember to update the platform-support docs too. @@ -98,17 +112,31 @@ fn deployment_target_env_var(os: &str) -> &'static str { /// minimum version supported by `rustc`. pub fn deployment_target(sess: &Session) -> OSVersion { let min = minimum_deployment_target(&sess.target); + let env_var = deployment_target_env_var(&sess.target.os); - if let Ok(deployment_target) = env::var(deployment_target_env_var(&sess.target.os)) { + if let Ok(deployment_target) = env::var(env_var) { match parse_version(&deployment_target) { - // It is common that the deployment target is set too low, e.g. on macOS Aarch64 to also - // target older x86_64, the user may set a lower deployment target than supported. - // - // To avoid such issues, we silently raise the deployment target here. - // FIXME: We want to show a warning when `version < os_min`. - Ok(version) => version.max(min), - // FIXME: Report erroneous environment variable to user. - Err(_) => min, + Ok(version) => { + let os_min = os_minimum_deployment_target(&sess.target.os); + // It is common that the deployment target is set a bit too low, for example on + // macOS Aarch64 to also target older x86_64. So we only want to warn when variable + // is lower than the minimum OS supported by rustc, not when the variable is lower + // than the minimum for a specific target. + if version < os_min { + sess.dcx().emit_warn(AppleDeploymentTarget::TooLow { + env_var, + version: pretty_version(version).to_string(), + os_min: pretty_version(os_min).to_string(), + }); + } + + // Raise the deployment target to the minimum supported. + version.max(min) + } + Err(error) => { + sess.dcx().emit_err(AppleDeploymentTarget::Invalid { env_var, error }); + min + } } } else { // If no deployment target variable is set, default to the minimum found above. diff --git a/compiler/rustc_codegen_ssa/src/errors.rs b/compiler/rustc_codegen_ssa/src/errors.rs index d67cf0e3a6d..cf8d1cfa0d1 100644 --- a/compiler/rustc_codegen_ssa/src/errors.rs +++ b/compiler/rustc_codegen_ssa/src/errors.rs @@ -2,6 +2,7 @@ use std::borrow::Cow; use std::io::Error; +use std::num::ParseIntError; use std::path::{Path, PathBuf}; use std::process::ExitStatus; @@ -539,6 +540,14 @@ pub(crate) struct UnsupportedArch<'a> { pub os: &'a str, } +#[derive(Diagnostic)] +pub(crate) enum AppleDeploymentTarget { + #[diag(codegen_ssa_apple_deployment_target_invalid)] + Invalid { env_var: &'static str, error: ParseIntError }, + #[diag(codegen_ssa_apple_deployment_target_too_low)] + TooLow { env_var: &'static str, version: String, os_min: String }, +} + #[derive(Diagnostic)] pub(crate) enum AppleSdkRootError<'a> { #[diag(codegen_ssa_apple_sdk_error_sdk_path)] diff --git a/compiler/rustc_codegen_ssa/src/lib.rs b/compiler/rustc_codegen_ssa/src/lib.rs index 73bfa9dbd10..7dc8ab38a97 100644 --- a/compiler/rustc_codegen_ssa/src/lib.rs +++ b/compiler/rustc_codegen_ssa/src/lib.rs @@ -6,6 +6,7 @@ #![doc(rust_logo)] #![feature(assert_matches)] #![feature(box_patterns)] +#![feature(debug_closure_helpers)] #![feature(file_buffered)] #![feature(if_let_guard)] #![feature(let_chains)] diff --git a/compiler/rustc_driver_impl/src/lib.rs b/compiler/rustc_driver_impl/src/lib.rs index 06b4c89946d..92b622fccf2 100644 --- a/compiler/rustc_driver_impl/src/lib.rs +++ b/compiler/rustc_driver_impl/src/lib.rs @@ -857,9 +857,10 @@ fn print_crate_info( } DeploymentTarget => { if sess.target.is_like_osx { - let (major, minor, patch) = apple::deployment_target(sess); - let patch = if patch != 0 { format!(".{patch}") } else { String::new() }; - println_info!("deployment_target={major}.{minor}{patch}") + println_info!( + "deployment_target={}", + apple::pretty_version(apple::deployment_target(sess)) + ) } else { #[allow(rustc::diagnostic_outside_of_impl)] sess.dcx().fatal("only Apple targets currently support deployment version info") From 45d44650280951c22ba625d0000d36216babb397 Mon Sep 17 00:00:00 2001 From: Camille GILLOT Date: Fri, 1 Nov 2024 17:03:17 +0000 Subject: [PATCH 09/16] Account for late-bound depth when capturing all opaque lifetimes. --- .../src/collect/resolve_bound_vars.rs | 9 +++++- .../in-trait/late-bound-in-object-assocty.rs | 13 ++++++++ .../late-bound-in-object-assocty.stderr | 32 +++++++++++++++++++ 3 files changed, 53 insertions(+), 1 deletion(-) create mode 100644 tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.rs create mode 100644 tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.stderr diff --git a/compiler/rustc_hir_analysis/src/collect/resolve_bound_vars.rs b/compiler/rustc_hir_analysis/src/collect/resolve_bound_vars.rs index 9483439ae4e..6fd0535a28b 100644 --- a/compiler/rustc_hir_analysis/src/collect/resolve_bound_vars.rs +++ b/compiler/rustc_hir_analysis/src/collect/resolve_bound_vars.rs @@ -571,17 +571,23 @@ impl<'a, 'tcx> Visitor<'tcx> for BoundVarContext<'a, 'tcx> { // We list scopes outwards, this causes us to see lifetime parameters in reverse // declaration order. In order to make it consistent with what `generics_of` might // give, we will reverse the IndexMap after early captures. + let mut late_depth = 0; let mut scope = self.scope; let mut opaque_capture_scopes = vec![(opaque.def_id, &captures)]; loop { match *scope { - Scope::Binder { ref bound_vars, s, .. } => { + Scope::Binder { ref bound_vars, scope_type, s, .. } => { for (&original_lifetime, &def) in bound_vars.iter().rev() { if let DefKind::LifetimeParam = self.tcx.def_kind(original_lifetime) { + let def = def.shifted(late_depth); let ident = lifetime_ident(original_lifetime); self.remap_opaque_captures(&opaque_capture_scopes, def, ident); } } + match scope_type { + BinderScopeType::Normal => late_depth += 1, + BinderScopeType::Concatenating => {} + } scope = s; } @@ -602,6 +608,7 @@ impl<'a, 'tcx> Visitor<'tcx> for BoundVarContext<'a, 'tcx> { Scope::Opaque { captures, def_id, s } => { opaque_capture_scopes.push((def_id, captures)); + late_depth = 0; scope = s; } diff --git a/tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.rs b/tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.rs new file mode 100644 index 00000000000..9d1bb22434c --- /dev/null +++ b/tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.rs @@ -0,0 +1,13 @@ +// Test for issue #132429 +//@compile-flags: -Zunstable-options --edition=2024 + +trait ThreeCellFragment { + fn ext_cells<'a>( + &'a self, + ) -> dyn core::future::Future> + 'a { + //~^ ERROR mismatched types + //~| ERROR return type cannot have an unboxed trait object + } +} + +fn main() {} diff --git a/tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.stderr b/tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.stderr new file mode 100644 index 00000000000..f771b802af9 --- /dev/null +++ b/tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.stderr @@ -0,0 +1,32 @@ +error[E0308]: mismatched types + --> $DIR/late-bound-in-object-assocty.rs:7:80 + | +LL | ) -> dyn core::future::Future> + 'a { + | ________________________________________________________________________________^ +LL | | +LL | | +LL | | } + | |_____^ expected `dyn Future`, found `()` + | + = note: expected trait object `(dyn Future + 'a)` + found unit type `()` + +error[E0746]: return type cannot have an unboxed trait object + --> $DIR/late-bound-in-object-assocty.rs:7:10 + | +LL | ) -> dyn core::future::Future> + 'a { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time + | +help: consider returning an `impl Trait` instead of a `dyn Trait` + | +LL | ) -> impl core::future::Future> + 'a { + | ~~~~ +help: alternatively, box the return type, and wrap all of the returned values in `Box::new` + | +LL | ) -> Box> + 'a> { + | ++++ + + +error: aborting due to 2 previous errors + +Some errors have detailed explanations: E0308, E0746. +For more information about an error, try `rustc --explain E0308`. From e169483879e73141bec00004c3c68eaa9652423b Mon Sep 17 00:00:00 2001 From: ismailarilik Date: Fri, 1 Nov 2024 20:19:01 +0300 Subject: [PATCH 10/16] refactor(config): remove FIXME statement in comment of `omit-git-hash` It is already fixed. --- config.example.toml | 2 -- 1 file changed, 2 deletions(-) diff --git a/config.example.toml b/config.example.toml index 9072a83551a..cd7ec6a05bc 100644 --- a/config.example.toml +++ b/config.example.toml @@ -668,8 +668,6 @@ # Flag indicating whether git info will be retrieved from .git automatically. # Having the git information can cause a lot of rebuilds during development. -# -# FIXME(#76720): this can causes bugs if different compilers reuse the same metadata cache. #omit-git-hash = if rust.channel == "dev" { true } else { false } # Whether to create a source tarball by default when running `x dist`. From a7f609504c92c9912b61025ae26a5404d3ee4311 Mon Sep 17 00:00:00 2001 From: Camille GILLOT Date: Fri, 1 Nov 2024 17:42:14 +0000 Subject: [PATCH 11/16] Skip late-bound lifetimes when crossing an AnonConst. --- .../src/collect/resolve_bound_vars.rs | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-) diff --git a/compiler/rustc_hir_analysis/src/collect/resolve_bound_vars.rs b/compiler/rustc_hir_analysis/src/collect/resolve_bound_vars.rs index 6fd0535a28b..dc3ef9952f0 100644 --- a/compiler/rustc_hir_analysis/src/collect/resolve_bound_vars.rs +++ b/compiler/rustc_hir_analysis/src/collect/resolve_bound_vars.rs @@ -573,11 +573,17 @@ impl<'a, 'tcx> Visitor<'tcx> for BoundVarContext<'a, 'tcx> { // give, we will reverse the IndexMap after early captures. let mut late_depth = 0; let mut scope = self.scope; + let mut crossed_late_boundary = None; let mut opaque_capture_scopes = vec![(opaque.def_id, &captures)]; loop { match *scope { Scope::Binder { ref bound_vars, scope_type, s, .. } => { for (&original_lifetime, &def) in bound_vars.iter().rev() { + if let ResolvedArg::LateBound(..) = def + && crossed_late_boundary.is_some() + { + continue; + } if let DefKind::LifetimeParam = self.tcx.def_kind(original_lifetime) { let def = def.shifted(late_depth); let ident = lifetime_ident(original_lifetime); @@ -618,8 +624,12 @@ impl<'a, 'tcx> Visitor<'tcx> for BoundVarContext<'a, 'tcx> { Scope::ObjectLifetimeDefault { s, .. } | Scope::Supertrait { s, .. } - | Scope::TraitRefBoundary { s, .. } - | Scope::LateBoundary { s, .. } => { + | Scope::TraitRefBoundary { s, .. } => { + scope = s; + } + + Scope::LateBoundary { s, what, .. } => { + crossed_late_boundary = Some(what); scope = s; } } From e2a50de5f4cda9958f910ee86a05c46e81767a32 Mon Sep 17 00:00:00 2001 From: Camille GILLOT Date: Fri, 1 Nov 2024 18:00:36 +0000 Subject: [PATCH 12/16] Use more minimized test. --- .../in-trait/late-bound-in-object-assocty.rs | 12 +++---- .../late-bound-in-object-assocty.stderr | 32 ------------------- 2 files changed, 6 insertions(+), 38 deletions(-) delete mode 100644 tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.stderr diff --git a/tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.rs b/tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.rs index 9d1bb22434c..83466535e13 100644 --- a/tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.rs +++ b/tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.rs @@ -1,12 +1,12 @@ // Test for issue #132429 //@compile-flags: -Zunstable-options --edition=2024 +//@check-pass -trait ThreeCellFragment { - fn ext_cells<'a>( - &'a self, - ) -> dyn core::future::Future> + 'a { - //~^ ERROR mismatched types - //~| ERROR return type cannot have an unboxed trait object +use std::future::Future; + +trait Test { + fn foo<'a>(&'a self) -> Box>> { + Box::new(async { [] }) } } diff --git a/tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.stderr b/tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.stderr deleted file mode 100644 index f771b802af9..00000000000 --- a/tests/ui/impl-trait/in-trait/late-bound-in-object-assocty.stderr +++ /dev/null @@ -1,32 +0,0 @@ -error[E0308]: mismatched types - --> $DIR/late-bound-in-object-assocty.rs:7:80 - | -LL | ) -> dyn core::future::Future> + 'a { - | ________________________________________________________________________________^ -LL | | -LL | | -LL | | } - | |_____^ expected `dyn Future`, found `()` - | - = note: expected trait object `(dyn Future + 'a)` - found unit type `()` - -error[E0746]: return type cannot have an unboxed trait object - --> $DIR/late-bound-in-object-assocty.rs:7:10 - | -LL | ) -> dyn core::future::Future> + 'a { - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time - | -help: consider returning an `impl Trait` instead of a `dyn Trait` - | -LL | ) -> impl core::future::Future> + 'a { - | ~~~~ -help: alternatively, box the return type, and wrap all of the returned values in `Box::new` - | -LL | ) -> Box> + 'a> { - | ++++ + - -error: aborting due to 2 previous errors - -Some errors have detailed explanations: E0308, E0746. -For more information about an error, try `rustc --explain E0308`. From e4305f16570efc342529e35c7b0ec5b1ca50b954 Mon Sep 17 00:00:00 2001 From: Noratrieb <48135649+Noratrieb@users.noreply.github.com> Date: Fri, 1 Nov 2024 20:10:36 +0100 Subject: [PATCH 13/16] Add a bunch of mailmap entries This adds a bunch of missing mailmap entries for many people. These are needed when using rust-lang/team information in rust-lang/thanks, as the emails there may differ. These are all the "easy" ones, where there was a mailmap entry already, making it clear which one is the preferred email address. --- .mailmap | 22 ++++++++++++++++++++-- 1 file changed, 20 insertions(+), 2 deletions(-) diff --git a/.mailmap b/.mailmap index 56490ca5059..fdb62a9d778 100644 --- a/.mailmap +++ b/.mailmap @@ -31,6 +31,7 @@ Alexis Beingessner Alfie John Alfie John Alona Enraght-Moony Alona Enraght-Moony +Alona Enraght-Moony Amanda Stjerna Amanda Stjerna Amos Onn @@ -75,6 +76,7 @@ Benjamin Jackman Benoît Cortier Bheesham Persaud Bheesham Persaud bjorn3 <17426603+bjorn3@users.noreply.github.com> +bjorn3 <17426603+bjorn3@users.noreply.github.com> Björn Steinbrink blake2-ppc blyxyas Alejandra González @@ -172,6 +174,7 @@ Dzmitry Malyshau E. Dunham edunham Ed Barnard Eduard-Mihai Burtescu +Eduard-Mihai Burtescu Eduardo Bautista <=> Eduardo Bautista Eduardo Broto @@ -186,6 +189,7 @@ Erick Tryzelaar Erik Desjardins Erik Jensen Erin Power +Erin Power Erin Power Erin Power Esteban Küber @@ -198,6 +202,7 @@ F001 Fabian Kössel Falco Hirschenberger Felix S. Klock II Felix S Klock II +Felix S. Klock II Félix Saparelli Flaper Fesp Florian Berger @@ -245,7 +250,7 @@ Irina Popa Ivan Ivaschenko ivan tkachenko J. J. Weber -Jack Huey +Jack Huey Jacob Jacob Greenfield Jacob Pratt @@ -292,6 +297,7 @@ John Clements John Hodge John Hodge John Hörnvall John Kåre Alsaker +John Kåre Alsaker John Talling John Van Enk Jonas Tepe @@ -368,6 +374,7 @@ Lukas Lueg Luke Metz Luqman Aden Luqman Aden +Luqman Aden Lzu Tao Maik Klein Malo Jaffré @@ -409,6 +416,7 @@ mental mibac138 <5672750+mibac138@users.noreply.github.com> Michael Williams Michael Woerister +Michael Woerister Michael Woerister Michael Woerister Michael Zhang @@ -422,6 +430,7 @@ Ms2ger msizanoen1 Mukilan Thiagarajan Nadrieril Feneanar +Nadrieril Feneanar NAKASHIMA, Makoto NAKASHIMA, Makoto Nathan Ringo @@ -442,6 +451,8 @@ Niclas Schwarzlose <15schnic@gmail.com> Nicolas Abram Nicole Mazzuca Noratrieb <48135649+Noratrieb@users.noreply.github.com> <48135649+Nilstrieb@users.noreply.github.com> +Noratrieb <48135649+Noratrieb@users.noreply.github.com> +Noratrieb <48135649+Noratrieb@users.noreply.github.com> Nif Ward Nika Layzell NODA Kai @@ -460,6 +471,7 @@ Oliver Scherer Oliver Scherer Oliver Scherer Oliver Scherer +Oliver Scherer Oliver Scherer Onur Özkan Onur Özkan @@ -496,6 +508,7 @@ Raphaël Huchet rChaser53 Rémy Rakic Rémy Rakic +Rémy Rakic Renato Riccieri Santos Zannon Richard Diamond Ricky Hosfelt @@ -525,6 +538,7 @@ Samuel Tardieu Santiago Pastorino Santiago Pastorino Scott McMurray +Scott McMurray Scott Olson Scott Olson Sean Gillespie swgillespie Seiichi Uchida @@ -536,6 +550,7 @@ Shyam Sundar B Simon Barber-Dueck Simon BD Simon Sapin Simonas Kazlauskas Simonas Kazlauskas +Simonas Kazlauskas Siva Prasad Smittyvb Srinivas Reddy Thatiparthy @@ -556,6 +571,8 @@ Tatsuyuki Ishi Tau Gärtli Tero Hänninen Tero Hänninen The8472 +The8472 +The8472 Theo Belaire Theo Belaire Theodore Luo Wang Thiago Pontes thiagopnts @@ -593,7 +610,8 @@ Waffle Lapkin Wesley Wiser whitequark William Ting -Wim Looman +Wim Looman +Wim Looman Without Boats Without Boats Xinye Tao From d39270f775e06e4662ff66a2b3c54ff441163a69 Mon Sep 17 00:00:00 2001 From: MarcoIeni <11428655+MarcoIeni@users.noreply.github.com> Date: Fri, 1 Nov 2024 21:11:28 +0100 Subject: [PATCH 14/16] CI: switch dist-x86_64-musl to free runner --- src/ci/github-actions/jobs.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/ci/github-actions/jobs.yml b/src/ci/github-actions/jobs.yml index 8b7126d81d0..c0ce358486b 100644 --- a/src/ci/github-actions/jobs.yml +++ b/src/ci/github-actions/jobs.yml @@ -205,7 +205,7 @@ auto: - image: dist-x86_64-musl env: CODEGEN_BACKENDS: llvm,cranelift - <<: *job-linux-8c + <<: *job-linux-4c - image: dist-x86_64-netbsd <<: *job-linux-4c From 9e5e47fc32ed5eb26b5644675980537a6c7348e6 Mon Sep 17 00:00:00 2001 From: Michael Goulet Date: Sat, 2 Nov 2024 03:17:43 +0000 Subject: [PATCH 15/16] Remove or fix some FIXME(async_closure) --- .../rustc_infer/src/infer/opaque_types/mod.rs | 1 - tests/ui/async-await/async-closures/mangle.rs | 3 --- .../async-closures/no-borrow-from-env.rs | 5 ++++- tests/ui/async-await/async-closures/not-fn.rs | 2 +- .../async-closures/precise-captures.rs | 4 ++-- ...thout-precise-captures-we-are-powerless.rs | 4 +++- ...t-precise-captures-we-are-powerless.stderr | 21 ++++++++++++------- 7 files changed, 24 insertions(+), 16 deletions(-) diff --git a/compiler/rustc_infer/src/infer/opaque_types/mod.rs b/compiler/rustc_infer/src/infer/opaque_types/mod.rs index 2bc006c37da..d65ed72a8e8 100644 --- a/compiler/rustc_infer/src/infer/opaque_types/mod.rs +++ b/compiler/rustc_infer/src/infer/opaque_types/mod.rs @@ -432,7 +432,6 @@ where upvar.visit_with(self); } - // FIXME(async_closures): Is this the right signature to visit here? args.as_coroutine_closure().signature_parts_ty().visit_with(self); } diff --git a/tests/ui/async-await/async-closures/mangle.rs b/tests/ui/async-await/async-closures/mangle.rs index 632f1657436..a428905e40b 100644 --- a/tests/ui/async-await/async-closures/mangle.rs +++ b/tests/ui/async-await/async-closures/mangle.rs @@ -5,9 +5,6 @@ //@[v0] compile-flags: -Csymbol-mangling-version=v0 //@[legacy] compile-flags: -Csymbol-mangling-version=legacy -Zunstable-options -// FIXME(async_closures): When `fn_sig_for_fn_abi` is fixed, remove this. -//@ ignore-pass (test emits codegen-time warnings) - #![feature(async_closure, noop_waker)] extern crate block_on; diff --git a/tests/ui/async-await/async-closures/no-borrow-from-env.rs b/tests/ui/async-await/async-closures/no-borrow-from-env.rs index fe84aeeb32f..3f9d26b9713 100644 --- a/tests/ui/async-await/async-closures/no-borrow-from-env.rs +++ b/tests/ui/async-await/async-closures/no-borrow-from-env.rs @@ -38,7 +38,10 @@ fn through_field_and_ref<'a>(x: &S<'a>) { let c = async move || { println!("{}", *x.0); }; outlives::<'a>(c()); - // outlives::<'a>(call_once(c)); // FIXME(async_closures): Figure out why this fails + + // outlives::<'a>(call_once(c)); + // The above fails b/c the by-move coroutine of `c` captures `x` in its entirety. + // Since we have not asserted that the borrow for `&S<'a>` outlives `'a`, it'll fail. } fn main() {} diff --git a/tests/ui/async-await/async-closures/not-fn.rs b/tests/ui/async-await/async-closures/not-fn.rs index 5322a6d5d7a..5f2d047c3e9 100644 --- a/tests/ui/async-await/async-closures/not-fn.rs +++ b/tests/ui/async-await/async-closures/not-fn.rs @@ -9,7 +9,7 @@ fn main() { let mut x = 1; needs_fn(async || { - //~^ ERROR async closure does not implement `FnMut` because it captures state from its environment + //~^ ERROR async closure does not implement `FnMut` because it captures state from its environment x += 1; }); } diff --git a/tests/ui/async-await/async-closures/precise-captures.rs b/tests/ui/async-await/async-closures/precise-captures.rs index e82dd1dbaf0..c4c67df544f 100644 --- a/tests/ui/async-await/async-closures/precise-captures.rs +++ b/tests/ui/async-await/async-closures/precise-captures.rs @@ -126,7 +126,7 @@ async fn async_main() { { let mut s = S { a: 1, b: Drop("drop first"), c: Drop("untouched") }; let c = guidance!(async move || { - // s.a = 2; // FIXME(async_closures): Figure out why this fails + s.a = 2; drop(s.b); }); s.c.0 = "uncaptured"; @@ -141,7 +141,7 @@ async fn async_main() { { let mut s = S { a: 1, b: Drop("drop first"), c: Drop("untouched") }; let c = guidance!(async move || { - // s.a = 2; // FIXME(async_closures): Figure out why this fails + s.a = 2; drop(s.b); }); s.c.0 = "uncaptured"; diff --git a/tests/ui/async-await/async-closures/without-precise-captures-we-are-powerless.rs b/tests/ui/async-await/async-closures/without-precise-captures-we-are-powerless.rs index 18f16ca4b2d..be3f032b8ff 100644 --- a/tests/ui/async-await/async-closures/without-precise-captures-we-are-powerless.rs +++ b/tests/ui/async-await/async-closures/without-precise-captures-we-are-powerless.rs @@ -38,10 +38,12 @@ fn through_field_and_ref<'a>(x: &S<'a>) { let c = async || { println!("{}", *x.0); }; //~ ERROR `x` does not live long enough outlives::<'a>(c()); outlives::<'a>(call_once(c)); //~ ERROR explicit lifetime required in the type of `x` +} +fn through_field_and_ref_move<'a>(x: &S<'a>) { let c = async move || { println!("{}", *x.0); }; outlives::<'a>(c()); //~ ERROR `c` does not live long enough - // outlives::<'a>(call_once(c)); // FIXME(async_closures): Figure out why this fails + outlives::<'a>(call_once(c)); //~ ERROR explicit lifetime required in the type of `x` } fn main() {} diff --git a/tests/ui/async-await/async-closures/without-precise-captures-we-are-powerless.stderr b/tests/ui/async-await/async-closures/without-precise-captures-we-are-powerless.stderr index 1df5abdbb18..a70aece2dea 100644 --- a/tests/ui/async-await/async-closures/without-precise-captures-we-are-powerless.stderr +++ b/tests/ui/async-await/async-closures/without-precise-captures-we-are-powerless.stderr @@ -100,7 +100,6 @@ LL | let c = async || { println!("{}", *x.0); }; LL | outlives::<'a>(c()); LL | outlives::<'a>(call_once(c)); | ------------ argument requires that `x` is borrowed for `'a` -... LL | } | - `x` dropped here while still borrowed @@ -114,11 +113,10 @@ LL | outlives::<'a>(call_once(c)); | ^^^^^^^^^^^^ lifetime `'a` required error[E0597]: `c` does not live long enough - --> $DIR/without-precise-captures-we-are-powerless.rs:43:20 + --> $DIR/without-precise-captures-we-are-powerless.rs:45:20 | -LL | fn through_field_and_ref<'a>(x: &S<'a>) { - | -- lifetime `'a` defined here -... +LL | fn through_field_and_ref_move<'a>(x: &S<'a>) { + | -- lifetime `'a` defined here LL | let c = async move || { println!("{}", *x.0); }; | - binding `c` declared here LL | outlives::<'a>(c()); @@ -126,11 +124,20 @@ LL | outlives::<'a>(c()); | | | borrowed value does not live long enough | argument requires that `c` is borrowed for `'a` -LL | // outlives::<'a>(call_once(c)); // FIXME(async_closures): Figure out why this fails +LL | outlives::<'a>(call_once(c)); LL | } | - `c` dropped here while still borrowed -error: aborting due to 9 previous errors +error[E0621]: explicit lifetime required in the type of `x` + --> $DIR/without-precise-captures-we-are-powerless.rs:46:20 + | +LL | fn through_field_and_ref_move<'a>(x: &S<'a>) { + | ------ help: add explicit lifetime `'a` to the type of `x`: `&'a S<'a>` +... +LL | outlives::<'a>(call_once(c)); + | ^^^^^^^^^^^^ lifetime `'a` required + +error: aborting due to 10 previous errors Some errors have detailed explanations: E0505, E0597, E0621. For more information about an error, try `rustc --explain E0505`. From d2aa91054b360046bbb065336d7ffc7ccfd63b43 Mon Sep 17 00:00:00 2001 From: Veera Date: Sat, 26 Oct 2024 03:58:30 +0000 Subject: [PATCH 16/16] Add a Few Codegen Tests --- ...fn-ptr-call-returning-never-is-noreturn.rs | 19 ++++++++++++++ ...issue-86109-eliminate-div-by-zero-check.rs | 26 +++++++++++++++++++ 2 files changed, 45 insertions(+) create mode 100644 tests/codegen/issues/issue-64219-fn-ptr-call-returning-never-is-noreturn.rs create mode 100644 tests/codegen/issues/issue-86109-eliminate-div-by-zero-check.rs diff --git a/tests/codegen/issues/issue-64219-fn-ptr-call-returning-never-is-noreturn.rs b/tests/codegen/issues/issue-64219-fn-ptr-call-returning-never-is-noreturn.rs new file mode 100644 index 00000000000..86d020e1751 --- /dev/null +++ b/tests/codegen/issues/issue-64219-fn-ptr-call-returning-never-is-noreturn.rs @@ -0,0 +1,19 @@ +//! Test for https://github.com/rust-lang/rust/issues/64219 +//! Check if `noreturn` attribute is applied on calls to +//! function pointers returning `!` (never type). + +#![crate_type = "lib"] + +extern "C" { + static FOO: fn() -> !; +} + +// CHECK-LABEL: @foo +#[no_mangle] +pub unsafe fn foo() { + // CHECK: call + // CHECK-SAME: [[NUM:#[0-9]+$]] + FOO(); +} + +// CHECK: attributes [[NUM]] = {{{.*}} noreturn {{.*}}} diff --git a/tests/codegen/issues/issue-86109-eliminate-div-by-zero-check.rs b/tests/codegen/issues/issue-86109-eliminate-div-by-zero-check.rs new file mode 100644 index 00000000000..a8fab61b13e --- /dev/null +++ b/tests/codegen/issues/issue-86109-eliminate-div-by-zero-check.rs @@ -0,0 +1,26 @@ +//@ compile-flags: -O +//! Test for https://github.com/rust-lang/rust/issues/86109 +//! Check LLVM can eliminate the impossible division by zero check by +//! ensuring there is no call (to panic) instruction. +//! +//! This has been fixed since `rustc 1.70.0`. + +#![crate_type = "lib"] + +type T = i16; + +// CHECK-LABEL: @foo +#[no_mangle] +pub fn foo(start: T) -> T { + // CHECK-NOT: panic + if start <= 0 { + return 0; + } + let mut count = 0; + for i in start..10_000 { + if 752 % i != 0 { + count += 1; + } + } + count +}