Auto merge of #144130 - matthiaskrgr:rollup-t75stad, r=matthiaskrgr

Rollup of 11 pull requests

Successful merges:

 - rust-lang/rust#143280 (Remove duplicate error about raw underscore lifetime)
 - rust-lang/rust#143649 (Add test for `default_field_values` and `const_default`)
 - rust-lang/rust#143699 (Make `AsyncDrop` check that it's being implemented on a local ADT)
 - rust-lang/rust#143908 (`tests/ui`: A New Order [0/28] )
 - rust-lang/rust#143909 (docs(alloc::fmt): Make type optional, instead of matching empty string)
 - rust-lang/rust#143925 (Make slice comparisons const)
 - rust-lang/rust#143997 (Use $crate in macros for rustc_public (aka stable_mir))
 - rust-lang/rust#144013 (resolve: Make disambiguators for underscore bindings module-local)
 - rust-lang/rust#144029 (Fix wrong messages from methods with the same name from different traits)
 - rust-lang/rust#144063 (Add myself to the `infra-ci` reviewer group and adjust some infra auto-labels)
 - rust-lang/rust#144069 (ci: use windows 22 for all free runners)

r? `@ghost`
`@rustbot` modify labels: rollup
This commit is contained in:
bors 2025-07-18 13:26:31 +00:00
commit 82310651b9
64 changed files with 427 additions and 155 deletions

View file

@ -23,6 +23,7 @@ pub(crate) fn expand_deriving_copy(
methods: Vec::new(),
associated_types: Vec::new(),
is_const,
is_staged_api_crate: cx.ecfg.features.staged_api(),
};
trait_def.expand(cx, mitem, item, push);
@ -46,6 +47,7 @@ pub(crate) fn expand_deriving_const_param_ty(
methods: Vec::new(),
associated_types: Vec::new(),
is_const,
is_staged_api_crate: cx.ecfg.features.staged_api(),
};
trait_def.expand(cx, mitem, item, push);
@ -60,6 +62,7 @@ pub(crate) fn expand_deriving_const_param_ty(
methods: Vec::new(),
associated_types: Vec::new(),
is_const,
is_staged_api_crate: cx.ecfg.features.staged_api(),
};
trait_def.expand(cx, mitem, item, push);
@ -83,6 +86,7 @@ pub(crate) fn expand_deriving_unsized_const_param_ty(
methods: Vec::new(),
associated_types: Vec::new(),
is_const,
is_staged_api_crate: cx.ecfg.features.staged_api(),
};
trait_def.expand(cx, mitem, item, push);

View file

@ -87,6 +87,7 @@ pub(crate) fn expand_deriving_clone(
}],
associated_types: Vec::new(),
is_const,
is_staged_api_crate: cx.ecfg.features.staged_api(),
};
trait_def.expand_ext(cx, mitem, item, push, is_simple)

View file

@ -43,6 +43,7 @@ pub(crate) fn expand_deriving_eq(
}],
associated_types: Vec::new(),
is_const,
is_staged_api_crate: cx.ecfg.features.staged_api(),
};
trait_def.expand_ext(cx, mitem, item, push, true)
}

View file

@ -34,6 +34,7 @@ pub(crate) fn expand_deriving_ord(
}],
associated_types: Vec::new(),
is_const,
is_staged_api_crate: cx.ecfg.features.staged_api(),
};
trait_def.expand(cx, mitem, item, push)

View file

@ -30,6 +30,7 @@ pub(crate) fn expand_deriving_partial_eq(
methods: Vec::new(),
associated_types: Vec::new(),
is_const: false,
is_staged_api_crate: cx.ecfg.features.staged_api(),
};
structural_trait_def.expand(cx, mitem, item, push);
@ -58,6 +59,7 @@ pub(crate) fn expand_deriving_partial_eq(
methods,
associated_types: Vec::new(),
is_const,
is_staged_api_crate: cx.ecfg.features.staged_api(),
};
trait_def.expand(cx, mitem, item, push)
}

View file

@ -64,6 +64,7 @@ pub(crate) fn expand_deriving_partial_ord(
methods: vec![partial_cmp_def],
associated_types: Vec::new(),
is_const,
is_staged_api_crate: cx.ecfg.features.staged_api(),
};
trait_def.expand(cx, mitem, item, push)
}

View file

@ -41,6 +41,7 @@ pub(crate) fn expand_deriving_debug(
}],
associated_types: Vec::new(),
is_const,
is_staged_api_crate: cx.ecfg.features.staged_api(),
};
trait_def.expand(cx, mitem, item, push)
}

View file

@ -51,6 +51,7 @@ pub(crate) fn expand_deriving_default(
}],
associated_types: Vec::new(),
is_const,
is_staged_api_crate: cx.ecfg.features.staged_api(),
};
trait_def.expand(cx, mitem, item, push)
}

View file

@ -181,9 +181,11 @@ use std::{iter, vec};
pub(crate) use StaticFields::*;
pub(crate) use SubstructureFields::*;
use rustc_ast::ptr::P;
use rustc_ast::token::{IdentIsRaw, LitKind, Token, TokenKind};
use rustc_ast::tokenstream::{DelimSpan, Spacing, TokenTree};
use rustc_ast::{
self as ast, AnonConst, BindingMode, ByRef, EnumDef, Expr, GenericArg, GenericParamKind,
Generics, Mutability, PatKind, VariantData,
self as ast, AnonConst, AttrArgs, BindingMode, ByRef, DelimArgs, EnumDef, Expr, GenericArg,
GenericParamKind, Generics, Mutability, PatKind, Safety, VariantData,
};
use rustc_attr_data_structures::{AttributeKind, ReprPacked};
use rustc_attr_parsing::AttributeParser;
@ -222,6 +224,8 @@ pub(crate) struct TraitDef<'a> {
pub associated_types: Vec<(Ident, Ty)>,
pub is_const: bool,
pub is_staged_api_crate: bool,
}
pub(crate) struct MethodDef<'a> {
@ -784,8 +788,45 @@ impl<'a> TraitDef<'a> {
// Create the type of `self`.
let path = cx.path_all(self.span, false, vec![type_ident], self_params);
let self_type = cx.ty_path(path);
let rustc_const_unstable =
cx.path_ident(self.span, Ident::new(sym::rustc_const_unstable, self.span));
let mut attrs = thin_vec![cx.attr_word(sym::automatically_derived, self.span),];
// Only add `rustc_const_unstable` attributes if `derive_const` is used within libcore/libstd,
// Other crates don't need stability attributes, so adding them is not useful, but libcore needs them
// on all const trait impls.
if self.is_const && self.is_staged_api_crate {
attrs.push(
cx.attr_nested(
rustc_ast::AttrItem {
unsafety: Safety::Default,
path: rustc_const_unstable,
args: AttrArgs::Delimited(DelimArgs {
dspan: DelimSpan::from_single(self.span),
delim: rustc_ast::token::Delimiter::Parenthesis,
tokens: [
TokenKind::Ident(sym::feature, IdentIsRaw::No),
TokenKind::Eq,
TokenKind::lit(LitKind::Str, sym::derive_const, None),
TokenKind::Comma,
TokenKind::Ident(sym::issue, IdentIsRaw::No),
TokenKind::Eq,
TokenKind::lit(LitKind::Str, sym::derive_const_issue, None),
]
.into_iter()
.map(|kind| {
TokenTree::Token(Token { kind, span: self.span }, Spacing::Alone)
})
.collect(),
}),
tokens: None,
},
self.span,
),
)
}
let attrs = thin_vec![cx.attr_word(sym::automatically_derived, self.span),];
let opt_trait_ref = Some(trait_ref);
cx.item(

View file

@ -41,6 +41,7 @@ pub(crate) fn expand_deriving_hash(
}],
associated_types: Vec::new(),
is_const,
is_staged_api_crate: cx.ecfg.features.staged_api(),
};
hash_trait_def.expand(cx, mitem, item, push);

View file

@ -3,8 +3,8 @@ use rustc_ast::token::Delimiter;
use rustc_ast::tokenstream::TokenStream;
use rustc_ast::util::literal;
use rustc_ast::{
self as ast, AnonConst, AttrVec, BlockCheckMode, Expr, LocalKind, MatchKind, PatKind, UnOp,
attr, token, tokenstream,
self as ast, AnonConst, AttrItem, AttrVec, BlockCheckMode, Expr, LocalKind, MatchKind, PatKind,
UnOp, attr, token, tokenstream,
};
use rustc_span::source_map::Spanned;
use rustc_span::{DUMMY_SP, Ident, Span, Symbol, kw, sym};
@ -766,4 +766,10 @@ impl<'a> ExtCtxt<'a> {
span,
)
}
// Builds an attribute fully manually.
pub fn attr_nested(&self, inner: AttrItem, span: Span) -> ast::Attribute {
let g = &self.sess.psess.attr_id_generator;
attr::mk_attr_from_item(g, inner, None, ast::AttrStyle::Outer, span)
}
}

View file

@ -158,7 +158,7 @@ hir_analysis_dispatch_from_dyn_zst = the trait `DispatchFromDyn` may only be imp
hir_analysis_drop_impl_negative = negative `Drop` impls are not supported
hir_analysis_drop_impl_on_wrong_item =
the `Drop` trait may only be implemented for local structs, enums, and unions
the `{$trait_}` trait may only be implemented for local structs, enums, and unions
.label = must be a struct, enum, or union in the current crate
hir_analysis_drop_impl_reservation = reservation `Drop` impls are not supported

View file

@ -37,6 +37,7 @@ pub(super) fn check_trait<'tcx>(
let lang_items = tcx.lang_items();
let checker = Checker { tcx, trait_def_id, impl_def_id, impl_header };
checker.check(lang_items.drop_trait(), visit_implementation_of_drop)?;
checker.check(lang_items.async_drop_trait(), visit_implementation_of_drop)?;
checker.check(lang_items.copy_trait(), visit_implementation_of_copy)?;
checker.check(lang_items.const_param_ty_trait(), |checker| {
visit_implementation_of_const_param_ty(checker, LangItem::ConstParamTy)
@ -83,7 +84,10 @@ fn visit_implementation_of_drop(checker: &Checker<'_>) -> Result<(), ErrorGuaran
let impl_ = tcx.hir_expect_item(impl_did).expect_impl();
Err(tcx.dcx().emit_err(errors::DropImplOnWrongItem { span: impl_.self_ty.span }))
Err(tcx.dcx().emit_err(errors::DropImplOnWrongItem {
span: impl_.self_ty.span,
trait_: tcx.item_name(checker.impl_header.trait_ref.skip_binder().def_id),
}))
}
fn visit_implementation_of_copy(checker: &Checker<'_>) -> Result<(), ErrorGuaranteed> {

View file

@ -205,6 +205,7 @@ pub(crate) struct DropImplOnWrongItem {
#[primary_span]
#[label]
pub span: Span,
pub trait_: Symbol,
}
#[derive(Diagnostic)]

View file

@ -1650,7 +1650,8 @@ impl<'a, 'tcx> ProbeContext<'a, 'tcx> {
}
}
let sources = candidates.iter().map(|p| self.candidate_source(p, self_ty)).collect();
let sources =
applicable_candidates.iter().map(|p| self.candidate_source(p.0, self_ty)).collect();
return Some(Err(MethodError::Ambiguity(sources)));
}

View file

@ -144,10 +144,10 @@ where
#[macro_export]
macro_rules! run {
($args:expr, $callback_fn:ident) => {
run_driver!($args, || $callback_fn())
$crate::run_driver!($args, || $callback_fn())
};
($args:expr, $callback:expr) => {
run_driver!($args, $callback)
$crate::run_driver!($args, $callback)
};
}
@ -158,10 +158,10 @@ macro_rules! run {
#[macro_export]
macro_rules! run_with_tcx {
($args:expr, $callback_fn:ident) => {
run_driver!($args, |tcx| $callback_fn(tcx), with_tcx)
$crate::run_driver!($args, |tcx| $callback_fn(tcx), with_tcx)
};
($args:expr, $callback:expr) => {
run_driver!($args, $callback, with_tcx)
$crate::run_driver!($args, $callback, with_tcx)
};
}
@ -191,11 +191,11 @@ macro_rules! run_driver {
use rustc_public::CompilerError;
use std::ops::ControlFlow;
pub struct StableMir<B = (), C = (), F = fn($(optional!($with_tcx TyCtxt))?) -> ControlFlow<B, C>>
pub struct StableMir<B = (), C = (), F = fn($($crate::optional!($with_tcx TyCtxt))?) -> ControlFlow<B, C>>
where
B: Send,
C: Send,
F: FnOnce($(optional!($with_tcx TyCtxt))?) -> ControlFlow<B, C> + Send,
F: FnOnce($($crate::optional!($with_tcx TyCtxt))?) -> ControlFlow<B, C> + Send,
{
callback: Option<F>,
result: Option<ControlFlow<B, C>>,
@ -205,7 +205,7 @@ macro_rules! run_driver {
where
B: Send,
C: Send,
F: FnOnce($(optional!($with_tcx TyCtxt))?) -> ControlFlow<B, C> + Send,
F: FnOnce($($crate::optional!($with_tcx TyCtxt))?) -> ControlFlow<B, C> + Send,
{
/// Creates a new `StableMir` instance, with given test_function and arguments.
pub fn new(callback: F) -> Self {
@ -240,7 +240,7 @@ macro_rules! run_driver {
where
B: Send,
C: Send,
F: FnOnce($(optional!($with_tcx TyCtxt))?) -> ControlFlow<B, C> + Send,
F: FnOnce($($crate::optional!($with_tcx TyCtxt))?) -> ControlFlow<B, C> + Send,
{
/// Called after analysis. Return value instructs the compiler whether to
/// continue the compilation afterwards (defaults to `Compilation::Continue`)
@ -251,7 +251,7 @@ macro_rules! run_driver {
) -> Compilation {
if let Some(callback) = self.callback.take() {
rustc_internal::run(tcx, || {
self.result = Some(callback($(optional!($with_tcx tcx))?));
self.result = Some(callback($($crate::optional!($with_tcx tcx))?));
})
.unwrap();
if self.result.as_ref().is_some_and(|val| val.is_continue()) {

View file

@ -49,8 +49,7 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
ns: Namespace,
binding: NameBinding<'ra>,
) {
let key = self.new_disambiguated_key(ident, ns);
if let Err(old_binding) = self.try_define(parent, key, binding, false) {
if let Err(old_binding) = self.try_define(parent, ident, ns, binding, false) {
self.report_conflict(parent, ident, ns, old_binding, binding);
}
}
@ -442,16 +441,18 @@ impl<'a, 'ra, 'tcx> BuildReducedGraphVisitor<'a, 'ra, 'tcx> {
self.r.indeterminate_imports.push(import);
match import.kind {
// Don't add unresolved underscore imports to modules
ImportKind::Single { target: Ident { name: kw::Underscore, .. }, .. } => {}
ImportKind::Single { target, type_ns_only, .. } => {
self.r.per_ns(|this, ns| {
if !type_ns_only || ns == TypeNS {
let key = BindingKey::new(target, ns);
let mut resolution = this.resolution(current_module, key).borrow_mut();
resolution.single_imports.insert(import);
}
});
// Don't add underscore imports to `single_imports`
// because they cannot define any usable names.
if target.name != kw::Underscore {
self.r.per_ns(|this, ns| {
if !type_ns_only || ns == TypeNS {
let key = BindingKey::new(target, ns);
let mut resolution = this.resolution(current_module, key).borrow_mut();
resolution.single_imports.insert(import);
}
});
}
}
// We don't add prelude imports to the globs since they only affect lexical scopes,
// which are not relevant to import resolution.
@ -1405,9 +1406,12 @@ impl<'a, 'ra, 'tcx> Visitor<'a> for BuildReducedGraphVisitor<'a, 'ra, 'tcx> {
let parent = self.parent_scope.module;
let expansion = self.parent_scope.expansion;
self.r.define(parent, ident, ns, self.res(def_id), vis, item.span, expansion);
} else if !matches!(&item.kind, AssocItemKind::Delegation(deleg) if deleg.from_glob) {
} else if !matches!(&item.kind, AssocItemKind::Delegation(deleg) if deleg.from_glob)
&& ident.name != kw::Underscore
{
// Don't add underscore names, they cannot be looked up anyway.
let impl_def_id = self.r.tcx.local_parent(local_def_id);
let key = BindingKey::new(ident.normalize_to_macros_2_0(), ns);
let key = BindingKey::new(ident, ns);
self.r.impl_binding_keys.entry(impl_def_id).or_default().insert(key);
}

View file

@ -25,7 +25,7 @@ use rustc_span::{Ident, Span, Symbol, kw, sym};
use smallvec::SmallVec;
use tracing::debug;
use crate::Namespace::*;
use crate::Namespace::{self, *};
use crate::diagnostics::{DiagMode, Suggestion, import_candidates};
use crate::errors::{
CannotBeReexportedCratePublic, CannotBeReexportedCratePublicNS, CannotBeReexportedPrivate,
@ -338,13 +338,20 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
pub(crate) fn try_define(
&mut self,
module: Module<'ra>,
key: BindingKey,
ident: Ident,
ns: Namespace,
binding: NameBinding<'ra>,
warn_ambiguity: bool,
) -> Result<(), NameBinding<'ra>> {
let res = binding.res();
self.check_reserved_macro_name(key.ident, res);
self.check_reserved_macro_name(ident, res);
self.set_binding_parent_module(binding, module);
// Even if underscore names cannot be looked up, we still need to add them to modules,
// because they can be fetched by glob imports from those modules, and bring traits
// into scope both directly and through glob imports.
let key = BindingKey::new_disambiguated(ident, ns, || {
(module.0.0.lazy_resolutions.borrow().len() + 1).try_into().unwrap()
});
self.update_resolution(module, key, warn_ambiguity, |this, resolution| {
if let Some(old_binding) = resolution.best_binding() {
if res == Res::Err && old_binding.res() != Res::Err {
@ -383,7 +390,7 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
(old_glob @ true, false) | (old_glob @ false, true) => {
let (glob_binding, non_glob_binding) =
if old_glob { (old_binding, binding) } else { (binding, old_binding) };
if key.ns == MacroNS
if ns == MacroNS
&& non_glob_binding.expansion != LocalExpnId::ROOT
&& glob_binding.res() != non_glob_binding.res()
{
@ -489,10 +496,10 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
};
if self.is_accessible_from(binding.vis, scope) {
let imported_binding = self.import(binding, *import);
let key = BindingKey { ident, ..key };
let _ = self.try_define(
import.parent_scope.module,
key,
ident,
key.ns,
imported_binding,
warn_ambiguity,
);
@ -514,11 +521,15 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
let dummy_binding = self.dummy_binding;
let dummy_binding = self.import(dummy_binding, import);
self.per_ns(|this, ns| {
let key = BindingKey::new(target, ns);
let _ = this.try_define(import.parent_scope.module, key, dummy_binding, false);
this.update_resolution(import.parent_scope.module, key, false, |_, resolution| {
resolution.single_imports.swap_remove(&import);
})
let module = import.parent_scope.module;
let _ = this.try_define(module, target, ns, dummy_binding, false);
// Don't remove underscores from `single_imports`, they were never added.
if target.name != kw::Underscore {
let key = BindingKey::new(target, ns);
this.update_resolution(module, key, false, |_, resolution| {
resolution.single_imports.swap_remove(&import);
})
}
});
self.record_use(target, dummy_binding, Used::Other);
} else if import.imported_module.get().is_none() {
@ -895,7 +906,7 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
PendingBinding::Ready(Some(imported_binding))
}
Err(Determinacy::Determined) => {
// Don't update the resolution for underscores, because it was never added.
// Don't remove underscores from `single_imports`, they were never added.
if target.name != kw::Underscore {
let key = BindingKey::new(target, ns);
this.update_resolution(parent, key, false, |_, resolution| {
@ -1510,7 +1521,8 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
.is_some_and(|binding| binding.warn_ambiguity_recursive());
let _ = self.try_define(
import.parent_scope.module,
key,
key.ident,
key.ns,
imported_binding,
warn_ambiguity,
);

View file

@ -2899,9 +2899,21 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> {
}
if param.ident.name == kw::UnderscoreLifetime {
// To avoid emitting two similar errors,
// we need to check if the span is a raw underscore lifetime, see issue #143152
let is_raw_underscore_lifetime = self
.r
.tcx
.sess
.psess
.raw_identifier_spans
.iter()
.any(|span| span == param.span());
self.r
.dcx()
.emit_err(errors::UnderscoreLifetimeIsReserved { span: param.ident.span });
.create_err(errors::UnderscoreLifetimeIsReserved { span: param.ident.span })
.emit_unless(is_raw_underscore_lifetime);
// Record lifetime res, so lowering knows there is something fishy.
self.record_lifetime_param(param.id, LifetimeRes::Error);
continue;

View file

@ -532,15 +532,26 @@ struct BindingKey {
/// identifier.
ident: Ident,
ns: Namespace,
/// 0 if ident is not `_`, otherwise a value that's unique to the specific
/// `_` in the expanded AST that introduced this binding.
/// When we add an underscore binding (with ident `_`) to some module, this field has
/// a non-zero value that uniquely identifies this binding in that module.
/// For non-underscore bindings this field is zero.
/// When a key is constructed for name lookup (as opposed to name definition), this field is
/// also zero, even for underscore names, so for underscores the lookup will never succeed.
disambiguator: u32,
}
impl BindingKey {
fn new(ident: Ident, ns: Namespace) -> Self {
let ident = ident.normalize_to_macros_2_0();
BindingKey { ident, ns, disambiguator: 0 }
BindingKey { ident: ident.normalize_to_macros_2_0(), ns, disambiguator: 0 }
}
fn new_disambiguated(
ident: Ident,
ns: Namespace,
disambiguator: impl FnOnce() -> u32,
) -> BindingKey {
let disambiguator = if ident.name == kw::Underscore { disambiguator() } else { 0 };
BindingKey { ident: ident.normalize_to_macros_2_0(), ns, disambiguator }
}
}
@ -1087,8 +1098,6 @@ pub struct Resolver<'ra, 'tcx> {
extern_module_map: RefCell<FxIndexMap<DefId, Module<'ra>>>,
binding_parent_modules: FxHashMap<NameBinding<'ra>, Module<'ra>>,
underscore_disambiguator: u32,
/// Maps glob imports to the names of items actually imported.
glob_map: FxIndexMap<LocalDefId, FxIndexSet<Symbol>>,
glob_error: Option<ErrorGuaranteed>,
@ -1501,7 +1510,6 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
extern_crate_map: Default::default(),
module_children: Default::default(),
trait_map: NodeMap::default(),
underscore_disambiguator: 0,
empty_module,
local_module_map,
extern_module_map: Default::default(),
@ -1887,17 +1895,6 @@ impl<'ra, 'tcx> Resolver<'ra, 'tcx> {
import_ids
}
fn new_disambiguated_key(&mut self, ident: Ident, ns: Namespace) -> BindingKey {
let ident = ident.normalize_to_macros_2_0();
let disambiguator = if ident.name == kw::Underscore {
self.underscore_disambiguator += 1;
self.underscore_disambiguator
} else {
0
};
BindingKey { ident, ns, disambiguator }
}
fn resolutions(&mut self, module: Module<'ra>) -> &'ra Resolutions<'ra> {
if module.populate_on_access.get() {
module.populate_on_access.set(false);

View file

@ -530,7 +530,7 @@ impl<'ra, 'tcx> ResolverExpand for Resolver<'ra, 'tcx> {
target_trait.for_each_child(self, |this, ident, ns, _binding| {
// FIXME: Adjust hygiene for idents from globs, like for glob imports.
if let Some(overriding_keys) = this.impl_binding_keys.get(&impl_def_id)
&& overriding_keys.contains(&BindingKey::new(ident.normalize_to_macros_2_0(), ns))
&& overriding_keys.contains(&BindingKey::new(ident, ns))
{
// The name is overridden, do not produce it from the glob delegation.
} else {

View file

@ -840,6 +840,7 @@ symbols! {
derive,
derive_coerce_pointee,
derive_const,
derive_const_issue: "118304",
derive_default_enum,
derive_smart_pointer,
destruct,

View file

@ -348,13 +348,13 @@
//! format := '{' [ argument ] [ ':' format_spec ] [ ws ] * '}'
//! argument := integer | identifier
//!
//! format_spec := [[fill]align][sign]['#']['0'][width]['.' precision]type
//! format_spec := [[fill]align][sign]['#']['0'][width]['.' precision][type]
//! fill := character
//! align := '<' | '^' | '>'
//! sign := '+' | '-'
//! width := count
//! precision := count | '*'
//! type := '' | '?' | 'x?' | 'X?' | identifier
//! type := '?' | 'x?' | 'X?' | identifier
//! count := parameter | integer
//! parameter := argument '$'
//! ```

View file

@ -381,7 +381,8 @@ pub struct AssertParamIsEq<T: Eq + PointeeSized> {
///
/// assert_eq!(2.cmp(&1), Ordering::Greater);
/// ```
#[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Debug, Hash)]
#[derive(Clone, Copy, Eq, PartialOrd, Ord, Debug, Hash)]
#[derive_const(PartialEq)]
#[stable(feature = "rust1", since = "1.0.0")]
// This is a lang item only so that `BinOp::Cmp` in MIR can return it.
// It has no special behavior, but does require that the three variants

View file

@ -17,11 +17,15 @@ use crate::num::NonZero;
/// - Neither `Self` nor `Rhs` have provenance, so integer comparisons are correct.
/// - `<Self as PartialEq<Rhs>>::{eq,ne}` are equivalent to comparing the bytes.
#[rustc_specialization_trait]
pub(crate) unsafe trait BytewiseEq<Rhs = Self>: PartialEq<Rhs> + Sized {}
#[const_trait]
pub(crate) unsafe trait BytewiseEq<Rhs = Self>:
~const PartialEq<Rhs> + Sized
{
}
macro_rules! is_bytewise_comparable {
($($t:ty),+ $(,)?) => {$(
unsafe impl BytewiseEq for $t {}
unsafe impl const BytewiseEq for $t {}
)+};
}

View file

@ -2208,6 +2208,7 @@ pub const unsafe fn raw_eq<T>(a: &T, b: &T) -> bool;
/// [valid]: crate::ptr#safety
#[rustc_nounwind]
#[rustc_intrinsic]
#[rustc_const_unstable(feature = "const_cmp", issue = "143800")]
pub const unsafe fn compare_bytes(left: *const u8, right: *const u8, bytes: usize) -> i32;
/// See documentation of [`std::hint::black_box`] for details.

View file

@ -103,6 +103,7 @@
#![feature(cfg_select)]
#![feature(cfg_target_has_reliable_f16_f128)]
#![feature(const_carrying_mul_add)]
#![feature(const_cmp)]
#![feature(const_destruct)]
#![feature(const_eval_select)]
#![feature(core_intrinsics)]
@ -146,6 +147,7 @@
#![feature(const_trait_impl)]
#![feature(decl_macro)]
#![feature(deprecated_suggestion)]
#![feature(derive_const)]
#![feature(doc_cfg)]
#![feature(doc_cfg_hide)]
#![feature(doc_notable_trait)]

View file

@ -1615,7 +1615,7 @@ pub(crate) mod builtin {
/// See [the reference] for more info.
///
/// [the reference]: ../../../reference/attributes/derive.html
#[unstable(feature = "derive_const", issue = "none")]
#[unstable(feature = "derive_const", issue = "118304")]
#[rustc_builtin_macro]
pub macro derive_const($item:item) {
/* compiler built-in */

View file

@ -200,9 +200,10 @@ impl<T> UseCloned for NonZero<T> where T: ZeroablePrimitive {}
impl<T> Copy for NonZero<T> where T: ZeroablePrimitive {}
#[stable(feature = "nonzero", since = "1.28.0")]
impl<T> PartialEq for NonZero<T>
#[rustc_const_unstable(feature = "const_cmp", issue = "143800")]
impl<T> const PartialEq for NonZero<T>
where
T: ZeroablePrimitive + PartialEq,
T: ZeroablePrimitive + ~const PartialEq,
{
#[inline]
fn eq(&self, other: &Self) -> bool {

View file

@ -2300,7 +2300,8 @@ impl<'a, T> From<&'a mut Option<T>> for Option<&'a mut T> {
#[stable(feature = "rust1", since = "1.0.0")]
impl<T> crate::marker::StructuralPartialEq for Option<T> {}
#[stable(feature = "rust1", since = "1.0.0")]
impl<T: PartialEq> PartialEq for Option<T> {
#[rustc_const_unstable(feature = "const_cmp", issue = "143800")]
impl<T: ~const PartialEq> const PartialEq for Option<T> {
#[inline]
fn eq(&self, other: &Self) -> bool {
// Spelling out the cases explicitly optimizes better than

View file

@ -80,7 +80,7 @@ pub use crate::macros::builtin::{
alloc_error_handler, bench, derive, global_allocator, test, test_case,
};
#[unstable(feature = "derive_const", issue = "none")]
#[unstable(feature = "derive_const", issue = "118304")]
pub use crate::macros::builtin::derive_const;
#[unstable(

View file

@ -8,9 +8,10 @@ use crate::num::NonZero;
use crate::ops::ControlFlow;
#[stable(feature = "rust1", since = "1.0.0")]
impl<T, U> PartialEq<[U]> for [T]
#[rustc_const_unstable(feature = "const_cmp", issue = "143800")]
impl<T, U> const PartialEq<[U]> for [T]
where
T: PartialEq<U>,
T: ~const PartialEq<U>,
{
fn eq(&self, other: &[U]) -> bool {
SlicePartialEq::equal(self, other)
@ -94,6 +95,8 @@ impl<T: PartialOrd> PartialOrd for [T] {
#[doc(hidden)]
// intermediate trait for specialization of slice's PartialEq
#[const_trait]
#[rustc_const_unstable(feature = "const_cmp", issue = "143800")]
trait SlicePartialEq<B> {
fn equal(&self, other: &[B]) -> bool;
@ -103,9 +106,10 @@ trait SlicePartialEq<B> {
}
// Generic slice equality
impl<A, B> SlicePartialEq<B> for [A]
#[rustc_const_unstable(feature = "const_cmp", issue = "143800")]
impl<A, B> const SlicePartialEq<B> for [A]
where
A: PartialEq<B>,
A: ~const PartialEq<B>,
{
default fn equal(&self, other: &[B]) -> bool {
if self.len() != other.len() {
@ -115,11 +119,14 @@ where
// Implemented as explicit indexing rather
// than zipped iterators for performance reasons.
// See PR https://github.com/rust-lang/rust/pull/116846
for idx in 0..self.len() {
// FIXME(const_hack): make this a `for idx in 0..self.len()` loop.
let mut idx = 0;
while idx < self.len() {
// bound checks are optimized away
if self[idx] != other[idx] {
return false;
}
idx += 1;
}
true
@ -128,9 +135,10 @@ where
// When each element can be compared byte-wise, we can compare all the bytes
// from the whole size in one call to the intrinsics.
impl<A, B> SlicePartialEq<B> for [A]
#[rustc_const_unstable(feature = "const_cmp", issue = "143800")]
impl<A, B> const SlicePartialEq<B> for [A]
where
A: BytewiseEq<B>,
A: ~const BytewiseEq<B>,
{
fn equal(&self, other: &[B]) -> bool {
if self.len() != other.len() {

View file

@ -23,7 +23,8 @@ impl Ord for str {
}
#[stable(feature = "rust1", since = "1.0.0")]
impl PartialEq for str {
#[rustc_const_unstable(feature = "const_cmp", issue = "143800")]
impl const PartialEq for str {
#[inline]
fn eq(&self, other: &str) -> bool {
self.as_bytes() == other.as_bytes()

View file

@ -67,7 +67,7 @@ pub use core::prelude::v1::{
alloc_error_handler, bench, derive, global_allocator, test, test_case,
};
#[unstable(feature = "derive_const", issue = "none")]
#[unstable(feature = "derive_const", issue = "118304")]
pub use core::prelude::v1::derive_const;
// Do not `doc(no_inline)` either.

View file

@ -34,6 +34,8 @@ runners:
os: windows-2022
<<: *base-job
# NOTE: windows-2025 has less disk space available than windows-2022,
# because the D drive is missing.
- &job-windows-25
os: windows-2025
<<: *base-job
@ -542,13 +544,13 @@ auto:
env:
RUST_CONFIGURE_ARGS: --build=x86_64-pc-windows-msvc --enable-sanitizers --enable-profiler
SCRIPT: make ci-msvc-py
<<: *job-windows-25
<<: *job-windows
- name: x86_64-msvc-2
env:
RUST_CONFIGURE_ARGS: --build=x86_64-pc-windows-msvc --enable-sanitizers --enable-profiler
SCRIPT: make ci-msvc-ps1
<<: *job-windows-25
<<: *job-windows
# i686-msvc is split into two jobs to run tests in parallel.
- name: i686-msvc-1

View file

@ -0,0 +1,21 @@
//@ edition: 2018
#![feature(async_drop)]
//~^ WARN the feature `async_drop` is incomplete
use std::future::AsyncDrop;
use std::pin::Pin;
struct Foo;
impl AsyncDrop for &Foo {
//~^ ERROR the `AsyncDrop` trait may only be implemented for
async fn drop(self: Pin<&mut Self>) {}
}
impl AsyncDrop for Pin<Foo> {
//~^ ERROR the `AsyncDrop` trait may only be implemented for
async fn drop(self: Pin<&mut Self>) {}
}
fn main() {}

View file

@ -0,0 +1,24 @@
warning: the feature `async_drop` is incomplete and may not be safe to use and/or cause compiler crashes
--> $DIR/foreign-fundamental.rs:3:12
|
LL | #![feature(async_drop)]
| ^^^^^^^^^^
|
= note: see issue #126482 <https://github.com/rust-lang/rust/issues/126482> for more information
= note: `#[warn(incomplete_features)]` on by default
error[E0120]: the `AsyncDrop` trait may only be implemented for local structs, enums, and unions
--> $DIR/foreign-fundamental.rs:11:20
|
LL | impl AsyncDrop for &Foo {
| ^^^^ must be a struct, enum, or union in the current crate
error[E0120]: the `AsyncDrop` trait may only be implemented for local structs, enums, and unions
--> $DIR/foreign-fundamental.rs:16:20
|
LL | impl AsyncDrop for Pin<Foo> {
| ^^^^^^^^ must be a struct, enum, or union in the current crate
error: aborting due to 2 previous errors; 1 warning emitted
For more information about this error, try `rustc --explain E0120`.

View file

@ -1,6 +1,6 @@
//@ check-fail
#![feature(core_intrinsics)]
#![feature(core_intrinsics, const_cmp)]
use std::intrinsics::compare_bytes;
use std::mem::MaybeUninit;

View file

@ -1,6 +1,6 @@
//@ run-pass
#![feature(core_intrinsics)]
#![feature(core_intrinsics, const_cmp)]
use std::intrinsics::compare_bytes;
fn main() {

View file

@ -1,10 +1,11 @@
// Crate that exports a const fn. Used for testing cross-crate.
#![crate_type="rlib"]
#![crate_type = "rlib"]
#![stable(feature = "rust1", since = "1.0.0")]
#![feature(staged_api)]
#[stable(feature = "rust1", since = "1.0.0")]
#[rustc_const_unstable(feature="foo", issue = "none")]
pub const fn foo() -> u32 { 42 }
#[rustc_const_unstable(feature = "foo", issue = "none")]
pub const fn foo() -> u32 {
42
}

View file

@ -1,11 +1,11 @@
error[E0452]: malformed lint attribute input
--> $DIR/deduplicate-diagnostics.rs:8:8
--> $DIR/deduplicate-diagnostics.rs:10:8
|
LL | #[deny("literal")]
| ^^^^^^^^^ bad attribute argument
error: cannot find derive macro `Unresolved` in this scope
--> $DIR/deduplicate-diagnostics.rs:4:10
--> $DIR/deduplicate-diagnostics.rs:6:10
|
LL | #[derive(Unresolved)]
| ^^^^^^^^^^

View file

@ -1,17 +1,17 @@
error[E0452]: malformed lint attribute input
--> $DIR/deduplicate-diagnostics.rs:8:8
--> $DIR/deduplicate-diagnostics.rs:10:8
|
LL | #[deny("literal")]
| ^^^^^^^^^ bad attribute argument
error: cannot find derive macro `Unresolved` in this scope
--> $DIR/deduplicate-diagnostics.rs:4:10
--> $DIR/deduplicate-diagnostics.rs:6:10
|
LL | #[derive(Unresolved)]
| ^^^^^^^^^^
error: cannot find derive macro `Unresolved` in this scope
--> $DIR/deduplicate-diagnostics.rs:4:10
--> $DIR/deduplicate-diagnostics.rs:6:10
|
LL | #[derive(Unresolved)]
| ^^^^^^^^^^
@ -19,7 +19,7 @@ LL | #[derive(Unresolved)]
= note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
error[E0452]: malformed lint attribute input
--> $DIR/deduplicate-diagnostics.rs:8:8
--> $DIR/deduplicate-diagnostics.rs:10:8
|
LL | #[deny("literal")]
| ^^^^^^^^^ bad attribute argument
@ -27,7 +27,7 @@ LL | #[deny("literal")]
= note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
error[E0452]: malformed lint attribute input
--> $DIR/deduplicate-diagnostics.rs:8:8
--> $DIR/deduplicate-diagnostics.rs:10:8
|
LL | #[deny("literal")]
| ^^^^^^^^^ bad attribute argument

View file

@ -1,3 +1,5 @@
//! Test that `-Z deduplicate-diagnostics` flag properly deduplicates diagnostic messages.
//@ revisions: duplicate deduplicate
//@[deduplicate] compile-flags: -Z deduplicate-diagnostics=yes

View file

@ -1,4 +1,4 @@
trait MyTrait { fn foo() {} }
trait MyTrait { fn foo(&self) {} }
impl Drop for dyn MyTrait {
//~^ ERROR E0120

View file

@ -1,8 +1,10 @@
//! Smoke test for println!() with debug format specifiers.
//@ run-pass
#[derive(Debug)]
enum Numbers {
Three
Three,
}
pub fn main() {

View file

@ -22,15 +22,10 @@ LL | x.fmt(f);
= help: items from traits can only be used if the trait is in scope
help: the following traits which provide `fmt` are implemented but not in scope; perhaps you want to import one of them
|
LL + use std::fmt::Binary;
|
LL + use std::fmt::Debug;
|
LL + use std::fmt::Display;
LL + use std::fmt::Pointer;
|
LL + use std::fmt::LowerExp;
|
= and 5 other candidates
error: aborting due to 2 previous errors

View file

@ -9,12 +9,8 @@ help: the following traits which provide `method` are implemented but not in sco
|
LL + use foo::Bar;
|
LL + use no_method_suggested_traits::Reexported;
|
LL + use no_method_suggested_traits::foo::PubPub;
|
LL + use no_method_suggested_traits::qux::PrivPub;
|
help: there is a method `method2` with a similar name
|
LL | 1u32.method2();
@ -31,12 +27,8 @@ help: the following traits which provide `method` are implemented but not in sco
|
LL + use foo::Bar;
|
LL + use no_method_suggested_traits::Reexported;
|
LL + use no_method_suggested_traits::foo::PubPub;
|
LL + use no_method_suggested_traits::qux::PrivPub;
|
help: there is a method `method2` with a similar name
|
LL | std::rc::Rc::new(&mut Box::new(&1u32)).method2();

View file

@ -1,11 +1,11 @@
//! This is a regression test for https://github.com/rust-lang/rust/issues/140686.
//! Although this is a ld64(ld-classic) bug, we still need to support it
//! due to cross-compilation and support for older Xcode.
//@ compile-flags: -Copt-level=3 -Ccodegen-units=256 -Clink-arg=-ld_classic
//@ run-pass
//@ only-x86_64-apple-darwin
// This is a regression test for https://github.com/rust-lang/rust/issues/140686.
// Although this is a ld64(ld-classic) bug, we still need to support it
// due to cross-compilation and support for older Xcode.
fn main() {
let dst: Vec<u8> = Vec::new();
let len = broken_func(std::hint::black_box(2), dst);

View file

@ -20,17 +20,12 @@ error[E0034]: multiple applicable items in scope
LL | let z = x.foo();
| ^^^ multiple `foo` found
|
note: candidate #1 is defined in the trait `FinalFoo`
--> $DIR/method-deref-to-same-trait-object-with-separate-params.rs:60:5
|
LL | fn foo(&self) -> u8;
| ^^^^^^^^^^^^^^^^^^^^
note: candidate #2 is defined in an impl of the trait `NuisanceFoo` for the type `T`
note: candidate #1 is defined in an impl of the trait `NuisanceFoo` for the type `T`
--> $DIR/method-deref-to-same-trait-object-with-separate-params.rs:73:9
|
LL | fn foo(self) {}
| ^^^^^^^^^^^^
note: candidate #3 is defined in an impl of the trait `X` for the type `T`
note: candidate #2 is defined in an impl of the trait `X` for the type `T`
--> $DIR/method-deref-to-same-trait-object-with-separate-params.rs:46:9
|
LL | fn foo(self: Smaht<Self, u64>) -> u64 {
@ -38,14 +33,9 @@ LL | fn foo(self: Smaht<Self, u64>) -> u64 {
help: disambiguate the method for candidate #1
|
LL - let z = x.foo();
LL + let z = FinalFoo::foo(&x);
|
help: disambiguate the method for candidate #2
|
LL - let z = x.foo();
LL + let z = NuisanceFoo::foo(x);
|
help: disambiguate the method for candidate #3
help: disambiguate the method for candidate #2
|
LL - let z = x.foo();
LL + let z = X::foo(x);

View file

@ -0,0 +1,34 @@
fn main() {
trait Hello {
fn name(&self) -> String;
}
#[derive(Debug)]
struct Container2 {
val: String,
}
trait AName2 {
fn name(&self) -> String;
}
trait BName2 {
fn name(&self, v: bool) -> String;
}
impl AName2 for Container2 {
fn name(&self) -> String {
"aname2".into()
}
}
impl BName2 for Container2 {
fn name(&self, _v: bool) -> String {
"bname2".into()
}
}
let c2 = Container2 { val: "abc".into() };
println!("c2 = {:?}", c2.name());
//~^ ERROR: multiple applicable items in scope
}

View file

@ -0,0 +1,30 @@
error[E0034]: multiple applicable items in scope
--> $DIR/wrong-ambig-message.rs:32:30
|
LL | println!("c2 = {:?}", c2.name());
| ^^^^ multiple `name` found
|
note: candidate #1 is defined in an impl of the trait `AName2` for the type `Container2`
--> $DIR/wrong-ambig-message.rs:20:9
|
LL | fn name(&self) -> String {
| ^^^^^^^^^^^^^^^^^^^^^^^^
note: candidate #2 is defined in an impl of the trait `BName2` for the type `Container2`
--> $DIR/wrong-ambig-message.rs:26:9
|
LL | fn name(&self, _v: bool) -> String {
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
help: disambiguate the method for candidate #1
|
LL - println!("c2 = {:?}", c2.name());
LL + println!("c2 = {:?}", AName2::name(&c2));
|
help: disambiguate the method for candidate #2
|
LL - println!("c2 = {:?}", c2.name());
LL + println!("c2 = {:?}", BName2::name(&c2));
|
error: aborting due to 1 previous error
For more information about this error, try `rustc --explain E0034`.

View file

@ -1,3 +1,5 @@
//! Test that generic parameters shadow structs and modules with the same name.
struct T { i: i32 }
fn f<T>() {
let t = T { i: 0 }; //~ ERROR expected struct, variant or union type, found type parameter `T`

View file

@ -1,5 +1,5 @@
error[E0574]: expected struct, variant or union type, found type parameter `T`
--> $DIR/lexical-scopes.rs:3:13
--> $DIR/shadowing-generic-item.rs:5:13
|
LL | struct T { i: i32 }
| - you might have meant to refer to this struct
@ -9,7 +9,7 @@ LL | let t = T { i: 0 };
| ^ not a struct, variant or union type
error[E0599]: no function or associated item named `f` found for type parameter `Foo` in the current scope
--> $DIR/lexical-scopes.rs:10:10
--> $DIR/shadowing-generic-item.rs:12:10
|
LL | fn g<Foo>() {
| --- function or associated item `f` not found for this type parameter

View file

@ -0,0 +1,37 @@
//@ check-pass
// Ensure that `default_field_values` and `const_default` interact properly.
#![feature(const_default)]
#![feature(const_trait_impl)]
#![feature(default_field_values)]
#![feature(derive_const)]
#[derive(PartialEq, Eq, Debug)]
#[derive_const(Default)]
struct S {
r: Option<String> = <Option<_> as Default>::default(),
s: String = String::default(),
o: Option<String> = Option::<String>::default(),
p: std::marker::PhantomData<()> = std::marker::PhantomData::default(),
q: Option<String> = <Option<String> as Default>::default(),
t: Option<String> = Option::default(),
v: Option<String> = const { Option::default() },
}
const _: S = S { .. };
const _: S = const { S { .. } };
const _: S = S::default();
const _: S = const { S::default() };
fn main() {
let s = S { .. };
assert_eq!(s.r, None);
assert_eq!(&s.s, "");
assert_eq!(s.o, None);
assert_eq!(s.p, std::marker::PhantomData);
assert_eq!(s.q, None);
assert_eq!(s.t, None);
assert_eq!(s.v, None);
assert_eq!(s, S::default());
}

View file

@ -1,3 +1,5 @@
//! Test that the symbol mangling of Foo-the-constructor-function versus Foo-the-type do not collide
//@ run-pass
fn size_of_val<T>(_: &T) -> usize {
@ -6,8 +8,6 @@ fn size_of_val<T>(_: &T) -> usize {
struct Foo(#[allow(dead_code)] i64);
// Test that the (symbol) mangling of `Foo` (the `struct` type) and that of
// `typeof Foo` (the function type of the `struct` constructor) don't collide.
fn main() {
size_of_val(&Foo(0));
size_of_val(&Foo);

View file

@ -1,7 +1,7 @@
//@ compile-flags: -Znext-solver
//@ known-bug: #110395
// Broken until we have `const PartialEq` impl in stdlib
// Broken until `(): const PartialEq`
#![allow(incomplete_features)]
#![feature(const_trait_impl, const_cmp, const_destruct)]

View file

@ -4,6 +4,7 @@ error[E0658]: use of unstable library feature `derive_const`
LL | #[derive_const(Debug)]
| ^^^^^^^^^^^^
|
= note: see issue #118304 <https://github.com/rust-lang/rust/issues/118304> for more information
= help: add `#![feature(derive_const)]` to the crate attributes to enable
= note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date

View file

@ -1,12 +0,0 @@
error[E0015]: cannot match on `str` in constant functions
--> $DIR/match-non-const-eq.rs:7:9
|
LL | "a" => (), //FIXME [gated]~ ERROR can't compare `str` with `str` in const contexts
| ^^^
|
= note: `str` cannot be compared in compile-time, and therefore cannot be used in `match`es
= note: calls in constant functions are limited to constant functions, tuple structs and tuple variants
error: aborting due to 1 previous error
For more information about this error, try `rustc --explain E0015`.

View file

@ -1,11 +1,12 @@
//@ known-bug: #110395
//@ revisions: stock gated
#![cfg_attr(gated, feature(const_trait_impl))]
#![cfg_attr(gated, feature(const_trait_impl, const_cmp))]
//@[gated] check-pass
const fn foo(input: &'static str) {
match input {
"a" => (), //FIXME [gated]~ ERROR can't compare `str` with `str` in const contexts
//FIXME ~^ ERROR cannot match on `str` in constant functions
"a" => (),
//[stock]~^ ERROR cannot match on `str` in constant functions
//[stock]~| ERROR `PartialEq` is not yet stable as a const trait
_ => (),
}
}

View file

@ -1,12 +1,26 @@
error[E0015]: cannot match on `str` in constant functions
error[E0658]: cannot match on `str` in constant functions
--> $DIR/match-non-const-eq.rs:7:9
|
LL | "a" => (), //FIXME [gated]~ ERROR can't compare `str` with `str` in const contexts
LL | "a" => (),
| ^^^
|
= note: `str` cannot be compared in compile-time, and therefore cannot be used in `match`es
= note: calls in constant functions are limited to constant functions, tuple structs and tuple variants
= note: see issue #143874 <https://github.com/rust-lang/rust/issues/143874> for more information
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
= note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date
error: aborting due to 1 previous error
error: `PartialEq` is not yet stable as a const trait
--> $DIR/match-non-const-eq.rs:7:9
|
LL | "a" => (),
| ^^^
|
help: add `#![feature(const_cmp)]` to the crate attributes to enable
|
LL + #![feature(const_cmp)]
|
For more information about this error, try `rustc --explain E0015`.
error: aborting due to 2 previous errors
For more information about this error, try `rustc --explain E0658`.

View file

@ -0,0 +1,9 @@
// This test is to ensure that the raw underscore lifetime won't emit two duplicate errors.
// See issue #143152
//@ edition: 2021
fn f<'r#_>(){}
//~^ ERROR `_` cannot be a raw lifetime
fn main() {}

View file

@ -0,0 +1,8 @@
error: `_` cannot be a raw lifetime
--> $DIR/raw-underscore-lifetime.rs:6:6
|
LL | fn f<'r#_>(){}
| ^^^^
error: aborting due to 1 previous error

View file

@ -471,6 +471,7 @@ trigger_files = [
[autolabel."T-infra"]
trigger_files = [
".github/workflows",
"src/ci",
"src/tools/bump-stage0",
"src/tools/cargotest",
@ -598,6 +599,12 @@ trigger_files = [
"src/tools/clippy",
]
[autolabel."A-CI"]
trigger_files = [
".github/workflows",
"src/ci",
]
# ------------------------------------------------------------------------------
# Prioritization and team nominations
# ------------------------------------------------------------------------------
@ -1316,6 +1323,7 @@ infra-ci = [
"@Kobzol",
"@marcoieni",
"@jdno",
"@jieyouxu",
]
rustdoc = [
"@GuillaumeGomez",