Skip to content

Rollup of 10 pull requests #143322

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
wants to merge 25 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
25 commits
Select commit Hold shift + click to select a range
e95751a
Explain TOCTOU on the top of `std::fs`, and ref it in functions
xizheyin Jun 1, 2025
230b55d
Add `into_chunks`
ashivaram23 Jun 7, 2025
e4e7773
put feature attribute in example
ashivaram23 Jun 7, 2025
343db27
cfg for no no_global_oom_handling
ashivaram23 Jun 7, 2025
c1d32d8
fix wording in assert
ashivaram23 Jun 7, 2025
cfa6731
expose abi information on ppc64 targets
ostylk Jun 16, 2025
45538e0
ci: aarch64-gnu: Stop skipping `panic_abort_doc_tests`
Enselic Jun 22, 2025
e86fddc
fix bitcast of single-element SIMD vectors
folkertdev Jun 29, 2025
08278eb
Don't recompute DisambiguatorState for every RPITIT in trait definition
compiler-errors Jun 30, 2025
c073286
Use the correct export kind for __rust_alloc_error_handler_should_panic
dpaoliello Jun 30, 2025
311a99c
ci: support optional jobs
marcoieni Jul 1, 2025
e7c3703
Suggest use another lifetime specifier instead of underscore lifetime
xizheyin Jun 30, 2025
cf5788d
Rename `header` -> `directives`
jieyouxu Jun 30, 2025
475f447
Update compiletest to use "directive" terminology consistently
jieyouxu Jun 30, 2025
0346895
Rename {`HeadersCache`, `iter_header`} -> {`DirectivesCache`, `iter_d…
jieyouxu Jun 30, 2025
0c60f2b
Rollup merge of #141847 - xizheyin:141837, r=jhpratt
matthiaskrgr Jul 2, 2025
fb8421f
Rollup merge of #142138 - ashivaram23:vec_into_chunks, r=scottmcm
matthiaskrgr Jul 2, 2025
616e4ef
Rollup merge of #142321 - ostylk:fix/ppc64_abi, r=workingjubilee
matthiaskrgr Jul 2, 2025
7532d5f
Rollup merge of #142886 - Enselic:aarch64-panic, r=cuviper
matthiaskrgr Jul 2, 2025
a07f31c
Rollup merge of #143194 - folkertdev:fix-single-element-simd-bitcast,…
matthiaskrgr Jul 2, 2025
507a6fd
Rollup merge of #143231 - xizheyin:143152, r=fee1-dead
matthiaskrgr Jul 2, 2025
99a1af5
Rollup merge of #143232 - jieyouxu:compiletest-maintenance-3, r=Kobzol
matthiaskrgr Jul 2, 2025
85c5774
Rollup merge of #143258 - compiler-errors:disambiguator-state, r=oli-obk
matthiaskrgr Jul 2, 2025
d7fbef4
Rollup merge of #143260 - dpaoliello:arm64eclinkagain, r=bjorn3
matthiaskrgr Jul 2, 2025
87e28ff
Rollup merge of #143274 - marcoieni:optional-jobs, r=Kobzol
matthiaskrgr Jul 2, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
17 changes: 11 additions & 6 deletions compiler/rustc_codegen_ssa/src/back/symbol_export.rs
Original file line number Diff line number Diff line change
Expand Up @@ -219,13 +219,18 @@ fn exported_non_generic_symbols_provider_local<'tcx>(

// Mark allocator shim symbols as exported only if they were generated.
if allocator_kind_for_codegen(tcx).is_some() {
for symbol_name in ALLOCATOR_METHODS
for (symbol_name, export_kind) in ALLOCATOR_METHODS
.iter()
.map(|method| mangle_internal_symbol(tcx, global_fn_name(method.name).as_str()))
.map(|method| {
(
mangle_internal_symbol(tcx, global_fn_name(method.name).as_str()),
SymbolExportKind::Text,
)
})
.chain([
mangle_internal_symbol(tcx, "__rust_alloc_error_handler"),
mangle_internal_symbol(tcx, OomStrategy::SYMBOL),
mangle_internal_symbol(tcx, NO_ALLOC_SHIM_IS_UNSTABLE),
(mangle_internal_symbol(tcx, "__rust_alloc_error_handler"), SymbolExportKind::Text),
(mangle_internal_symbol(tcx, OomStrategy::SYMBOL), SymbolExportKind::Data),
(mangle_internal_symbol(tcx, NO_ALLOC_SHIM_IS_UNSTABLE), SymbolExportKind::Text),
])
{
let exported_symbol = ExportedSymbol::NoDefId(SymbolName::new(tcx, &symbol_name));
Expand All @@ -234,7 +239,7 @@ fn exported_non_generic_symbols_provider_local<'tcx>(
exported_symbol,
SymbolExportInfo {
level: SymbolExportLevel::Rust,
kind: SymbolExportKind::Text,
kind: export_kind,
used: false,
rustc_std_internal_symbol: true,
},
Expand Down
10 changes: 2 additions & 8 deletions compiler/rustc_codegen_ssa/src/mir/rvalue.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1117,7 +1117,7 @@ pub(super) fn transmute_immediate<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>(
// While optimizations will remove no-op transmutes, they might still be
// there in debug or things that aren't no-op in MIR because they change
// the Rust type but not the underlying layout/niche.
if from_scalar == to_scalar {
if from_scalar == to_scalar && from_backend_ty == to_backend_ty {
return imm;
}

Expand All @@ -1136,13 +1136,7 @@ pub(super) fn transmute_immediate<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>(
assume_scalar_range(bx, imm, from_scalar, from_backend_ty);

imm = match (from_scalar.primitive(), to_scalar.primitive()) {
(Int(..) | Float(_), Int(..) | Float(_)) => {
if from_backend_ty == to_backend_ty {
imm
} else {
bx.bitcast(imm, to_backend_ty)
}
}
(Int(..) | Float(_), Int(..) | Float(_)) => bx.bitcast(imm, to_backend_ty),
(Pointer(..), Pointer(..)) => bx.pointercast(imm, to_backend_ty),
(Int(..), Pointer(..)) => bx.ptradd(bx.const_null(bx.type_ptr()), imm),
(Pointer(..), Int(..)) => {
Expand Down
28 changes: 19 additions & 9 deletions compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2459,13 +2459,15 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ {
// type a projection.
let in_trait = match opaque_ty.origin {
hir::OpaqueTyOrigin::FnReturn {
parent,
in_trait_or_impl: Some(hir::RpitContext::Trait),
..
}
| hir::OpaqueTyOrigin::AsyncFn {
parent,
in_trait_or_impl: Some(hir::RpitContext::Trait),
..
} => true,
} => Some(parent),
hir::OpaqueTyOrigin::FnReturn {
in_trait_or_impl: None | Some(hir::RpitContext::TraitImpl),
..
Expand All @@ -2474,7 +2476,7 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ {
in_trait_or_impl: None | Some(hir::RpitContext::TraitImpl),
..
}
| hir::OpaqueTyOrigin::TyAlias { .. } => false,
| hir::OpaqueTyOrigin::TyAlias { .. } => None,
};

self.lower_opaque_ty(opaque_ty.def_id, in_trait)
Expand Down Expand Up @@ -2594,17 +2596,25 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ {

/// Lower an opaque type (i.e., an existential impl-Trait type) from the HIR.
#[instrument(level = "debug", skip(self), ret)]
fn lower_opaque_ty(&self, def_id: LocalDefId, in_trait: bool) -> Ty<'tcx> {
fn lower_opaque_ty(&self, def_id: LocalDefId, in_trait: Option<LocalDefId>) -> Ty<'tcx> {
let tcx = self.tcx();

let lifetimes = tcx.opaque_captured_lifetimes(def_id);
debug!(?lifetimes);

// If this is an RPITIT and we are using the new RPITIT lowering scheme, we
// generate the def_id of an associated type for the trait and return as
// type a projection.
let def_id = if in_trait {
tcx.associated_type_for_impl_trait_in_trait(def_id).to_def_id()
// If this is an RPITIT and we are using the new RPITIT lowering scheme,
// do a linear search to map this to the synthetic associated type that
// it will be lowered to.
let def_id = if let Some(parent_def_id) = in_trait {
*tcx.associated_types_for_impl_traits_in_associated_fn(parent_def_id)
.iter()
.find(|rpitit| match tcx.opt_rpitit_info(**rpitit) {
Some(ty::ImplTraitInTraitData::Trait { opaque_def_id, .. }) => {
opaque_def_id.expect_local() == def_id
}
_ => unreachable!(),
})
.unwrap()
} else {
def_id.to_def_id()
};
Expand All @@ -2627,7 +2637,7 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ {
});
debug!(?args);

if in_trait {
if in_trait.is_some() {
Ty::new_projection_from_args(tcx, def_id, args)
} else {
Ty::new_opaque(tcx, def_id, args)
Expand Down
7 changes: 0 additions & 7 deletions compiler/rustc_middle/src/query/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1093,13 +1093,6 @@ rustc_queries! {
separate_provide_extern
}

/// Given an impl trait in trait `opaque_ty_def_id`, create and return the corresponding
/// associated item.
query associated_type_for_impl_trait_in_trait(opaque_ty_def_id: LocalDefId) -> LocalDefId {
desc { |tcx| "creating the associated item corresponding to the opaque type `{}`", tcx.def_path_str(opaque_ty_def_id.to_def_id()) }
cache_on_disk_if { true }
}

/// Given an `impl_id`, return the trait it implements along with some header information.
/// Return `None` if this is an inherent impl.
query impl_trait_header(impl_id: DefId) -> Option<ty::ImplTraitHeader<'tcx>> {
Expand Down
1 change: 1 addition & 0 deletions compiler/rustc_resolve/messages.ftl
Original file line number Diff line number Diff line change
Expand Up @@ -432,6 +432,7 @@ resolve_undeclared_label =
resolve_underscore_lifetime_is_reserved = `'_` cannot be used here
.label = `'_` is a reserved lifetime name
.help = use another lifetime specifier
resolve_unexpected_res_change_ty_to_const_param_sugg =
you might have meant to write a const parameter here
Expand Down
1 change: 1 addition & 0 deletions compiler/rustc_resolve/src/errors.rs
Original file line number Diff line number Diff line change
Expand Up @@ -934,6 +934,7 @@ pub(crate) struct ImplicitElidedLifetimeNotAllowedHere {

#[derive(Diagnostic)]
#[diag(resolve_underscore_lifetime_is_reserved, code = E0637)]
#[help]
pub(crate) struct UnderscoreLifetimeIsReserved {
#[primary_span]
#[label]
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ pub(crate) fn target() -> Target {
base.add_pre_link_args(LinkerFlavor::Gnu(Cc::Yes, Lld::No), &["-m64"]);
base.max_atomic_width = Some(64);
base.stack_probes = StackProbeType::Inline;
base.abi = "elfv2".into();
base.llvm_abiname = "elfv2".into();

Target {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ pub(crate) fn target() -> Target {
base.add_pre_link_args(LinkerFlavor::Gnu(Cc::Yes, Lld::No), &["-m64"]);
base.max_atomic_width = Some(64);
base.stack_probes = StackProbeType::Inline;
base.abi = "elfv1".into();
base.llvm_abiname = "elfv1".into();

Target {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ pub(crate) fn target() -> Target {
base.stack_probes = StackProbeType::Inline;
// FIXME(compiler-team#422): musl targets should be dynamically linked by default.
base.crt_static_default = true;
base.abi = "elfv2".into();
base.llvm_abiname = "elfv2".into();

Target {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ pub(crate) fn target() -> Target {
base.add_pre_link_args(LinkerFlavor::Gnu(Cc::Yes, Lld::No), &["-m64"]);
base.max_atomic_width = Some(64);
base.stack_probes = StackProbeType::Inline;
base.abi = "elfv2".into();
base.llvm_abiname = "elfv2".into();

Target {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ pub(crate) fn target() -> Target {
base.add_pre_link_args(LinkerFlavor::Gnu(Cc::Yes, Lld::No), &["-m64"]);
base.max_atomic_width = Some(64);
base.stack_probes = StackProbeType::Inline;
base.abi = "elfv1".into();
base.llvm_abiname = "elfv1".into();

Target {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ pub(crate) fn target() -> Target {
base.add_pre_link_args(LinkerFlavor::Gnu(Cc::Yes, Lld::No), &["-m64"]);
base.max_atomic_width = Some(64);
base.stack_probes = StackProbeType::Inline;
base.abi = "elfv2".into();
base.llvm_abiname = "elfv2".into();

Target {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ pub(crate) fn target() -> Target {
base.add_pre_link_args(LinkerFlavor::Gnu(Cc::Yes, Lld::No), &["-m64"]);
base.max_atomic_width = Some(64);
base.stack_probes = StackProbeType::Inline;
base.abi = "elfv2".into();
base.llvm_abiname = "elfv2".into();

Target {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ pub(crate) fn target() -> Target {
base.stack_probes = StackProbeType::Inline;
// FIXME(compiler-team#422): musl targets should be dynamically linked by default.
base.crt_static_default = true;
base.abi = "elfv2".into();
base.llvm_abiname = "elfv2".into();

Target {
Expand Down
58 changes: 28 additions & 30 deletions compiler/rustc_ty_utils/src/assoc.rs
Original file line number Diff line number Diff line change
@@ -1,9 +1,8 @@
use rustc_data_structures::fx::FxIndexSet;
use rustc_hir as hir;
use rustc_hir::def::DefKind;
use rustc_hir::def_id::{DefId, DefIdMap, LocalDefId};
use rustc_hir::definitions::{DefPathData, DisambiguatorState};
use rustc_hir::intravisit::{self, Visitor};
use rustc_hir::{self as hir, AmbigArg};
use rustc_middle::query::Providers;
use rustc_middle::ty::{self, ImplTraitInTraitData, TyCtxt};
use rustc_middle::{bug, span_bug};
Expand All @@ -14,7 +13,6 @@ pub(crate) fn provide(providers: &mut Providers) {
associated_item_def_ids,
associated_items,
associated_types_for_impl_traits_in_associated_fn,
associated_type_for_impl_trait_in_trait,
impl_item_implementor_ids,
..*providers
};
Expand Down Expand Up @@ -160,20 +158,22 @@ fn associated_item_from_impl_item_ref(impl_item_ref: &hir::ImplItemRef) -> ty::A
container: ty::AssocItemContainer::Impl,
}
}
struct RPITVisitor {
rpits: FxIndexSet<LocalDefId>,
struct RPITVisitor<'tcx> {
tcx: TyCtxt<'tcx>,
synthetics: Vec<LocalDefId>,
data: DefPathData,
disambiguator: DisambiguatorState,
}

impl<'tcx> Visitor<'tcx> for RPITVisitor {
fn visit_ty(&mut self, ty: &'tcx hir::Ty<'tcx, AmbigArg>) {
if let hir::TyKind::OpaqueDef(opaq) = ty.kind
&& self.rpits.insert(opaq.def_id)
{
for bound in opaq.bounds {
intravisit::walk_param_bound(self, bound);
}
}
intravisit::walk_ty(self, ty)
impl<'tcx> Visitor<'tcx> for RPITVisitor<'tcx> {
fn visit_opaque_ty(&mut self, opaque: &'tcx hir::OpaqueTy<'tcx>) -> Self::Result {
self.synthetics.push(associated_type_for_impl_trait_in_trait(
self.tcx,
opaque.def_id,
self.data,
&mut self.disambiguator,
));
intravisit::walk_opaque_ty(self, opaque)
}
}

Expand All @@ -194,14 +194,18 @@ fn associated_types_for_impl_traits_in_associated_fn(

match tcx.def_kind(parent_def_id) {
DefKind::Trait => {
let mut visitor = RPITVisitor { rpits: FxIndexSet::default() };

if let Some(output) = tcx.hir_get_fn_output(fn_def_id) {
let data = DefPathData::AnonAssocTy(tcx.item_name(fn_def_id.to_def_id()));
let mut visitor = RPITVisitor {
tcx,
synthetics: vec![],
data,
disambiguator: DisambiguatorState::with(parent_def_id, data, 0),
};
visitor.visit_fn_ret_ty(output);

tcx.arena.alloc_from_iter(visitor.rpits.iter().map(|opaque_ty_def_id| {
tcx.associated_type_for_impl_trait_in_trait(opaque_ty_def_id).to_def_id()
}))
tcx.arena.alloc_from_iter(
visitor.synthetics.into_iter().map(|def_id| def_id.to_def_id()),
)
} else {
&[]
}
Expand All @@ -211,7 +215,6 @@ fn associated_types_for_impl_traits_in_associated_fn(
let Some(trait_fn_def_id) = tcx.associated_item(fn_def_id).trait_item_def_id else {
return &[];
};

tcx.arena.alloc_from_iter(
tcx.associated_types_for_impl_traits_in_associated_fn(trait_fn_def_id).iter().map(
move |&trait_assoc_def_id| {
Expand All @@ -236,6 +239,8 @@ fn associated_types_for_impl_traits_in_associated_fn(
fn associated_type_for_impl_trait_in_trait(
tcx: TyCtxt<'_>,
opaque_ty_def_id: LocalDefId,
data: DefPathData,
disambiguator: &mut DisambiguatorState,
) -> LocalDefId {
let (hir::OpaqueTyOrigin::FnReturn { parent: fn_def_id, .. }
| hir::OpaqueTyOrigin::AsyncFn { parent: fn_def_id, .. }) =
Expand All @@ -246,22 +251,15 @@ fn associated_type_for_impl_trait_in_trait(
let trait_def_id = tcx.local_parent(fn_def_id);
assert_eq!(tcx.def_kind(trait_def_id), DefKind::Trait);

// Collect all opaque types in return position for the method and use
// the index as the disambiguator to make an unique def path.
let mut visitor = RPITVisitor { rpits: FxIndexSet::default() };
visitor.visit_fn_ret_ty(tcx.hir_get_fn_output(fn_def_id).unwrap());
let disambiguator = visitor.rpits.get_index_of(&opaque_ty_def_id).unwrap().try_into().unwrap();

let span = tcx.def_span(opaque_ty_def_id);
// Also use the method name to create an unique def path.
let data = DefPathData::AnonAssocTy(tcx.item_name(fn_def_id.to_def_id()));
let trait_assoc_ty = tcx.at(span).create_def(
trait_def_id,
// No name because this is an anonymous associated type.
None,
DefKind::AssocTy,
Some(data),
&mut DisambiguatorState::with(trait_def_id, data, disambiguator),
disambiguator,
);

let local_def_id = trait_assoc_ty.def_id();
Expand Down
55 changes: 55 additions & 0 deletions library/alloc/src/vec/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3031,6 +3031,61 @@ impl<T, A: Allocator> Vec<T, A> {
(initialized, spare, &mut self.len)
}
}

/// Groups every `N` elements in the `Vec<T>` into chunks to produce a `Vec<[T; N]>`, dropping
/// elements in the remainder. `N` must be greater than zero.
///
/// If the capacity is not a multiple of the chunk size, the buffer will shrink down to the
/// nearest multiple with a reallocation or deallocation.
///
/// This function can be used to reverse [`Vec::into_flattened`].
///
/// # Examples
///
/// ```
/// #![feature(vec_into_chunks)]
///
/// let vec = vec![0, 1, 2, 3, 4, 5, 6, 7];
/// assert_eq!(vec.into_chunks::<3>(), [[0, 1, 2], [3, 4, 5]]);
///
/// let vec = vec![0, 1, 2, 3];
/// let chunks: Vec<[u8; 10]> = vec.into_chunks();
/// assert!(chunks.is_empty());
///
/// let flat = vec![0; 8 * 8 * 8];
/// let reshaped: Vec<[[[u8; 8]; 8]; 8]> = flat.into_chunks().into_chunks().into_chunks();
/// assert_eq!(reshaped.len(), 1);
/// ```
#[cfg(not(no_global_oom_handling))]
#[unstable(feature = "vec_into_chunks", issue = "142137")]
pub fn into_chunks<const N: usize>(mut self) -> Vec<[T; N], A> {
const {
assert!(N != 0, "chunk size must be greater than zero");
}

let (len, cap) = (self.len(), self.capacity());

let len_remainder = len % N;
if len_remainder != 0 {
self.truncate(len - len_remainder);
}

let cap_remainder = cap % N;
if !T::IS_ZST && cap_remainder != 0 {
self.buf.shrink_to_fit(cap - cap_remainder);
}

let (ptr, _, _, alloc) = self.into_raw_parts_with_alloc();

// SAFETY:
// - `ptr` and `alloc` were just returned from `self.into_raw_parts_with_alloc()`
// - `[T; N]` has the same alignment as `T`
// - `size_of::<[T; N]>() * cap / N == size_of::<T>() * cap`
// - `len / N <= cap / N` because `len <= cap`
// - the allocated memory consists of `len / N` valid values of type `[T; N]`
// - `cap / N` fits the size of the allocated memory after shrinking
unsafe { Vec::from_raw_parts_in(ptr.cast(), len / N, cap / N, alloc) }
}
}

impl<T: Clone, A: Allocator> Vec<T, A> {
Expand Down
Loading
Loading