Auto merge of #127197 - matthiaskrgr:rollup-aqpvn5q, r=matthiaskrgr

Rollup of 7 pull requests

Successful merges:

 - #126923 (test: dont optimize to invalid bitcasts)
 - #127090 (Reduce merge conflicts from rustfmt's wrapping)
 - #127105 (Only update `Eq` operands in GVN if it can update both sides)
 - #127150 (Fix x86_64 code being produced for bare-metal LoongArch targets' `compiler_builtins`)
 - #127181 (Introduce a `rustc_` attribute to dump all the `DefId` parents of a `DefId`)
 - #127182 (Fix error in documentation for IpAddr::to_canonical and Ipv6Addr::to_canonical)
 - #127191 (Ensure `out_of_scope_macro_calls` lint is registered)

r? `@ghost`
`@rustbot` modify labels: rollup
This commit is contained in:
bors 2024-07-01 08:51:46 +00:00
commit c3774be741
20 changed files with 436 additions and 18 deletions

View File

@ -1117,6 +1117,10 @@ pub const BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[
TEST, rustc_dump_predicates, Normal, template!(Word),
WarnFollowing, EncodeCrossCrate::No
),
rustc_attr!(
TEST, rustc_dump_def_parents, Normal, template!(Word),
WarnFollowing, EncodeCrossCrate::No
),
rustc_attr!(
TEST, rustc_object_lifetime_default, Normal, template!(Word),
WarnFollowing, EncodeCrossCrate::No

View File

@ -1,5 +1,7 @@
use rustc_hir::def::DefKind;
use rustc_hir::def_id::CRATE_DEF_ID;
use rustc_hir::def_id::{LocalDefId, CRATE_DEF_ID};
use rustc_hir::intravisit;
use rustc_middle::hir::nested_filter::OnlyBodies;
use rustc_middle::ty::TyCtxt;
use rustc_span::sym;
@ -41,3 +43,49 @@ pub(crate) fn predicates_and_item_bounds(tcx: TyCtxt<'_>) {
}
}
}
pub(crate) fn def_parents(tcx: TyCtxt<'_>) {
for did in tcx.hir().body_owners() {
if tcx.has_attr(did, sym::rustc_dump_def_parents) {
struct AnonConstFinder<'tcx> {
tcx: TyCtxt<'tcx>,
anon_consts: Vec<LocalDefId>,
}
impl<'tcx> intravisit::Visitor<'tcx> for AnonConstFinder<'tcx> {
type NestedFilter = OnlyBodies;
fn nested_visit_map(&mut self) -> Self::Map {
self.tcx.hir()
}
fn visit_anon_const(&mut self, c: &'tcx rustc_hir::AnonConst) {
self.anon_consts.push(c.def_id);
intravisit::walk_anon_const(self, c)
}
}
// Look for any anon consts inside of this body owner as there is no way to apply
// the `rustc_dump_def_parents` attribute to the anon const so it would not be possible
// to see what its def parent is.
let mut anon_ct_finder = AnonConstFinder { tcx, anon_consts: vec![] };
intravisit::walk_expr(&mut anon_ct_finder, tcx.hir().body_owned_by(did).value);
for did in [did].into_iter().chain(anon_ct_finder.anon_consts) {
let span = tcx.def_span(did);
let mut diag = tcx.dcx().struct_span_err(
span,
format!("{}: {did:?}", sym::rustc_dump_def_parents.as_str()),
);
let mut current_did = did.to_def_id();
while let Some(parent_did) = tcx.opt_parent(current_did) {
current_did = parent_did;
diag.span_note(tcx.def_span(parent_did), format!("{parent_did:?}"));
}
diag.emit();
}
}
}
}

View File

@ -175,6 +175,7 @@ pub fn check_crate(tcx: TyCtxt<'_>) {
tcx.sess.time("variance_dumping", || variance::dump::variances(tcx));
collect::dump::opaque_hidden_types(tcx);
collect::dump::predicates_and_item_bounds(tcx);
collect::dump::def_parents(tcx);
}
// Make sure we evaluate all static and (non-associated) const items, even if unused.

View File

@ -2,14 +2,22 @@
use crate::interface::{initialize_checked_jobserver, parse_cfg};
use rustc_data_structures::profiling::TimePassesFormat;
use rustc_errors::{emitter::HumanReadableErrorType, registry, ColorConfig};
use rustc_session::config::{build_configuration, build_session_options, rustc_optgroups};
use rustc_session::config::{
build_configuration, build_session_options, rustc_optgroups, BranchProtection, CFGuard, Cfg,
CollapseMacroDebuginfo, CoverageLevel, CoverageOptions, DebugInfo, DumpMonoStatsFormat,
ErrorOutputType, ExternEntry, ExternLocation, Externs, FunctionReturn, InliningThreshold,
Input, InstrumentCoverage, InstrumentXRay, LinkSelfContained, LinkerPluginLto, LocationDetail,
LtoCli, NextSolverConfig, OomStrategy, Options, OutFileName, OutputType, OutputTypes, PAuthKey,
PacRet, Passes, PatchableFunctionEntry, Polonius, ProcMacroExecutionStrategy, Strip,
SwitchWithOptPath, SymbolManglingVersion, WasiExecModel,
BranchProtection, CFGuard, Cfg, CollapseMacroDebuginfo, CoverageLevel, CoverageOptions,
DebugInfo, DumpMonoStatsFormat, ErrorOutputType,
};
use rustc_session::config::{
ExternEntry, ExternLocation, Externs, FunctionReturn, InliningThreshold, Input,
InstrumentCoverage, InstrumentXRay, LinkSelfContained, LinkerPluginLto,
};
use rustc_session::config::{
LocationDetail, LtoCli, NextSolverConfig, OomStrategy, Options, OutFileName, OutputType,
OutputTypes, PAuthKey, PacRet, Passes, PatchableFunctionEntry,
};
use rustc_session::config::{
Polonius, ProcMacroExecutionStrategy, Strip, SwitchWithOptPath, SymbolManglingVersion,
WasiExecModel,
};
use rustc_session::lint::Level;
use rustc_session::search_paths::SearchPath;

View File

@ -74,6 +74,7 @@ declare_lint_pass! {
NON_CONTIGUOUS_RANGE_ENDPOINTS,
NON_EXHAUSTIVE_OMITTED_PATTERNS,
ORDER_DEPENDENT_TRAIT_OBJECTS,
OUT_OF_SCOPE_MACRO_CALLS,
OVERLAPPING_RANGE_ENDPOINTS,
PATTERNS_IN_FNS_WITHOUT_BODY,
PRIVATE_BOUNDS,

View File

@ -1074,11 +1074,11 @@ impl<'body, 'tcx> VnState<'body, 'tcx> {
{
lhs = *lhs_value;
rhs = *rhs_value;
if let Some(op) = self.try_as_operand(lhs, location) {
*lhs_operand = op;
}
if let Some(op) = self.try_as_operand(rhs, location) {
*rhs_operand = op;
if let Some(lhs_op) = self.try_as_operand(lhs, location)
&& let Some(rhs_op) = self.try_as_operand(rhs, location)
{
*lhs_operand = lhs_op;
*rhs_operand = rhs_op;
}
}

View File

@ -1614,6 +1614,7 @@ symbols! {
rustc_do_not_const_check,
rustc_doc_primitive,
rustc_dummy,
rustc_dump_def_parents,
rustc_dump_item_bounds,
rustc_dump_predicates,
rustc_dump_user_args,

View File

@ -406,7 +406,7 @@ impl IpAddr {
matches!(self, IpAddr::V6(_))
}
/// Converts this address to an `IpAddr::V4` if it is an IPv4-mapped IPv6 addresses, otherwise it
/// Converts this address to an `IpAddr::V4` if it is an IPv4-mapped IPv6 address, otherwise it
/// returns `self` as-is.
///
/// # Examples
@ -1879,7 +1879,7 @@ impl Ipv6Addr {
}
}
/// Converts this address to an `IpAddr::V4` if it is an IPv4-mapped addresses, otherwise it
/// Converts this address to an `IpAddr::V4` if it is an IPv4-mapped address, otherwise it
/// returns self wrapped in an `IpAddr::V6`.
///
/// # Examples

View File

@ -23,7 +23,25 @@ ENV CC_loongarch64_unknown_linux_gnu=loongarch64-unknown-linux-gnu-gcc \
AR_loongarch64_unknown_linux_gnu=loongarch64-unknown-linux-gnu-ar \
CXX_loongarch64_unknown_linux_gnu=loongarch64-unknown-linux-gnu-g++
# We re-use the Linux toolchain for bare-metal, because upstream bare-metal
# target support for LoongArch is only available from GCC 14+.
#
# See: https://github.com/gcc-mirror/gcc/commit/976f4f9e4770
ENV CC_loongarch64_unknown_none=loongarch64-unknown-linux-gnu-gcc \
AR_loongarch64_unknown_none=loongarch64-unknown-linux-gnu-ar \
CXX_loongarch64_unknown_none=loongarch64-unknown-linux-gnu-g++ \
CFLAGS_loongarch64_unknown_none="-ffreestanding -mabi=lp64d" \
CXXFLAGS_loongarch64_unknown_none="-ffreestanding -mabi=lp64d" \
CC_loongarch64_unknown_none_softfloat=loongarch64-unknown-linux-gnu-gcc \
AR_loongarch64_unknown_none_softfloat=loongarch64-unknown-linux-gnu-ar \
CXX_loongarch64_unknown_none_softfloat=loongarch64-unknown-linux-gnu-g++ \
CFLAGS_loongarch64_unknown_none_softfloat="-ffreestanding -mabi=lp64s -mfpu=none" \
CXXFLAGS_loongarch64_unknown_none_softfloat="-ffreestanding -mabi=lp64s -mfpu=none"
ENV HOSTS=loongarch64-unknown-linux-gnu
ENV TARGETS=$HOSTS
ENV TARGETS=$TARGETS,loongarch64-unknown-none
ENV TARGETS=$TARGETS,loongarch64-unknown-none-softfloat
ENV RUST_CONFIGURE_ARGS \
--enable-extended \
@ -31,4 +49,4 @@ ENV RUST_CONFIGURE_ARGS \
--enable-profiler \
--disable-docs
ENV SCRIPT python3 ../x.py dist --host $HOSTS --target $HOSTS
ENV SCRIPT python3 ../x.py dist --host $HOSTS --target $TARGETS

View File

@ -121,8 +121,6 @@ ENV TARGETS=$TARGETS,armv7-unknown-linux-gnueabi
ENV TARGETS=$TARGETS,armv7-unknown-linux-musleabi
ENV TARGETS=$TARGETS,i686-unknown-freebsd
ENV TARGETS=$TARGETS,x86_64-unknown-none
ENV TARGETS=$TARGETS,loongarch64-unknown-none
ENV TARGETS=$TARGETS,loongarch64-unknown-none-softfloat
ENV TARGETS=$TARGETS,aarch64-unknown-uefi
ENV TARGETS=$TARGETS,i686-unknown-uefi
ENV TARGETS=$TARGETS,x86_64-unknown-uefi

View File

@ -0,0 +1,16 @@
- // MIR for `remove_casts_must_change_both_sides` before GVN
+ // MIR for `remove_casts_must_change_both_sides` after GVN
fn remove_casts_must_change_both_sides(_1: &*mut u8, _2: *mut u8) -> bool {
let mut _0: bool;
let mut _3: *const u8;
let mut _4: *const u8;
bb0: {
_3 = (*_1) as *const u8 (PtrToPtr);
_4 = _2 as *const u8 (PtrToPtr);
_0 = Eq(_3, _4);
return;
}
}

View File

@ -0,0 +1,16 @@
- // MIR for `remove_casts_must_change_both_sides` before GVN
+ // MIR for `remove_casts_must_change_both_sides` after GVN
fn remove_casts_must_change_both_sides(_1: &*mut u8, _2: *mut u8) -> bool {
let mut _0: bool;
let mut _3: *const u8;
let mut _4: *const u8;
bb0: {
_3 = (*_1) as *const u8 (PtrToPtr);
_4 = _2 as *const u8 (PtrToPtr);
_0 = Eq(_3, _4);
return;
}
}

View File

@ -926,6 +926,25 @@ unsafe fn cast_pointer_then_transmute(thin: *mut u32, fat: *mut [u8]) {
let fat_addr: usize = std::intrinsics::transmute(fat as *const ());
}
#[custom_mir(dialect = "analysis")]
fn remove_casts_must_change_both_sides(mut_a: &*mut u8, mut_b: *mut u8) -> bool {
// CHECK-LABEL: fn remove_casts_must_change_both_sides(
mir! {
// We'd like to remove these casts, but we can't change *both* of them
// to be locals, so make sure we don't change one without the other, as
// that would be a type error.
{
// CHECK: [[A:_.+]] = (*_1) as *const u8 (PtrToPtr);
let a = *mut_a as *const u8;
// CHECK: [[B:_.+]] = _2 as *const u8 (PtrToPtr);
let b = mut_b as *const u8;
// CHECK: _0 = Eq([[A]], [[B]]);
RET = a == b;
Return()
}
}
}
fn main() {
subexpression_elimination(2, 4, 5);
wrap_unwrap(5);
@ -995,3 +1014,4 @@ fn identity<T>(x: T) -> T {
// EMIT_MIR gvn.generic_cast_metadata.GVN.diff
// EMIT_MIR gvn.cast_pointer_eq.GVN.diff
// EMIT_MIR gvn.cast_pointer_then_transmute.GVN.diff
// EMIT_MIR gvn.remove_casts_must_change_both_sides.GVN.diff

View File

@ -0,0 +1,52 @@
- // MIR for `main` before GVN
+ // MIR for `main` after GVN
fn main() -> () {
let mut _0: ();
let _1: bool;
let mut _2: *mut u8;
scope 1 (inlined dangling_mut::<u8>) {
let mut _3: usize;
scope 2 (inlined align_of::<u8>) {
}
scope 3 (inlined without_provenance_mut::<u8>) {
}
}
scope 4 (inlined Foo::<u8>::cmp_ptr) {
let mut _4: *const u8;
let mut _5: *mut u8;
let mut _6: *const u8;
scope 5 (inlined std::ptr::eq::<u8>) {
}
}
bb0: {
StorageLive(_1);
StorageLive(_2);
StorageLive(_3);
- _3 = AlignOf(u8);
- _2 = _3 as *mut u8 (Transmute);
+ _3 = const 1_usize;
+ _2 = const {0x1 as *mut u8};
StorageDead(_3);
StorageLive(_4);
StorageLive(_5);
- _5 = _2;
- _4 = _2 as *const u8 (PtrToPtr);
+ _5 = const {0x1 as *mut u8};
+ _4 = const {0x1 as *const u8};
StorageDead(_5);
StorageLive(_6);
- _6 = const Foo::<u8>::SENTINEL as *const u8 (PtrToPtr);
- _1 = Eq(_4, _6);
+ _6 = const {0x1 as *const u8};
+ _1 = const true;
StorageDead(_6);
StorageDead(_4);
StorageDead(_2);
StorageDead(_1);
_0 = const ();
return;
}
}

View File

@ -0,0 +1,23 @@
// skip-filecheck
//@ test-mir-pass: GVN
//@ only-64bit
//@ compile-flags: -Z mir-enable-passes=+Inline
// Regression for <https://github.com/rust-lang/rust/issues/127089>
#![feature(strict_provenance)]
struct Foo<T>(std::marker::PhantomData<T>);
impl<T> Foo<T> {
const SENTINEL: *mut T = std::ptr::dangling_mut();
fn cmp_ptr(a: *mut T) -> bool {
std::ptr::eq(a, Self::SENTINEL)
}
}
// EMIT_MIR gvn_ptr_eq_with_constant.main.GVN.diff
pub fn main() {
Foo::<u8>::cmp_ptr(std::ptr::dangling_mut());
}

View File

@ -0,0 +1,34 @@
//@ normalize-stderr-test "DefId\(.+?\)" -> "DefId(..)"
#![feature(rustc_attrs)]
fn bar() {
fn foo() {
fn baz() {
#[rustc_dump_def_parents]
|| {
//~^ ERROR: rustc_dump_def_parents: DefId
qux::<
{
//~^ ERROR: rustc_dump_def_parents: DefId
fn inhibits_dump() {
qux::<
{
"hi";
1
},
>();
}
qux::<{ 1 + 1 }>();
//~^ ERROR: rustc_dump_def_parents: DefId
1
},
>();
};
}
}
}
const fn qux<const N: usize>() {}
fn main() {}

View File

@ -0,0 +1,128 @@
error: rustc_dump_def_parents: DefId(..)
--> $DIR/dump_def_parents.rs:8:13
|
LL | || {
| ^^
|
note: DefId(..)
--> $DIR/dump_def_parents.rs:6:9
|
LL | fn baz() {
| ^^^^^^^^
note: DefId(..)
--> $DIR/dump_def_parents.rs:5:5
|
LL | fn foo() {
| ^^^^^^^^
note: DefId(..)
--> $DIR/dump_def_parents.rs:4:1
|
LL | fn bar() {
| ^^^^^^^^
note: DefId(..)
--> $DIR/dump_def_parents.rs:2:1
|
LL | / #![feature(rustc_attrs)]
LL | |
LL | | fn bar() {
LL | | fn foo() {
... |
LL | |
LL | | fn main() {}
| |____________^
error: rustc_dump_def_parents: DefId(..)
--> $DIR/dump_def_parents.rs:11:21
|
LL | / {
LL | |
LL | | fn inhibits_dump() {
LL | | qux::<
... |
LL | | 1
LL | | },
| |_____________________^
|
note: DefId(..)
--> $DIR/dump_def_parents.rs:8:13
|
LL | || {
| ^^
note: DefId(..)
--> $DIR/dump_def_parents.rs:6:9
|
LL | fn baz() {
| ^^^^^^^^
note: DefId(..)
--> $DIR/dump_def_parents.rs:5:5
|
LL | fn foo() {
| ^^^^^^^^
note: DefId(..)
--> $DIR/dump_def_parents.rs:4:1
|
LL | fn bar() {
| ^^^^^^^^
note: DefId(..)
--> $DIR/dump_def_parents.rs:2:1
|
LL | / #![feature(rustc_attrs)]
LL | |
LL | | fn bar() {
LL | | fn foo() {
... |
LL | |
LL | | fn main() {}
| |____________^
error: rustc_dump_def_parents: DefId(..)
--> $DIR/dump_def_parents.rs:22:31
|
LL | qux::<{ 1 + 1 }>();
| ^^^^^^^^^
|
note: DefId(..)
--> $DIR/dump_def_parents.rs:11:21
|
LL | / {
LL | |
LL | | fn inhibits_dump() {
LL | | qux::<
... |
LL | | 1
LL | | },
| |_____________________^
note: DefId(..)
--> $DIR/dump_def_parents.rs:8:13
|
LL | || {
| ^^
note: DefId(..)
--> $DIR/dump_def_parents.rs:6:9
|
LL | fn baz() {
| ^^^^^^^^
note: DefId(..)
--> $DIR/dump_def_parents.rs:5:5
|
LL | fn foo() {
| ^^^^^^^^
note: DefId(..)
--> $DIR/dump_def_parents.rs:4:1
|
LL | fn bar() {
| ^^^^^^^^
note: DefId(..)
--> $DIR/dump_def_parents.rs:2:1
|
LL | / #![feature(rustc_attrs)]
LL | |
LL | | fn bar() {
LL | | fn foo() {
... |
LL | |
LL | | fn main() {}
| |____________^
error: aborting due to 3 previous errors

View File

@ -0,0 +1,6 @@
//@ check-pass
#![deny(unknown_lints)]
#![allow(out_of_scope_macro_calls)]
fn main() {}

View File

@ -0,0 +1,17 @@
//@ build-pass
//@ compile-flags: -Copt-level=3
// regression test for https://github.com/rust-lang/rust/issues/110722
// in --release we were optimizing to invalid bitcasts, due to a combination of MIR inlining and
// mostly bad repr(simd) lowering which prevented even basic splats from working
#![crate_type = "rlib"]
#![feature(portable_simd)]
use std::simd::*;
use std::simd::num::*;
pub unsafe fn mask_to_array(mask: u8) -> [i32; 8] {
let mut output = [0; 8];
let m = masksizex8::from_bitmask(mask as _);
output.copy_from_slice(&m.to_int().cast::<i32>().to_array());
output
}

View File

@ -0,0 +1,27 @@
//@ build-pass
//@ compile-flags: -Copt-level=3
//@ only-x86_64
// ignore-tidy-linelength
// regression test for https://github.com/rust-lang/rust/issues/110707
// in --release we were optimizing to invalid bitcasts, due to a combination of MIR inlining and
// mostly bad repr(simd) lowering which prevented even basic splats from working
#![crate_type = "rlib"]
#![feature(portable_simd)]
use std::simd::*;
use std::arch::x86_64::*;
#[target_feature(enable = "sse4.1")]
pub unsafe fn fast_round_sse(i: f32x8) -> f32x8 {
let a = i.to_array();
let [low, high]: [[f32; 4]; 2] =
unsafe { std::mem::transmute::<[f32; 8], [[f32; 4]; 2]>(a) };
let low = f32x4::from(_mm_round_ps::<{_MM_FROUND_TO_NEAREST_INT | _MM_FROUND_NO_EXC}>(f32x4::from_array(low).into()));
let high = f32x4::from(_mm_round_ps::<{_MM_FROUND_TO_NEAREST_INT | _MM_FROUND_NO_EXC}>(f32x4::from_array(high).into()));
let a: [f32; 8] =
unsafe { std::mem::transmute::<[[f32; 4]; 2], [f32; 8]>([low.to_array(), high.to_array()]) };
f32x8::from_array(a)
}