mirror of
https://github.com/rust-lang/rust.git
synced 2025-02-16 17:03:35 +00:00
Use is_lang_item more aggressively
This commit is contained in:
parent
d5c48ebc71
commit
93ff86ed7c
@ -284,7 +284,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
|
|||||||
&& let CallKind::FnCall { fn_trait_id, self_ty } = kind
|
&& let CallKind::FnCall { fn_trait_id, self_ty } = kind
|
||||||
&& let ty::Param(_) = self_ty.kind()
|
&& let ty::Param(_) = self_ty.kind()
|
||||||
&& ty == self_ty
|
&& ty == self_ty
|
||||||
&& Some(fn_trait_id) == self.infcx.tcx.lang_items().fn_once_trait()
|
&& self.infcx.tcx.is_lang_item(fn_trait_id, LangItem::FnOnce)
|
||||||
{
|
{
|
||||||
// this is a type parameter `T: FnOnce()`, don't suggest `T: FnOnce() + Clone`.
|
// this is a type parameter `T: FnOnce()`, don't suggest `T: FnOnce() + Clone`.
|
||||||
true
|
true
|
||||||
@ -708,9 +708,9 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
|
|||||||
if let ty::ClauseKind::Trait(pred) = pred.kind().skip_binder()
|
if let ty::ClauseKind::Trait(pred) = pred.kind().skip_binder()
|
||||||
&& pred.self_ty() == ty
|
&& pred.self_ty() == ty
|
||||||
{
|
{
|
||||||
if Some(pred.def_id()) == tcx.lang_items().fn_trait() {
|
if tcx.is_lang_item(pred.def_id(), LangItem::Fn) {
|
||||||
return Some(hir::Mutability::Not);
|
return Some(hir::Mutability::Not);
|
||||||
} else if Some(pred.def_id()) == tcx.lang_items().fn_mut_trait() {
|
} else if tcx.is_lang_item(pred.def_id(), LangItem::FnMut) {
|
||||||
return Some(hir::Mutability::Mut);
|
return Some(hir::Mutability::Mut);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1832,7 +1832,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
|
|||||||
if let hir::ExprKind::MethodCall(..) = ex.kind
|
if let hir::ExprKind::MethodCall(..) = ex.kind
|
||||||
&& let Some(method_def_id) =
|
&& let Some(method_def_id) =
|
||||||
self.typeck_results.type_dependent_def_id(ex.hir_id)
|
self.typeck_results.type_dependent_def_id(ex.hir_id)
|
||||||
&& self.tcx.lang_items().clone_trait() == Some(self.tcx.parent(method_def_id))
|
&& self.tcx.is_lang_item(self.tcx.parent(method_def_id), LangItem::Clone)
|
||||||
{
|
{
|
||||||
self.clones.push(ex);
|
self.clones.push(ex);
|
||||||
}
|
}
|
||||||
@ -3159,8 +3159,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
|
|||||||
let is_format_arguments_item = if let Some(expr_ty) = expr_ty
|
let is_format_arguments_item = if let Some(expr_ty) = expr_ty
|
||||||
&& let ty::Adt(adt, _) = expr_ty.kind()
|
&& let ty::Adt(adt, _) = expr_ty.kind()
|
||||||
{
|
{
|
||||||
self.infcx.tcx.lang_items().get(LangItem::FormatArguments)
|
self.infcx.tcx.is_lang_item(adt.did(), LangItem::FormatArguments)
|
||||||
== Some(adt.did())
|
|
||||||
} else {
|
} else {
|
||||||
false
|
false
|
||||||
};
|
};
|
||||||
|
@ -6,9 +6,9 @@ use crate::session_diagnostics::{
|
|||||||
};
|
};
|
||||||
use rustc_errors::{Applicability, Diag};
|
use rustc_errors::{Applicability, Diag};
|
||||||
use rustc_errors::{DiagCtxt, MultiSpan};
|
use rustc_errors::{DiagCtxt, MultiSpan};
|
||||||
use rustc_hir as hir;
|
|
||||||
use rustc_hir::def::{CtorKind, Namespace};
|
use rustc_hir::def::{CtorKind, Namespace};
|
||||||
use rustc_hir::CoroutineKind;
|
use rustc_hir::CoroutineKind;
|
||||||
|
use rustc_hir::{self as hir, LangItem};
|
||||||
use rustc_index::IndexSlice;
|
use rustc_index::IndexSlice;
|
||||||
use rustc_infer::infer::BoundRegionConversionTime;
|
use rustc_infer::infer::BoundRegionConversionTime;
|
||||||
use rustc_infer::traits::SelectionError;
|
use rustc_infer::traits::SelectionError;
|
||||||
@ -116,7 +116,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
|
|||||||
{
|
{
|
||||||
if let ty::FnDef(id, _) = *const_.ty().kind() {
|
if let ty::FnDef(id, _) = *const_.ty().kind() {
|
||||||
debug!("add_moved_or_invoked_closure_note: id={:?}", id);
|
debug!("add_moved_or_invoked_closure_note: id={:?}", id);
|
||||||
if Some(self.infcx.tcx.parent(id)) == self.infcx.tcx.lang_items().fn_once_trait() {
|
if self.infcx.tcx.is_lang_item(self.infcx.tcx.parent(id), LangItem::FnOnce) {
|
||||||
let closure = match args.first() {
|
let closure = match args.first() {
|
||||||
Some(Spanned {
|
Some(Spanned {
|
||||||
node: Operand::Copy(place) | Operand::Move(place), ..
|
node: Operand::Copy(place) | Operand::Move(place), ..
|
||||||
@ -767,13 +767,12 @@ impl<'tcx> BorrowedContentSource<'tcx> {
|
|||||||
ty::FnDef(def_id, args) => {
|
ty::FnDef(def_id, args) => {
|
||||||
let trait_id = tcx.trait_of_item(def_id)?;
|
let trait_id = tcx.trait_of_item(def_id)?;
|
||||||
|
|
||||||
let lang_items = tcx.lang_items();
|
if tcx.is_lang_item(trait_id, LangItem::Deref)
|
||||||
if Some(trait_id) == lang_items.deref_trait()
|
|| tcx.is_lang_item(trait_id, LangItem::DerefMut)
|
||||||
|| Some(trait_id) == lang_items.deref_mut_trait()
|
|
||||||
{
|
{
|
||||||
Some(BorrowedContentSource::OverloadedDeref(args.type_at(0)))
|
Some(BorrowedContentSource::OverloadedDeref(args.type_at(0)))
|
||||||
} else if Some(trait_id) == lang_items.index_trait()
|
} else if tcx.is_lang_item(trait_id, LangItem::Index)
|
||||||
|| Some(trait_id) == lang_items.index_mut_trait()
|
|| tcx.is_lang_item(trait_id, LangItem::IndexMut)
|
||||||
{
|
{
|
||||||
Some(BorrowedContentSource::OverloadedIndex(args.type_at(0)))
|
Some(BorrowedContentSource::OverloadedIndex(args.type_at(0)))
|
||||||
} else {
|
} else {
|
||||||
@ -1041,7 +1040,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
|
|||||||
.unwrap_or_else(|| "value".to_owned());
|
.unwrap_or_else(|| "value".to_owned());
|
||||||
match kind {
|
match kind {
|
||||||
CallKind::FnCall { fn_trait_id, self_ty }
|
CallKind::FnCall { fn_trait_id, self_ty }
|
||||||
if Some(fn_trait_id) == self.infcx.tcx.lang_items().fn_once_trait() =>
|
if self.infcx.tcx.is_lang_item(fn_trait_id, LangItem::FnOnce) =>
|
||||||
{
|
{
|
||||||
err.subdiagnostic(
|
err.subdiagnostic(
|
||||||
self.dcx(),
|
self.dcx(),
|
||||||
@ -1268,7 +1267,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
|
|||||||
let ty = moved_place.ty(self.body, tcx).ty;
|
let ty = moved_place.ty(self.body, tcx).ty;
|
||||||
|
|
||||||
if let ty::Adt(def, args) = ty.peel_refs().kind()
|
if let ty::Adt(def, args) = ty.peel_refs().kind()
|
||||||
&& Some(def.did()) == tcx.lang_items().pin_type()
|
&& tcx.is_lang_item(def.did(), LangItem::Pin)
|
||||||
&& let ty::Ref(_, _, hir::Mutability::Mut) = args.type_at(0).kind()
|
&& let ty::Ref(_, _, hir::Mutability::Mut) = args.type_at(0).kind()
|
||||||
&& let self_ty = self.infcx.instantiate_binder_with_fresh_vars(
|
&& let self_ty = self.infcx.instantiate_binder_with_fresh_vars(
|
||||||
fn_call_span,
|
fn_call_span,
|
||||||
|
@ -4,6 +4,7 @@ use std::fmt::Write;
|
|||||||
|
|
||||||
use cranelift_codegen::isa::CallConv;
|
use cranelift_codegen::isa::CallConv;
|
||||||
use rustc_ast::ast::{InlineAsmOptions, InlineAsmTemplatePiece};
|
use rustc_ast::ast::{InlineAsmOptions, InlineAsmTemplatePiece};
|
||||||
|
use rustc_hir::LangItem;
|
||||||
use rustc_span::sym;
|
use rustc_span::sym;
|
||||||
use rustc_target::asm::*;
|
use rustc_target::asm::*;
|
||||||
use target_lexicon::BinaryFormat;
|
use target_lexicon::BinaryFormat;
|
||||||
@ -927,7 +928,7 @@ fn call_inline_asm<'tcx>(
|
|||||||
fn asm_clif_type<'tcx>(fx: &FunctionCx<'_, '_, 'tcx>, ty: Ty<'tcx>) -> Option<types::Type> {
|
fn asm_clif_type<'tcx>(fx: &FunctionCx<'_, '_, 'tcx>, ty: Ty<'tcx>) -> Option<types::Type> {
|
||||||
match ty.kind() {
|
match ty.kind() {
|
||||||
// Adapted from https://github.com/rust-lang/rust/blob/f3c66088610c1b80110297c2d9a8b5f9265b013f/compiler/rustc_hir_analysis/src/check/intrinsicck.rs#L136-L151
|
// Adapted from https://github.com/rust-lang/rust/blob/f3c66088610c1b80110297c2d9a8b5f9265b013f/compiler/rustc_hir_analysis/src/check/intrinsicck.rs#L136-L151
|
||||||
ty::Adt(adt, args) if Some(adt.did()) == fx.tcx.lang_items().maybe_uninit() => {
|
ty::Adt(adt, args) if fx.tcx.is_lang_item(adt.did(), LangItem::MaybeUninit) => {
|
||||||
let fields = &adt.non_enum_variant().fields;
|
let fields = &adt.non_enum_variant().fields;
|
||||||
let ty = fields[FieldIdx::from_u32(1)].ty(fx.tcx, args);
|
let ty = fields[FieldIdx::from_u32(1)].ty(fx.tcx, args);
|
||||||
let ty::Adt(ty, args) = ty.kind() else {
|
let ty::Adt(ty, args) = ty.kind() else {
|
||||||
|
@ -1,8 +1,8 @@
|
|||||||
//! The `Visitor` responsible for actually checking a `mir::Body` for invalid operations.
|
//! The `Visitor` responsible for actually checking a `mir::Body` for invalid operations.
|
||||||
|
|
||||||
use rustc_errors::{Diag, ErrorGuaranteed};
|
use rustc_errors::{Diag, ErrorGuaranteed};
|
||||||
use rustc_hir as hir;
|
|
||||||
use rustc_hir::def_id::DefId;
|
use rustc_hir::def_id::DefId;
|
||||||
|
use rustc_hir::{self as hir, LangItem};
|
||||||
use rustc_index::bit_set::BitSet;
|
use rustc_index::bit_set::BitSet;
|
||||||
use rustc_infer::infer::TyCtxtInferExt;
|
use rustc_infer::infer::TyCtxtInferExt;
|
||||||
use rustc_infer::traits::ObligationCause;
|
use rustc_infer::traits::ObligationCause;
|
||||||
@ -801,7 +801,7 @@ impl<'tcx> Visitor<'tcx> for Checker<'_, 'tcx> {
|
|||||||
// const-eval.
|
// const-eval.
|
||||||
|
|
||||||
// const-eval of the `begin_panic` fn assumes the argument is `&str`
|
// const-eval of the `begin_panic` fn assumes the argument is `&str`
|
||||||
if Some(callee) == tcx.lang_items().begin_panic_fn() {
|
if tcx.is_lang_item(callee, LangItem::BeginPanic) {
|
||||||
match args[0].node.ty(&self.ccx.body.local_decls, tcx).kind() {
|
match args[0].node.ty(&self.ccx.body.local_decls, tcx).kind() {
|
||||||
ty::Ref(_, ty, _) if ty.is_str() => return,
|
ty::Ref(_, ty, _) if ty.is_str() => return,
|
||||||
_ => self.check_op(ops::PanicNonStr),
|
_ => self.check_op(ops::PanicNonStr),
|
||||||
@ -819,7 +819,7 @@ impl<'tcx> Visitor<'tcx> for Checker<'_, 'tcx> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if Some(callee) == tcx.lang_items().exchange_malloc_fn() {
|
if tcx.is_lang_item(callee, LangItem::ExchangeMalloc) {
|
||||||
self.check_op(ops::HeapAllocation);
|
self.check_op(ops::HeapAllocation);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -218,7 +218,7 @@ impl<'tcx> NonConstOp<'tcx> for FnCallNonConst<'tcx> {
|
|||||||
} else {
|
} else {
|
||||||
let mut sugg = None;
|
let mut sugg = None;
|
||||||
|
|
||||||
if Some(trait_id) == ccx.tcx.lang_items().eq_trait() {
|
if ccx.tcx.is_lang_item(trait_id, LangItem::PartialEq) {
|
||||||
match (args[0].unpack(), args[1].unpack()) {
|
match (args[0].unpack(), args[1].unpack()) {
|
||||||
(GenericArgKind::Type(self_ty), GenericArgKind::Type(rhs_ty))
|
(GenericArgKind::Type(self_ty), GenericArgKind::Type(rhs_ty))
|
||||||
if self_ty == rhs_ty
|
if self_ty == rhs_ty
|
||||||
|
@ -230,7 +230,7 @@ impl<'tcx> CompileTimeInterpCx<'tcx> {
|
|||||||
let def_id = instance.def_id();
|
let def_id = instance.def_id();
|
||||||
|
|
||||||
if self.tcx.has_attr(def_id, sym::rustc_const_panic_str)
|
if self.tcx.has_attr(def_id, sym::rustc_const_panic_str)
|
||||||
|| Some(def_id) == self.tcx.lang_items().begin_panic_fn()
|
|| self.tcx.is_lang_item(def_id, LangItem::BeginPanic)
|
||||||
{
|
{
|
||||||
let args = self.copy_fn_args(args);
|
let args = self.copy_fn_args(args);
|
||||||
// &str or &&str
|
// &str or &&str
|
||||||
@ -245,7 +245,7 @@ impl<'tcx> CompileTimeInterpCx<'tcx> {
|
|||||||
let span = self.find_closest_untracked_caller_location();
|
let span = self.find_closest_untracked_caller_location();
|
||||||
let (file, line, col) = self.location_triple_for_span(span);
|
let (file, line, col) = self.location_triple_for_span(span);
|
||||||
return Err(ConstEvalErrKind::Panic { msg, file, line, col }.into());
|
return Err(ConstEvalErrKind::Panic { msg, file, line, col }.into());
|
||||||
} else if Some(def_id) == self.tcx.lang_items().panic_fmt() {
|
} else if self.tcx.is_lang_item(def_id, LangItem::PanicFmt) {
|
||||||
// For panic_fmt, call const_panic_fmt instead.
|
// For panic_fmt, call const_panic_fmt instead.
|
||||||
let const_def_id = self.tcx.require_lang_item(LangItem::ConstPanicFmt, None);
|
let const_def_id = self.tcx.require_lang_item(LangItem::ConstPanicFmt, None);
|
||||||
let new_instance = ty::Instance::expect_resolve(
|
let new_instance = ty::Instance::expect_resolve(
|
||||||
@ -256,7 +256,7 @@ impl<'tcx> CompileTimeInterpCx<'tcx> {
|
|||||||
);
|
);
|
||||||
|
|
||||||
return Ok(Some(new_instance));
|
return Ok(Some(new_instance));
|
||||||
} else if Some(def_id) == self.tcx.lang_items().align_offset_fn() {
|
} else if self.tcx.is_lang_item(def_id, LangItem::AlignOffset) {
|
||||||
let args = self.copy_fn_args(args);
|
let args = self.copy_fn_args(args);
|
||||||
// For align_offset, we replace the function call if the pointer has no address.
|
// For align_offset, we replace the function call if the pointer has no address.
|
||||||
match self.align_offset(instance, &args, dest, ret)? {
|
match self.align_offset(instance, &args, dest, ret)? {
|
||||||
|
@ -53,7 +53,7 @@ impl<'tcx> Bounds<'tcx> {
|
|||||||
span,
|
span,
|
||||||
);
|
);
|
||||||
// FIXME(-Znext-solver): We can likely remove this hack once the new trait solver lands.
|
// FIXME(-Znext-solver): We can likely remove this hack once the new trait solver lands.
|
||||||
if tcx.lang_items().sized_trait() == Some(trait_ref.def_id()) {
|
if tcx.is_lang_item(trait_ref.def_id(), LangItem::Sized) {
|
||||||
self.clauses.insert(0, clause);
|
self.clauses.insert(0, clause);
|
||||||
} else {
|
} else {
|
||||||
self.clauses.push(clause);
|
self.clauses.push(clause);
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
use rustc_ast::InlineAsmTemplatePiece;
|
use rustc_ast::InlineAsmTemplatePiece;
|
||||||
use rustc_data_structures::fx::FxIndexSet;
|
use rustc_data_structures::fx::FxIndexSet;
|
||||||
use rustc_hir as hir;
|
use rustc_hir::{self as hir, LangItem};
|
||||||
use rustc_middle::bug;
|
use rustc_middle::bug;
|
||||||
use rustc_middle::ty::{self, Article, FloatTy, IntTy, Ty, TyCtxt, TypeVisitableExt, UintTy};
|
use rustc_middle::ty::{self, Article, FloatTy, IntTy, Ty, TyCtxt, TypeVisitableExt, UintTy};
|
||||||
use rustc_session::lint;
|
use rustc_session::lint;
|
||||||
@ -134,7 +134,7 @@ impl<'a, 'tcx> InlineAsmCtxt<'a, 'tcx> {
|
|||||||
// `!` is allowed for input but not for output (issue #87802)
|
// `!` is allowed for input but not for output (issue #87802)
|
||||||
ty::Never if is_input => return None,
|
ty::Never if is_input => return None,
|
||||||
_ if ty.references_error() => return None,
|
_ if ty.references_error() => return None,
|
||||||
ty::Adt(adt, args) if Some(adt.did()) == self.tcx.lang_items().maybe_uninit() => {
|
ty::Adt(adt, args) if self.tcx.is_lang_item(adt.did(), LangItem::MaybeUninit) => {
|
||||||
let fields = &adt.non_enum_variant().fields;
|
let fields = &adt.non_enum_variant().fields;
|
||||||
let ty = fields[FieldIdx::from_u32(1)].ty(self.tcx, args);
|
let ty = fields[FieldIdx::from_u32(1)].ty(self.tcx, args);
|
||||||
// FIXME: Are we just trying to map to the `T` in `MaybeUninit<T>`?
|
// FIXME: Are we just trying to map to the `T` in `MaybeUninit<T>`?
|
||||||
|
@ -8,6 +8,7 @@
|
|||||||
use crate::errors;
|
use crate::errors;
|
||||||
use rustc_errors::{codes::*, struct_span_code_err};
|
use rustc_errors::{codes::*, struct_span_code_err};
|
||||||
use rustc_hir::def_id::{DefId, LocalDefId};
|
use rustc_hir::def_id::{DefId, LocalDefId};
|
||||||
|
use rustc_hir::LangItem;
|
||||||
use rustc_middle::query::Providers;
|
use rustc_middle::query::Providers;
|
||||||
use rustc_middle::ty::{self, TyCtxt, TypeVisitableExt};
|
use rustc_middle::ty::{self, TyCtxt, TypeVisitableExt};
|
||||||
use rustc_session::parse::feature_err;
|
use rustc_session::parse::feature_err;
|
||||||
@ -49,7 +50,7 @@ fn enforce_trait_manually_implementable(
|
|||||||
) -> Result<(), ErrorGuaranteed> {
|
) -> Result<(), ErrorGuaranteed> {
|
||||||
let impl_header_span = tcx.def_span(impl_def_id);
|
let impl_header_span = tcx.def_span(impl_def_id);
|
||||||
|
|
||||||
if tcx.lang_items().freeze_trait() == Some(trait_def_id) {
|
if tcx.is_lang_item(trait_def_id, LangItem::Freeze) {
|
||||||
if !tcx.features().freeze_impls {
|
if !tcx.features().freeze_impls {
|
||||||
feature_err(
|
feature_err(
|
||||||
&tcx.sess,
|
&tcx.sess,
|
||||||
@ -75,7 +76,7 @@ fn enforce_trait_manually_implementable(
|
|||||||
|
|
||||||
// Maintain explicit error code for `Unsize`, since it has a useful
|
// Maintain explicit error code for `Unsize`, since it has a useful
|
||||||
// explanation about using `CoerceUnsized` instead.
|
// explanation about using `CoerceUnsized` instead.
|
||||||
if Some(trait_def_id) == tcx.lang_items().unsize_trait() {
|
if tcx.is_lang_item(trait_def_id, LangItem::Unsize) {
|
||||||
err.code(E0328);
|
err.code(E0328);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -5,9 +5,9 @@ use super::{Expectation, FnCtxt, TupleArgumentsFlag};
|
|||||||
use crate::errors;
|
use crate::errors;
|
||||||
use rustc_ast::util::parser::PREC_POSTFIX;
|
use rustc_ast::util::parser::PREC_POSTFIX;
|
||||||
use rustc_errors::{Applicability, Diag, ErrorGuaranteed, StashKey};
|
use rustc_errors::{Applicability, Diag, ErrorGuaranteed, StashKey};
|
||||||
use rustc_hir as hir;
|
|
||||||
use rustc_hir::def::{self, CtorKind, Namespace, Res};
|
use rustc_hir::def::{self, CtorKind, Namespace, Res};
|
||||||
use rustc_hir::def_id::DefId;
|
use rustc_hir::def_id::DefId;
|
||||||
|
use rustc_hir::{self as hir, LangItem};
|
||||||
use rustc_hir_analysis::autoderef::Autoderef;
|
use rustc_hir_analysis::autoderef::Autoderef;
|
||||||
use rustc_infer::traits::ObligationCauseCode;
|
use rustc_infer::traits::ObligationCauseCode;
|
||||||
use rustc_infer::{
|
use rustc_infer::{
|
||||||
@ -41,7 +41,7 @@ pub fn check_legal_trait_for_method_call(
|
|||||||
trait_id: DefId,
|
trait_id: DefId,
|
||||||
body_id: DefId,
|
body_id: DefId,
|
||||||
) -> Result<(), ErrorGuaranteed> {
|
) -> Result<(), ErrorGuaranteed> {
|
||||||
if tcx.lang_items().drop_trait() == Some(trait_id)
|
if tcx.is_lang_item(trait_id, LangItem::Drop)
|
||||||
&& tcx.lang_items().fallback_surface_drop_fn() != Some(body_id)
|
&& tcx.lang_items().fallback_surface_drop_fn() != Some(body_id)
|
||||||
{
|
{
|
||||||
let sugg = if let Some(receiver) = receiver.filter(|s| !s.is_empty()) {
|
let sugg = if let Some(receiver) = receiver.filter(|s| !s.is_empty()) {
|
||||||
|
@ -3150,7 +3150,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
|||||||
error.obligation.predicate.kind().skip_binder(),
|
error.obligation.predicate.kind().skip_binder(),
|
||||||
) {
|
) {
|
||||||
(ty::PredicateKind::Clause(ty::ClauseKind::Trait(predicate)), _)
|
(ty::PredicateKind::Clause(ty::ClauseKind::Trait(predicate)), _)
|
||||||
if self.tcx.lang_items().index_trait() == Some(predicate.trait_ref.def_id) =>
|
if self.tcx.is_lang_item(predicate.trait_ref.def_id, LangItem::Index) =>
|
||||||
{
|
{
|
||||||
seen_preds.insert(error.obligation.predicate.kind().skip_binder());
|
seen_preds.insert(error.obligation.predicate.kind().skip_binder());
|
||||||
}
|
}
|
||||||
|
@ -489,7 +489,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
|||||||
);
|
);
|
||||||
return true;
|
return true;
|
||||||
} else if let ty::Adt(adt, _) = found_ty_inner.peel_refs().kind()
|
} else if let ty::Adt(adt, _) = found_ty_inner.peel_refs().kind()
|
||||||
&& Some(adt.did()) == self.tcx.lang_items().string()
|
&& self.tcx.is_lang_item(adt.did(), LangItem::String)
|
||||||
&& peeled.is_str()
|
&& peeled.is_str()
|
||||||
// `Result::map`, conversely, does not take ref of the error type.
|
// `Result::map`, conversely, does not take ref of the error type.
|
||||||
&& error_tys.is_none_or(|(found, expected)| {
|
&& error_tys.is_none_or(|(found, expected)| {
|
||||||
@ -3147,7 +3147,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if let ty::Adt(adt, _) = expected_ty.kind()
|
if let ty::Adt(adt, _) = expected_ty.kind()
|
||||||
&& self.tcx.lang_items().range_struct() == Some(adt.did())
|
&& self.tcx.is_lang_item(adt.did(), LangItem::Range)
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -1102,7 +1102,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
|||||||
unsatisfied_predicates.iter().any(|(pred, _, _)| {
|
unsatisfied_predicates.iter().any(|(pred, _, _)| {
|
||||||
match pred.kind().skip_binder() {
|
match pred.kind().skip_binder() {
|
||||||
ty::PredicateKind::Clause(ty::ClauseKind::Trait(pred)) => {
|
ty::PredicateKind::Clause(ty::ClauseKind::Trait(pred)) => {
|
||||||
Some(pred.def_id()) == self.tcx.lang_items().sized_trait()
|
self.tcx.is_lang_item(pred.def_id(), LangItem::Sized)
|
||||||
&& pred.polarity == ty::PredicatePolarity::Positive
|
&& pred.polarity == ty::PredicatePolarity::Positive
|
||||||
}
|
}
|
||||||
_ => false,
|
_ => false,
|
||||||
@ -1375,10 +1375,10 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
|||||||
ty.is_str()
|
ty.is_str()
|
||||||
|| matches!(
|
|| matches!(
|
||||||
ty.kind(),
|
ty.kind(),
|
||||||
ty::Adt(adt, _) if Some(adt.did()) == self.tcx.lang_items().string()
|
ty::Adt(adt, _) if self.tcx.is_lang_item(adt.did(), LangItem::String)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
ty::Adt(adt, _) => Some(adt.did()) == self.tcx.lang_items().string(),
|
ty::Adt(adt, _) => self.tcx.is_lang_item(adt.did(), LangItem::String),
|
||||||
_ => false,
|
_ => false,
|
||||||
};
|
};
|
||||||
if is_string_or_ref_str && item_name.name == sym::iter {
|
if is_string_or_ref_str && item_name.name == sym::iter {
|
||||||
@ -2723,7 +2723,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
|||||||
|
|
||||||
if tcx.is_diagnostic_item(sym::LocalKey, inner_id) {
|
if tcx.is_diagnostic_item(sym::LocalKey, inner_id) {
|
||||||
err.help("use `with` or `try_with` to access thread local storage");
|
err.help("use `with` or `try_with` to access thread local storage");
|
||||||
} else if Some(kind.did()) == tcx.lang_items().maybe_uninit() {
|
} else if tcx.is_lang_item(kind.did(), LangItem::MaybeUninit) {
|
||||||
err.help(format!(
|
err.help(format!(
|
||||||
"if this `{name}` has been initialized, \
|
"if this `{name}` has been initialized, \
|
||||||
use one of the `assume_init` methods to access the inner value"
|
use one of the `assume_init` methods to access the inner value"
|
||||||
|
@ -7,7 +7,7 @@ use rustc_errors::{
|
|||||||
};
|
};
|
||||||
use rustc_hir::def::{CtorKind, DefKind, Res};
|
use rustc_hir::def::{CtorKind, DefKind, Res};
|
||||||
use rustc_hir::pat_util::EnumerateAndAdjustIterator;
|
use rustc_hir::pat_util::EnumerateAndAdjustIterator;
|
||||||
use rustc_hir::{self as hir, BindingMode, ByRef, HirId, Mutability, Pat, PatKind};
|
use rustc_hir::{self as hir, BindingMode, ByRef, HirId, LangItem, Mutability, Pat, PatKind};
|
||||||
use rustc_infer::infer;
|
use rustc_infer::infer;
|
||||||
use rustc_middle::mir::interpret::ErrorHandled;
|
use rustc_middle::mir::interpret::ErrorHandled;
|
||||||
use rustc_middle::ty::{self, Ty, TypeVisitableExt};
|
use rustc_middle::ty::{self, Ty, TypeVisitableExt};
|
||||||
@ -491,7 +491,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
|||||||
let tcx = self.tcx;
|
let tcx = self.tcx;
|
||||||
let expected = self.resolve_vars_if_possible(expected);
|
let expected = self.resolve_vars_if_possible(expected);
|
||||||
pat_ty = match expected.kind() {
|
pat_ty = match expected.kind() {
|
||||||
ty::Adt(def, _) if Some(def.did()) == tcx.lang_items().string() => expected,
|
ty::Adt(def, _) if tcx.is_lang_item(def.did(), LangItem::String) => expected,
|
||||||
ty::Str => Ty::new_static_str(tcx),
|
ty::Str => Ty::new_static_str(tcx),
|
||||||
_ => pat_ty,
|
_ => pat_ty,
|
||||||
};
|
};
|
||||||
|
@ -3,7 +3,7 @@ use crate::{
|
|||||||
LateContext, LateLintPass, LintContext,
|
LateContext, LateLintPass, LintContext,
|
||||||
};
|
};
|
||||||
|
|
||||||
use rustc_hir as hir;
|
use rustc_hir::{self as hir, LangItem};
|
||||||
use rustc_middle::ty;
|
use rustc_middle::ty;
|
||||||
use rustc_session::lint::FutureIncompatibilityReason;
|
use rustc_session::lint::FutureIncompatibilityReason;
|
||||||
use rustc_session::{declare_lint, declare_lint_pass};
|
use rustc_session::{declare_lint, declare_lint_pass};
|
||||||
@ -66,7 +66,7 @@ impl<'tcx> LateLintPass<'tcx> for DerefIntoDynSupertrait {
|
|||||||
// the trait is a `Deref` implementation
|
// the trait is a `Deref` implementation
|
||||||
&& let Some(trait_) = &impl_.of_trait
|
&& let Some(trait_) = &impl_.of_trait
|
||||||
&& let Some(did) = trait_.trait_def_id()
|
&& let Some(did) = trait_.trait_def_id()
|
||||||
&& Some(did) == tcx.lang_items().deref_trait()
|
&& tcx.is_lang_item(did, LangItem::Deref)
|
||||||
// the self type is `dyn t_principal`
|
// the self type is `dyn t_principal`
|
||||||
&& let self_ty = tcx.type_of(item.owner_id).instantiate_identity()
|
&& let self_ty = tcx.type_of(item.owner_id).instantiate_identity()
|
||||||
&& let ty::Dynamic(data, _, ty::Dyn) = self_ty.kind()
|
&& let ty::Dynamic(data, _, ty::Dyn) = self_ty.kind()
|
||||||
|
@ -2,7 +2,7 @@ use crate::lints::{NonFmtPanicBraces, NonFmtPanicUnused};
|
|||||||
use crate::{fluent_generated as fluent, LateContext, LateLintPass, LintContext};
|
use crate::{fluent_generated as fluent, LateContext, LateLintPass, LintContext};
|
||||||
use rustc_ast as ast;
|
use rustc_ast as ast;
|
||||||
use rustc_errors::Applicability;
|
use rustc_errors::Applicability;
|
||||||
use rustc_hir as hir;
|
use rustc_hir::{self as hir, LangItem};
|
||||||
use rustc_infer::infer::TyCtxtInferExt;
|
use rustc_infer::infer::TyCtxtInferExt;
|
||||||
use rustc_middle::bug;
|
use rustc_middle::bug;
|
||||||
use rustc_middle::lint::in_external_macro;
|
use rustc_middle::lint::in_external_macro;
|
||||||
@ -53,8 +53,8 @@ impl<'tcx> LateLintPass<'tcx> for NonPanicFmt {
|
|||||||
if let &ty::FnDef(def_id, _) = cx.typeck_results().expr_ty(f).kind() {
|
if let &ty::FnDef(def_id, _) = cx.typeck_results().expr_ty(f).kind() {
|
||||||
let f_diagnostic_name = cx.tcx.get_diagnostic_name(def_id);
|
let f_diagnostic_name = cx.tcx.get_diagnostic_name(def_id);
|
||||||
|
|
||||||
if Some(def_id) == cx.tcx.lang_items().begin_panic_fn()
|
if cx.tcx.is_lang_item(def_id, LangItem::BeginPanic)
|
||||||
|| Some(def_id) == cx.tcx.lang_items().panic_fn()
|
|| cx.tcx.is_lang_item(def_id, LangItem::Panic)
|
||||||
|| f_diagnostic_name == Some(sym::panic_str_2015)
|
|| f_diagnostic_name == Some(sym::panic_str_2015)
|
||||||
{
|
{
|
||||||
if let Some(id) = f.span.ctxt().outer_expn_data().macro_def_id {
|
if let Some(id) = f.span.ctxt().outer_expn_data().macro_def_id {
|
||||||
@ -153,7 +153,7 @@ fn check_panic<'tcx>(cx: &LateContext<'tcx>, f: &'tcx hir::Expr<'tcx>, arg: &'tc
|
|||||||
ty::Ref(_, r, _) if r.is_str(),
|
ty::Ref(_, r, _) if r.is_str(),
|
||||||
) || matches!(
|
) || matches!(
|
||||||
ty.ty_adt_def(),
|
ty.ty_adt_def(),
|
||||||
Some(ty_def) if Some(ty_def.did()) == cx.tcx.lang_items().string(),
|
Some(ty_def) if cx.tcx.is_lang_item(ty_def.did(), LangItem::String),
|
||||||
);
|
);
|
||||||
|
|
||||||
let infcx = cx.tcx.infer_ctxt().build();
|
let infcx = cx.tcx.infer_ctxt().build();
|
||||||
|
@ -2,7 +2,7 @@ use crate::lints::{DropGlue, DropTraitConstraintsDiag};
|
|||||||
use crate::LateContext;
|
use crate::LateContext;
|
||||||
use crate::LateLintPass;
|
use crate::LateLintPass;
|
||||||
use crate::LintContext;
|
use crate::LintContext;
|
||||||
use rustc_hir as hir;
|
use rustc_hir::{self as hir, LangItem};
|
||||||
use rustc_session::{declare_lint, declare_lint_pass};
|
use rustc_session::{declare_lint, declare_lint_pass};
|
||||||
use rustc_span::symbol::sym;
|
use rustc_span::symbol::sym;
|
||||||
|
|
||||||
@ -96,7 +96,7 @@ impl<'tcx> LateLintPass<'tcx> for DropTraitConstraints {
|
|||||||
continue;
|
continue;
|
||||||
};
|
};
|
||||||
let def_id = trait_predicate.trait_ref.def_id;
|
let def_id = trait_predicate.trait_ref.def_id;
|
||||||
if cx.tcx.lang_items().drop_trait() == Some(def_id) {
|
if cx.tcx.is_lang_item(def_id, LangItem::Drop) {
|
||||||
// Explicitly allow `impl Drop`, a drop-guards-as-unnameable-type pattern.
|
// Explicitly allow `impl Drop`, a drop-guards-as-unnameable-type pattern.
|
||||||
if trait_predicate.trait_ref.self_ty().is_impl_trait() {
|
if trait_predicate.trait_ref.self_ty().is_impl_trait() {
|
||||||
continue;
|
continue;
|
||||||
|
@ -10,9 +10,9 @@ use rustc_ast as ast;
|
|||||||
use rustc_ast::util::{classify, parser};
|
use rustc_ast::util::{classify, parser};
|
||||||
use rustc_ast::{ExprKind, StmtKind};
|
use rustc_ast::{ExprKind, StmtKind};
|
||||||
use rustc_errors::{pluralize, MultiSpan};
|
use rustc_errors::{pluralize, MultiSpan};
|
||||||
use rustc_hir as hir;
|
|
||||||
use rustc_hir::def::{DefKind, Res};
|
use rustc_hir::def::{DefKind, Res};
|
||||||
use rustc_hir::def_id::DefId;
|
use rustc_hir::def_id::DefId;
|
||||||
|
use rustc_hir::{self as hir, LangItem};
|
||||||
use rustc_infer::traits::util::elaborate;
|
use rustc_infer::traits::util::elaborate;
|
||||||
use rustc_middle::ty::adjustment;
|
use rustc_middle::ty::adjustment;
|
||||||
use rustc_middle::ty::{self, Ty};
|
use rustc_middle::ty::{self, Ty};
|
||||||
@ -289,7 +289,7 @@ impl<'tcx> LateLintPass<'tcx> for UnusedResults {
|
|||||||
is_ty_must_use(cx, boxed_ty, expr, span)
|
is_ty_must_use(cx, boxed_ty, expr, span)
|
||||||
.map(|inner| MustUsePath::Boxed(Box::new(inner)))
|
.map(|inner| MustUsePath::Boxed(Box::new(inner)))
|
||||||
}
|
}
|
||||||
ty::Adt(def, args) if cx.tcx.lang_items().pin_type() == Some(def.did()) => {
|
ty::Adt(def, args) if cx.tcx.is_lang_item(def.did(), LangItem::Pin) => {
|
||||||
let pinned_ty = args.type_at(0);
|
let pinned_ty = args.type_at(0);
|
||||||
is_ty_must_use(cx, pinned_ty, expr, span)
|
is_ty_must_use(cx, pinned_ty, expr, span)
|
||||||
.map(|inner| MustUsePath::Pinned(Box::new(inner)))
|
.map(|inner| MustUsePath::Pinned(Box::new(inner)))
|
||||||
|
@ -2020,7 +2020,7 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
|
|||||||
|
|
||||||
// if this is an impl of `CoerceUnsized`, create its
|
// if this is an impl of `CoerceUnsized`, create its
|
||||||
// "unsized info", else just store None
|
// "unsized info", else just store None
|
||||||
if Some(trait_ref.def_id) == tcx.lang_items().coerce_unsized_trait() {
|
if tcx.is_lang_item(trait_ref.def_id, LangItem::CoerceUnsized) {
|
||||||
let coerce_unsized_info = tcx.coerce_unsized_info(def_id).unwrap();
|
let coerce_unsized_info = tcx.coerce_unsized_info(def_id).unwrap();
|
||||||
record!(self.tables.coerce_unsized_info[def_id] <- coerce_unsized_info);
|
record!(self.tables.coerce_unsized_info[def_id] <- coerce_unsized_info);
|
||||||
}
|
}
|
||||||
|
@ -8,9 +8,9 @@ use rustc_data_structures::intern::Interned;
|
|||||||
use rustc_data_structures::stable_hasher::HashingControls;
|
use rustc_data_structures::stable_hasher::HashingControls;
|
||||||
use rustc_data_structures::stable_hasher::{HashStable, StableHasher};
|
use rustc_data_structures::stable_hasher::{HashStable, StableHasher};
|
||||||
use rustc_errors::ErrorGuaranteed;
|
use rustc_errors::ErrorGuaranteed;
|
||||||
use rustc_hir as hir;
|
|
||||||
use rustc_hir::def::{CtorKind, DefKind, Res};
|
use rustc_hir::def::{CtorKind, DefKind, Res};
|
||||||
use rustc_hir::def_id::DefId;
|
use rustc_hir::def_id::DefId;
|
||||||
|
use rustc_hir::{self as hir, LangItem};
|
||||||
use rustc_index::{IndexSlice, IndexVec};
|
use rustc_index::{IndexSlice, IndexVec};
|
||||||
use rustc_macros::{HashStable, TyDecodable, TyEncodable};
|
use rustc_macros::{HashStable, TyDecodable, TyEncodable};
|
||||||
use rustc_query_system::ich::StableHashingContext;
|
use rustc_query_system::ich::StableHashingContext;
|
||||||
@ -274,16 +274,16 @@ impl AdtDefData {
|
|||||||
if tcx.has_attr(did, sym::fundamental) {
|
if tcx.has_attr(did, sym::fundamental) {
|
||||||
flags |= AdtFlags::IS_FUNDAMENTAL;
|
flags |= AdtFlags::IS_FUNDAMENTAL;
|
||||||
}
|
}
|
||||||
if Some(did) == tcx.lang_items().phantom_data() {
|
if tcx.is_lang_item(did, LangItem::PhantomData) {
|
||||||
flags |= AdtFlags::IS_PHANTOM_DATA;
|
flags |= AdtFlags::IS_PHANTOM_DATA;
|
||||||
}
|
}
|
||||||
if Some(did) == tcx.lang_items().owned_box() {
|
if tcx.is_lang_item(did, LangItem::OwnedBox) {
|
||||||
flags |= AdtFlags::IS_BOX;
|
flags |= AdtFlags::IS_BOX;
|
||||||
}
|
}
|
||||||
if Some(did) == tcx.lang_items().manually_drop() {
|
if tcx.is_lang_item(did, LangItem::ManuallyDrop) {
|
||||||
flags |= AdtFlags::IS_MANUALLY_DROP;
|
flags |= AdtFlags::IS_MANUALLY_DROP;
|
||||||
}
|
}
|
||||||
if Some(did) == tcx.lang_items().unsafe_cell_type() {
|
if tcx.is_lang_item(did, LangItem::UnsafeCell) {
|
||||||
flags |= AdtFlags::IS_UNSAFE_CELL;
|
flags |= AdtFlags::IS_UNSAFE_CELL;
|
||||||
}
|
}
|
||||||
if is_anonymous {
|
if is_anonymous {
|
||||||
|
@ -699,26 +699,25 @@ impl<'tcx> Instance<'tcx> {
|
|||||||
};
|
};
|
||||||
let coroutine_kind = tcx.coroutine_kind(coroutine_def_id).unwrap();
|
let coroutine_kind = tcx.coroutine_kind(coroutine_def_id).unwrap();
|
||||||
|
|
||||||
let lang_items = tcx.lang_items();
|
let coroutine_callable_item = if tcx.is_lang_item(trait_id, LangItem::Future) {
|
||||||
let coroutine_callable_item = if Some(trait_id) == lang_items.future_trait() {
|
|
||||||
assert_matches!(
|
assert_matches!(
|
||||||
coroutine_kind,
|
coroutine_kind,
|
||||||
hir::CoroutineKind::Desugared(hir::CoroutineDesugaring::Async, _)
|
hir::CoroutineKind::Desugared(hir::CoroutineDesugaring::Async, _)
|
||||||
);
|
);
|
||||||
hir::LangItem::FuturePoll
|
hir::LangItem::FuturePoll
|
||||||
} else if Some(trait_id) == lang_items.iterator_trait() {
|
} else if tcx.is_lang_item(trait_id, LangItem::Iterator) {
|
||||||
assert_matches!(
|
assert_matches!(
|
||||||
coroutine_kind,
|
coroutine_kind,
|
||||||
hir::CoroutineKind::Desugared(hir::CoroutineDesugaring::Gen, _)
|
hir::CoroutineKind::Desugared(hir::CoroutineDesugaring::Gen, _)
|
||||||
);
|
);
|
||||||
hir::LangItem::IteratorNext
|
hir::LangItem::IteratorNext
|
||||||
} else if Some(trait_id) == lang_items.async_iterator_trait() {
|
} else if tcx.is_lang_item(trait_id, LangItem::AsyncIterator) {
|
||||||
assert_matches!(
|
assert_matches!(
|
||||||
coroutine_kind,
|
coroutine_kind,
|
||||||
hir::CoroutineKind::Desugared(hir::CoroutineDesugaring::AsyncGen, _)
|
hir::CoroutineKind::Desugared(hir::CoroutineDesugaring::AsyncGen, _)
|
||||||
);
|
);
|
||||||
hir::LangItem::AsyncIteratorPollNext
|
hir::LangItem::AsyncIteratorPollNext
|
||||||
} else if Some(trait_id) == lang_items.coroutine_trait() {
|
} else if tcx.is_lang_item(trait_id, LangItem::Coroutine) {
|
||||||
assert_matches!(coroutine_kind, hir::CoroutineKind::Coroutine(_));
|
assert_matches!(coroutine_kind, hir::CoroutineKind::Coroutine(_));
|
||||||
hir::LangItem::CoroutineResume
|
hir::LangItem::CoroutineResume
|
||||||
} else {
|
} else {
|
||||||
|
@ -9,6 +9,7 @@ use rustc_errors::{
|
|||||||
};
|
};
|
||||||
use rustc_hir as hir;
|
use rustc_hir as hir;
|
||||||
use rustc_hir::def_id::DefId;
|
use rustc_hir::def_id::DefId;
|
||||||
|
use rustc_hir::LangItem;
|
||||||
use rustc_index::IndexVec;
|
use rustc_index::IndexVec;
|
||||||
use rustc_macros::{extension, HashStable, TyDecodable, TyEncodable};
|
use rustc_macros::{extension, HashStable, TyDecodable, TyEncodable};
|
||||||
use rustc_session::config::OptLevel;
|
use rustc_session::config::OptLevel;
|
||||||
@ -850,7 +851,7 @@ where
|
|||||||
// and we rely on this layout information to trigger a panic in
|
// and we rely on this layout information to trigger a panic in
|
||||||
// `std::mem::uninitialized::<&dyn Trait>()`, for example.
|
// `std::mem::uninitialized::<&dyn Trait>()`, for example.
|
||||||
if let ty::Adt(def, args) = metadata.kind()
|
if let ty::Adt(def, args) = metadata.kind()
|
||||||
&& Some(def.did()) == tcx.lang_items().dyn_metadata()
|
&& tcx.is_lang_item(def.did(), LangItem::DynMetadata)
|
||||||
&& let ty::Dynamic(data, _, ty::Dyn) = args.type_at(0).kind()
|
&& let ty::Dynamic(data, _, ty::Dyn) = args.type_at(0).kind()
|
||||||
{
|
{
|
||||||
mk_dyn_vtable(data.principal())
|
mk_dyn_vtable(data.principal())
|
||||||
@ -1169,7 +1170,7 @@ pub fn fn_can_unwind(tcx: TyCtxt<'_>, fn_def_id: Option<DefId>, abi: SpecAbi) ->
|
|||||||
// This is not part of `codegen_fn_attrs` as it can differ between crates
|
// This is not part of `codegen_fn_attrs` as it can differ between crates
|
||||||
// and therefore cannot be computed in core.
|
// and therefore cannot be computed in core.
|
||||||
if tcx.sess.opts.unstable_opts.panic_in_drop == PanicStrategy::Abort {
|
if tcx.sess.opts.unstable_opts.panic_in_drop == PanicStrategy::Abort {
|
||||||
if Some(did) == tcx.lang_items().drop_in_place_fn() {
|
if tcx.is_lang_item(did, LangItem::DropInPlace) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -999,7 +999,7 @@ pub trait PrettyPrinter<'tcx>: Printer<'tcx> + fmt::Write {
|
|||||||
let trait_ref = bound_predicate.rebind(pred.trait_ref);
|
let trait_ref = bound_predicate.rebind(pred.trait_ref);
|
||||||
|
|
||||||
// Don't print `+ Sized`, but rather `+ ?Sized` if absent.
|
// Don't print `+ Sized`, but rather `+ ?Sized` if absent.
|
||||||
if Some(trait_ref.def_id()) == tcx.lang_items().sized_trait() {
|
if tcx.is_lang_item(trait_ref.def_id(), LangItem::Sized) {
|
||||||
match pred.polarity {
|
match pred.polarity {
|
||||||
ty::PredicatePolarity::Positive => {
|
ty::PredicatePolarity::Positive => {
|
||||||
has_sized_bound = true;
|
has_sized_bound = true;
|
||||||
@ -1254,14 +1254,14 @@ pub trait PrettyPrinter<'tcx>: Printer<'tcx> + fmt::Write {
|
|||||||
}
|
}
|
||||||
entry.has_fn_once = true;
|
entry.has_fn_once = true;
|
||||||
return;
|
return;
|
||||||
} else if Some(trait_def_id) == self.tcx().lang_items().fn_mut_trait() {
|
} else if self.tcx().is_lang_item(trait_def_id, LangItem::FnMut) {
|
||||||
let super_trait_ref = supertraits_for_pretty_printing(self.tcx(), trait_ref)
|
let super_trait_ref = supertraits_for_pretty_printing(self.tcx(), trait_ref)
|
||||||
.find(|super_trait_ref| super_trait_ref.def_id() == fn_once_trait)
|
.find(|super_trait_ref| super_trait_ref.def_id() == fn_once_trait)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
fn_traits.entry(super_trait_ref).or_default().fn_mut_trait_ref = Some(trait_ref);
|
fn_traits.entry(super_trait_ref).or_default().fn_mut_trait_ref = Some(trait_ref);
|
||||||
return;
|
return;
|
||||||
} else if Some(trait_def_id) == self.tcx().lang_items().fn_trait() {
|
} else if self.tcx().is_lang_item(trait_def_id, LangItem::Fn) {
|
||||||
let super_trait_ref = supertraits_for_pretty_printing(self.tcx(), trait_ref)
|
let super_trait_ref = supertraits_for_pretty_printing(self.tcx(), trait_ref)
|
||||||
.find(|super_trait_ref| super_trait_ref.def_id() == fn_once_trait)
|
.find(|super_trait_ref| super_trait_ref.def_id() == fn_once_trait)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
@ -117,19 +117,19 @@ pub fn call_kind<'tcx>(
|
|||||||
kind.unwrap_or_else(|| {
|
kind.unwrap_or_else(|| {
|
||||||
// This isn't a 'special' use of `self`
|
// This isn't a 'special' use of `self`
|
||||||
debug!(?method_did, ?fn_call_span);
|
debug!(?method_did, ?fn_call_span);
|
||||||
let desugaring = if Some(method_did) == tcx.lang_items().into_iter_fn()
|
let desugaring = if tcx.is_lang_item(method_did, LangItem::IntoIterIntoIter)
|
||||||
&& fn_call_span.desugaring_kind() == Some(DesugaringKind::ForLoop)
|
&& fn_call_span.desugaring_kind() == Some(DesugaringKind::ForLoop)
|
||||||
{
|
{
|
||||||
Some((CallDesugaringKind::ForLoopIntoIter, method_args.type_at(0)))
|
Some((CallDesugaringKind::ForLoopIntoIter, method_args.type_at(0)))
|
||||||
} else if fn_call_span.desugaring_kind() == Some(DesugaringKind::QuestionMark) {
|
} else if fn_call_span.desugaring_kind() == Some(DesugaringKind::QuestionMark) {
|
||||||
if Some(method_did) == tcx.lang_items().branch_fn() {
|
if tcx.is_lang_item(method_did, LangItem::TryTraitBranch) {
|
||||||
Some((CallDesugaringKind::QuestionBranch, method_args.type_at(0)))
|
Some((CallDesugaringKind::QuestionBranch, method_args.type_at(0)))
|
||||||
} else if Some(method_did) == tcx.lang_items().from_residual_fn() {
|
} else if tcx.is_lang_item(method_did, LangItem::TryTraitFromResidual) {
|
||||||
Some((CallDesugaringKind::QuestionFromResidual, method_args.type_at(0)))
|
Some((CallDesugaringKind::QuestionFromResidual, method_args.type_at(0)))
|
||||||
} else {
|
} else {
|
||||||
None
|
None
|
||||||
}
|
}
|
||||||
} else if Some(method_did) == tcx.lang_items().from_output_fn()
|
} else if tcx.is_lang_item(method_did, LangItem::TryTraitFromOutput)
|
||||||
&& fn_call_span.desugaring_kind() == Some(DesugaringKind::TryBlock)
|
&& fn_call_span.desugaring_kind() == Some(DesugaringKind::TryBlock)
|
||||||
{
|
{
|
||||||
Some((CallDesugaringKind::TryBlockFromOutput, method_args.type_at(0)))
|
Some((CallDesugaringKind::TryBlockFromOutput, method_args.type_at(0)))
|
||||||
|
@ -2,6 +2,7 @@
|
|||||||
|
|
||||||
use crate::build::{parse_float_into_constval, Builder};
|
use crate::build::{parse_float_into_constval, Builder};
|
||||||
use rustc_ast as ast;
|
use rustc_ast as ast;
|
||||||
|
use rustc_hir::LangItem;
|
||||||
use rustc_middle::mir;
|
use rustc_middle::mir;
|
||||||
use rustc_middle::mir::interpret::{Allocation, LitToConstError, LitToConstInput, Scalar};
|
use rustc_middle::mir::interpret::{Allocation, LitToConstError, LitToConstInput, Scalar};
|
||||||
use rustc_middle::mir::*;
|
use rustc_middle::mir::*;
|
||||||
@ -142,7 +143,7 @@ fn lit_to_mir_constant<'tcx>(
|
|||||||
let id = tcx.allocate_bytes(data);
|
let id = tcx.allocate_bytes(data);
|
||||||
ConstValue::Scalar(Scalar::from_pointer(id.into(), &tcx))
|
ConstValue::Scalar(Scalar::from_pointer(id.into(), &tcx))
|
||||||
}
|
}
|
||||||
(ast::LitKind::CStr(data, _), ty::Ref(_, inner_ty, _)) if matches!(inner_ty.kind(), ty::Adt(def, _) if Some(def.did()) == tcx.lang_items().c_str()) =>
|
(ast::LitKind::CStr(data, _), ty::Ref(_, inner_ty, _)) if matches!(inner_ty.kind(), ty::Adt(def, _) if tcx.is_lang_item(def.did(), LangItem::CStr)) =>
|
||||||
{
|
{
|
||||||
let allocation = Allocation::from_bytes_byte_aligned_immutable(data as &[u8]);
|
let allocation = Allocation::from_bytes_byte_aligned_immutable(data as &[u8]);
|
||||||
let allocation = tcx.mk_const_alloc(allocation);
|
let allocation = tcx.mk_const_alloc(allocation);
|
||||||
|
@ -141,7 +141,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
|
|||||||
let success_block = target_block(TestBranch::Success);
|
let success_block = target_block(TestBranch::Success);
|
||||||
let fail_block = target_block(TestBranch::Failure);
|
let fail_block = target_block(TestBranch::Failure);
|
||||||
if let ty::Adt(def, _) = ty.kind()
|
if let ty::Adt(def, _) = ty.kind()
|
||||||
&& Some(def.did()) == tcx.lang_items().string()
|
&& tcx.is_lang_item(def.did(), LangItem::String)
|
||||||
{
|
{
|
||||||
if !tcx.features().string_deref_patterns {
|
if !tcx.features().string_deref_patterns {
|
||||||
bug!(
|
bug!(
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
use rustc_ast as ast;
|
use rustc_ast as ast;
|
||||||
|
use rustc_hir::LangItem;
|
||||||
use rustc_middle::bug;
|
use rustc_middle::bug;
|
||||||
use rustc_middle::mir::interpret::{LitToConstError, LitToConstInput};
|
use rustc_middle::mir::interpret::{LitToConstError, LitToConstInput};
|
||||||
use rustc_middle::ty::{self, ParamEnv, ScalarInt, TyCtxt};
|
use rustc_middle::ty::{self, ParamEnv, ScalarInt, TyCtxt};
|
||||||
@ -46,7 +47,7 @@ pub(crate) fn lit_to_const<'tcx>(
|
|||||||
(ast::LitKind::Byte(n), ty::Uint(ty::UintTy::U8)) => {
|
(ast::LitKind::Byte(n), ty::Uint(ty::UintTy::U8)) => {
|
||||||
ty::ValTree::from_scalar_int((*n).into())
|
ty::ValTree::from_scalar_int((*n).into())
|
||||||
}
|
}
|
||||||
(ast::LitKind::CStr(data, _), ty::Ref(_, inner_ty, _)) if matches!(inner_ty.kind(), ty::Adt(def, _) if Some(def.did()) == tcx.lang_items().c_str()) =>
|
(ast::LitKind::CStr(data, _), ty::Ref(_, inner_ty, _)) if matches!(inner_ty.kind(), ty::Adt(def, _) if tcx.is_lang_item(def.did(), LangItem::CStr)) =>
|
||||||
{
|
{
|
||||||
let bytes = data as &[u8];
|
let bytes = data as &[u8];
|
||||||
ty::ValTree::from_raw_bytes(tcx, bytes)
|
ty::ValTree::from_raw_bytes(tcx, bytes)
|
||||||
|
@ -454,8 +454,7 @@ where
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
let skip_contents =
|
let skip_contents = adt.is_union() || adt.is_manually_drop();
|
||||||
adt.is_union() || Some(adt.did()) == self.tcx().lang_items().manually_drop();
|
|
||||||
let contents_drop = if skip_contents {
|
let contents_drop = if skip_contents {
|
||||||
(self.succ, self.unwind)
|
(self.succ, self.unwind)
|
||||||
} else {
|
} else {
|
||||||
|
@ -4,6 +4,7 @@
|
|||||||
//! of MIR building, and only after this pass we think of the program has having the
|
//! of MIR building, and only after this pass we think of the program has having the
|
||||||
//! normal MIR semantics.
|
//! normal MIR semantics.
|
||||||
|
|
||||||
|
use rustc_hir::LangItem;
|
||||||
use rustc_middle::mir::*;
|
use rustc_middle::mir::*;
|
||||||
use rustc_middle::ty::{self, Ty, TyCtxt};
|
use rustc_middle::ty::{self, Ty, TyCtxt};
|
||||||
|
|
||||||
@ -27,7 +28,7 @@ fn may_contain_reference<'tcx>(ty: Ty<'tcx>, depth: u32, tcx: TyCtxt<'tcx>) -> b
|
|||||||
// References and Boxes (`noalias` sources)
|
// References and Boxes (`noalias` sources)
|
||||||
ty::Ref(..) => true,
|
ty::Ref(..) => true,
|
||||||
ty::Adt(..) if ty.is_box() => true,
|
ty::Adt(..) if ty.is_box() => true,
|
||||||
ty::Adt(adt, _) if Some(adt.did()) == tcx.lang_items().ptr_unique() => true,
|
ty::Adt(adt, _) if tcx.is_lang_item(adt.did(), LangItem::PtrUnique) => true,
|
||||||
// Compound types: recurse
|
// Compound types: recurse
|
||||||
ty::Array(ty, _) | ty::Slice(ty) => {
|
ty::Array(ty, _) | ty::Slice(ty) => {
|
||||||
// This does not branch so we keep the depth the same.
|
// This does not branch so we keep the depth the same.
|
||||||
|
@ -561,7 +561,7 @@ impl<'tcx> AsyncDestructorCtorShimBuilder<'tcx> {
|
|||||||
|
|
||||||
// If projection of Discriminant then compare with `Ty::discriminant_ty`
|
// If projection of Discriminant then compare with `Ty::discriminant_ty`
|
||||||
if let ty::Alias(ty::Projection, ty::AliasTy { args, def_id, .. }) = expected_ty.kind()
|
if let ty::Alias(ty::Projection, ty::AliasTy { args, def_id, .. }) = expected_ty.kind()
|
||||||
&& Some(*def_id) == self.tcx.lang_items().discriminant_type()
|
&& self.tcx.is_lang_item(*def_id, LangItem::Discriminant)
|
||||||
&& args.first().unwrap().as_type().unwrap().discriminant_ty(self.tcx) == operand_ty
|
&& args.first().unwrap().as_type().unwrap().discriminant_ty(self.tcx) == operand_ty
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
use rustc_data_structures::flat_map_in_place::FlatMapInPlace;
|
use rustc_data_structures::flat_map_in_place::FlatMapInPlace;
|
||||||
|
use rustc_hir::LangItem;
|
||||||
use rustc_index::bit_set::{BitSet, GrowableBitSet};
|
use rustc_index::bit_set::{BitSet, GrowableBitSet};
|
||||||
use rustc_index::IndexVec;
|
use rustc_index::IndexVec;
|
||||||
use rustc_middle::bug;
|
use rustc_middle::bug;
|
||||||
@ -70,7 +71,7 @@ fn escaping_locals<'tcx>(
|
|||||||
// Exclude #[repr(simd)] types so that they are not de-optimized into an array
|
// Exclude #[repr(simd)] types so that they are not de-optimized into an array
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if Some(def.did()) == tcx.lang_items().dyn_metadata() {
|
if tcx.is_lang_item(def.did(), LangItem::DynMetadata) {
|
||||||
// codegen wants to see the `DynMetadata<T>`,
|
// codegen wants to see the `DynMetadata<T>`,
|
||||||
// not the inner reference-to-opaque-type.
|
// not the inner reference-to-opaque-type.
|
||||||
return true;
|
return true;
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
//! Validates the MIR to ensure that invariants are upheld.
|
//! Validates the MIR to ensure that invariants are upheld.
|
||||||
|
|
||||||
use rustc_data_structures::fx::{FxHashMap, FxHashSet};
|
use rustc_data_structures::fx::{FxHashMap, FxHashSet};
|
||||||
|
use rustc_hir::LangItem;
|
||||||
use rustc_index::bit_set::BitSet;
|
use rustc_index::bit_set::BitSet;
|
||||||
use rustc_index::IndexVec;
|
use rustc_index::IndexVec;
|
||||||
use rustc_infer::traits::Reveal;
|
use rustc_infer::traits::Reveal;
|
||||||
@ -689,7 +690,7 @@ impl<'a, 'tcx> Visitor<'tcx> for TypeChecker<'a, 'tcx> {
|
|||||||
}
|
}
|
||||||
ty::Adt(adt_def, args) => {
|
ty::Adt(adt_def, args) => {
|
||||||
// see <https://github.com/rust-lang/rust/blob/7601adcc764d42c9f2984082b49948af652df986/compiler/rustc_middle/src/ty/layout.rs#L861-L864>
|
// see <https://github.com/rust-lang/rust/blob/7601adcc764d42c9f2984082b49948af652df986/compiler/rustc_middle/src/ty/layout.rs#L861-L864>
|
||||||
if Some(adt_def.did()) == self.tcx.lang_items().dyn_metadata() {
|
if self.tcx.is_lang_item(adt_def.did(), LangItem::DynMetadata) {
|
||||||
self.fail(
|
self.fail(
|
||||||
location,
|
location,
|
||||||
format!(
|
format!(
|
||||||
|
@ -593,7 +593,7 @@ fn check_recursion_limit<'tcx>(
|
|||||||
let recursion_depth = recursion_depths.get(&def_id).cloned().unwrap_or(0);
|
let recursion_depth = recursion_depths.get(&def_id).cloned().unwrap_or(0);
|
||||||
debug!(" => recursion depth={}", recursion_depth);
|
debug!(" => recursion depth={}", recursion_depth);
|
||||||
|
|
||||||
let adjusted_recursion_depth = if Some(def_id) == tcx.lang_items().drop_in_place_fn() {
|
let adjusted_recursion_depth = if tcx.is_lang_item(def_id, LangItem::DropInPlace) {
|
||||||
// HACK: drop_in_place creates tight monomorphization loops. Give
|
// HACK: drop_in_place creates tight monomorphization loops. Give
|
||||||
// it more margin.
|
// it more margin.
|
||||||
recursion_depth / 4
|
recursion_depth / 4
|
||||||
|
@ -104,6 +104,7 @@ use rustc_data_structures::unord::{UnordMap, UnordSet};
|
|||||||
use rustc_hir::def::DefKind;
|
use rustc_hir::def::DefKind;
|
||||||
use rustc_hir::def_id::{DefId, DefIdSet, LOCAL_CRATE};
|
use rustc_hir::def_id::{DefId, DefIdSet, LOCAL_CRATE};
|
||||||
use rustc_hir::definitions::DefPathDataName;
|
use rustc_hir::definitions::DefPathDataName;
|
||||||
|
use rustc_hir::LangItem;
|
||||||
use rustc_middle::bug;
|
use rustc_middle::bug;
|
||||||
use rustc_middle::middle::codegen_fn_attrs::CodegenFnAttrFlags;
|
use rustc_middle::middle::codegen_fn_attrs::CodegenFnAttrFlags;
|
||||||
use rustc_middle::middle::exported_symbols::{SymbolExportInfo, SymbolExportLevel};
|
use rustc_middle::middle::exported_symbols::{SymbolExportInfo, SymbolExportLevel};
|
||||||
@ -813,7 +814,7 @@ fn mono_item_visibility<'tcx>(
|
|||||||
// from the `main` symbol we'll generate later.
|
// from the `main` symbol we'll generate later.
|
||||||
//
|
//
|
||||||
// This may be fixable with a new `InstanceDef` perhaps? Unsure!
|
// This may be fixable with a new `InstanceDef` perhaps? Unsure!
|
||||||
if tcx.lang_items().start_fn() == Some(def_id) {
|
if tcx.is_lang_item(def_id, LangItem::Start) {
|
||||||
*can_be_internalized = false;
|
*can_be_internalized = false;
|
||||||
return Visibility::Hidden;
|
return Visibility::Hidden;
|
||||||
}
|
}
|
||||||
|
@ -289,7 +289,7 @@ pub fn transform_instance<'tcx>(
|
|||||||
options: TransformTyOptions,
|
options: TransformTyOptions,
|
||||||
) -> Instance<'tcx> {
|
) -> Instance<'tcx> {
|
||||||
if (matches!(instance.def, ty::InstanceDef::Virtual(..))
|
if (matches!(instance.def, ty::InstanceDef::Virtual(..))
|
||||||
&& Some(instance.def_id()) == tcx.lang_items().drop_in_place_fn())
|
&& tcx.is_lang_item(instance.def_id(), LangItem::DropInPlace))
|
||||||
|| matches!(instance.def, ty::InstanceDef::DropGlue(..))
|
|| matches!(instance.def, ty::InstanceDef::DropGlue(..))
|
||||||
{
|
{
|
||||||
// Adjust the type ids of DropGlues
|
// Adjust the type ids of DropGlues
|
||||||
|
@ -6,6 +6,7 @@
|
|||||||
#![allow(rustc::usage_of_qualified_ty)]
|
#![allow(rustc::usage_of_qualified_ty)]
|
||||||
|
|
||||||
use rustc_abi::HasDataLayout;
|
use rustc_abi::HasDataLayout;
|
||||||
|
use rustc_hir::LangItem;
|
||||||
use rustc_middle::ty::layout::{
|
use rustc_middle::ty::layout::{
|
||||||
FnAbiOf, FnAbiOfHelpers, HasParamEnv, HasTyCtxt, LayoutOf, LayoutOfHelpers,
|
FnAbiOf, FnAbiOfHelpers, HasParamEnv, HasTyCtxt, LayoutOf, LayoutOfHelpers,
|
||||||
};
|
};
|
||||||
@ -295,7 +296,7 @@ impl<'tcx> Context for TablesWrapper<'tcx> {
|
|||||||
let mut tables = self.0.borrow_mut();
|
let mut tables = self.0.borrow_mut();
|
||||||
let tcx = tables.tcx;
|
let tcx = tables.tcx;
|
||||||
let def_id = def.0.internal(&mut *tables, tcx);
|
let def_id = def.0.internal(&mut *tables, tcx);
|
||||||
tables.tcx.lang_items().c_str() == Some(def_id)
|
tables.tcx.is_lang_item(def_id, LangItem::CStr)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn fn_sig(&self, def: FnDef, args: &GenericArgs) -> PolyFnSig {
|
fn fn_sig(&self, def: FnDef, args: &GenericArgs) -> PolyFnSig {
|
||||||
|
@ -794,7 +794,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
|
|
||||||
if let ty::PredicateKind::Clause(ty::ClauseKind::Trait(trait_pred)) =
|
if let ty::PredicateKind::Clause(ty::ClauseKind::Trait(trait_pred)) =
|
||||||
obligation.predicate.kind().skip_binder()
|
obligation.predicate.kind().skip_binder()
|
||||||
&& Some(trait_pred.def_id()) == self.tcx.lang_items().sized_trait()
|
&& self.tcx.is_lang_item(trait_pred.def_id(), LangItem::Sized)
|
||||||
{
|
{
|
||||||
// Don't suggest calling to turn an unsized type into a sized type
|
// Don't suggest calling to turn an unsized type into a sized type
|
||||||
return false;
|
return false;
|
||||||
@ -1106,7 +1106,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
.iter()
|
.iter()
|
||||||
.find_map(|pred| {
|
.find_map(|pred| {
|
||||||
if let ty::ClauseKind::Projection(proj) = pred.kind().skip_binder()
|
if let ty::ClauseKind::Projection(proj) = pred.kind().skip_binder()
|
||||||
&& Some(proj.projection_term.def_id) == self.tcx.lang_items().fn_once_output()
|
&& self.tcx.is_lang_item(proj.projection_term.def_id,LangItem::FnOnceOutput)
|
||||||
// args tuple will always be args[1]
|
// args tuple will always be args[1]
|
||||||
&& let ty::Tuple(args) = proj.projection_term.args.type_at(1).kind()
|
&& let ty::Tuple(args) = proj.projection_term.args.type_at(1).kind()
|
||||||
{
|
{
|
||||||
@ -1123,7 +1123,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
ty::Dynamic(data, _, ty::Dyn) => {
|
ty::Dynamic(data, _, ty::Dyn) => {
|
||||||
data.iter().find_map(|pred| {
|
data.iter().find_map(|pred| {
|
||||||
if let ty::ExistentialPredicate::Projection(proj) = pred.skip_binder()
|
if let ty::ExistentialPredicate::Projection(proj) = pred.skip_binder()
|
||||||
&& Some(proj.def_id) == self.tcx.lang_items().fn_once_output()
|
&& self.tcx.is_lang_item(proj.def_id, LangItem::FnOnceOutput)
|
||||||
// for existential projection, args are shifted over by 1
|
// for existential projection, args are shifted over by 1
|
||||||
&& let ty::Tuple(args) = proj.args.type_at(0).kind()
|
&& let ty::Tuple(args) = proj.args.type_at(0).kind()
|
||||||
{
|
{
|
||||||
@ -1150,7 +1150,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
};
|
};
|
||||||
param_env.caller_bounds().iter().find_map(|pred| {
|
param_env.caller_bounds().iter().find_map(|pred| {
|
||||||
if let ty::ClauseKind::Projection(proj) = pred.kind().skip_binder()
|
if let ty::ClauseKind::Projection(proj) = pred.kind().skip_binder()
|
||||||
&& Some(proj.projection_term.def_id) == self.tcx.lang_items().fn_once_output()
|
&& self.tcx.is_lang_item(proj.projection_term.def_id, LangItem::FnOnceOutput)
|
||||||
&& proj.projection_term.self_ty() == found
|
&& proj.projection_term.self_ty() == found
|
||||||
// args tuple will always be args[1]
|
// args tuple will always be args[1]
|
||||||
&& let ty::Tuple(args) = proj.projection_term.args.type_at(1).kind()
|
&& let ty::Tuple(args) = proj.projection_term.args.type_at(1).kind()
|
||||||
@ -1822,7 +1822,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
&& box_path
|
&& box_path
|
||||||
.res
|
.res
|
||||||
.opt_def_id()
|
.opt_def_id()
|
||||||
.is_some_and(|def_id| Some(def_id) == self.tcx.lang_items().owned_box())
|
.is_some_and(|def_id| self.tcx.is_lang_item(def_id, LangItem::OwnedBox))
|
||||||
{
|
{
|
||||||
// Don't box `Box::new`
|
// Don't box `Box::new`
|
||||||
vec![]
|
vec![]
|
||||||
@ -2737,7 +2737,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
| ObligationCauseCode::ObjectTypeBound(..) => {}
|
| ObligationCauseCode::ObjectTypeBound(..) => {}
|
||||||
ObligationCauseCode::RustCall => {
|
ObligationCauseCode::RustCall => {
|
||||||
if let Some(pred) = predicate.as_trait_clause()
|
if let Some(pred) = predicate.as_trait_clause()
|
||||||
&& Some(pred.def_id()) == tcx.lang_items().sized_trait()
|
&& tcx.is_lang_item(pred.def_id(), LangItem::Sized)
|
||||||
{
|
{
|
||||||
err.note("argument required to be sized due to `extern \"rust-call\"` ABI");
|
err.note("argument required to be sized due to `extern \"rust-call\"` ABI");
|
||||||
}
|
}
|
||||||
@ -2790,7 +2790,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
// Check for foreign traits being reachable.
|
// Check for foreign traits being reachable.
|
||||||
tcx.visible_parent_map(()).get(&def_id).is_some()
|
tcx.visible_parent_map(()).get(&def_id).is_some()
|
||||||
};
|
};
|
||||||
if Some(def_id) == tcx.lang_items().sized_trait() {
|
if tcx.is_lang_item(def_id, LangItem::Sized) {
|
||||||
// Check if this is an implicit bound, even in foreign crates.
|
// Check if this is an implicit bound, even in foreign crates.
|
||||||
if tcx
|
if tcx
|
||||||
.generics_of(item_def_id)
|
.generics_of(item_def_id)
|
||||||
|
@ -24,10 +24,10 @@ use rustc_data_structures::unord::UnordSet;
|
|||||||
use rustc_errors::codes::*;
|
use rustc_errors::codes::*;
|
||||||
use rustc_errors::{pluralize, struct_span_code_err, Applicability, MultiSpan, StringPart};
|
use rustc_errors::{pluralize, struct_span_code_err, Applicability, MultiSpan, StringPart};
|
||||||
use rustc_errors::{Diag, EmissionGuarantee, ErrorGuaranteed, FatalError, StashKey};
|
use rustc_errors::{Diag, EmissionGuarantee, ErrorGuaranteed, FatalError, StashKey};
|
||||||
use rustc_hir as hir;
|
|
||||||
use rustc_hir::def::{DefKind, Namespace, Res};
|
use rustc_hir::def::{DefKind, Namespace, Res};
|
||||||
use rustc_hir::def_id::{DefId, LocalDefId};
|
use rustc_hir::def_id::{DefId, LocalDefId};
|
||||||
use rustc_hir::intravisit::Visitor;
|
use rustc_hir::intravisit::Visitor;
|
||||||
|
use rustc_hir::{self as hir, LangItem};
|
||||||
use rustc_hir::{GenericParam, Item, Node};
|
use rustc_hir::{GenericParam, Item, Node};
|
||||||
use rustc_infer::infer::error_reporting::TypeErrCtxt;
|
use rustc_infer::infer::error_reporting::TypeErrCtxt;
|
||||||
use rustc_infer::infer::{InferOk, TypeTrace};
|
use rustc_infer::infer::{InferOk, TypeTrace};
|
||||||
@ -118,7 +118,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
// with more relevant type information and hide redundant E0282 errors.
|
// with more relevant type information and hide redundant E0282 errors.
|
||||||
errors.sort_by_key(|e| match e.obligation.predicate.kind().skip_binder() {
|
errors.sort_by_key(|e| match e.obligation.predicate.kind().skip_binder() {
|
||||||
ty::PredicateKind::Clause(ty::ClauseKind::Trait(pred))
|
ty::PredicateKind::Clause(ty::ClauseKind::Trait(pred))
|
||||||
if Some(pred.def_id()) == self.tcx.lang_items().sized_trait() =>
|
if self.tcx.is_lang_item(pred.def_id(), LangItem::Sized) =>
|
||||||
{
|
{
|
||||||
1
|
1
|
||||||
}
|
}
|
||||||
@ -513,7 +513,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
let have_alt_message = message.is_some() || label.is_some();
|
let have_alt_message = message.is_some() || label.is_some();
|
||||||
let is_try_conversion = self.is_try_conversion(span, main_trait_ref.def_id());
|
let is_try_conversion = self.is_try_conversion(span, main_trait_ref.def_id());
|
||||||
let is_unsize =
|
let is_unsize =
|
||||||
Some(leaf_trait_ref.def_id()) == self.tcx.lang_items().unsize_trait();
|
self.tcx.is_lang_item(leaf_trait_ref.def_id(), LangItem::Unsize);
|
||||||
let (message, notes, append_const_msg) = if is_try_conversion {
|
let (message, notes, append_const_msg) = if is_try_conversion {
|
||||||
(
|
(
|
||||||
Some(format!(
|
Some(format!(
|
||||||
@ -586,14 +586,14 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if Some(leaf_trait_ref.def_id()) == tcx.lang_items().tuple_trait() {
|
if tcx.is_lang_item(leaf_trait_ref.def_id(), LangItem::Tuple) {
|
||||||
self.add_tuple_trait_message(
|
self.add_tuple_trait_message(
|
||||||
obligation.cause.code().peel_derives(),
|
obligation.cause.code().peel_derives(),
|
||||||
&mut err,
|
&mut err,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if Some(leaf_trait_ref.def_id()) == tcx.lang_items().drop_trait()
|
if tcx.is_lang_item(leaf_trait_ref.def_id(), LangItem::Drop)
|
||||||
&& predicate_is_const
|
&& predicate_is_const
|
||||||
{
|
{
|
||||||
err.note("`~const Drop` was renamed to `~const Destruct`");
|
err.note("`~const Drop` was renamed to `~const Destruct`");
|
||||||
@ -648,7 +648,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
if let ObligationCauseCode::Coercion { source, target } =
|
if let ObligationCauseCode::Coercion { source, target } =
|
||||||
*obligation.cause.code().peel_derives()
|
*obligation.cause.code().peel_derives()
|
||||||
{
|
{
|
||||||
if Some(leaf_trait_ref.def_id()) == self.tcx.lang_items().sized_trait() {
|
if self.tcx.is_lang_item(leaf_trait_ref.def_id(), LangItem::Sized) {
|
||||||
self.suggest_borrowing_for_object_cast(
|
self.suggest_borrowing_for_object_cast(
|
||||||
&mut err,
|
&mut err,
|
||||||
root_obligation,
|
root_obligation,
|
||||||
@ -716,7 +716,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
self.suggest_remove_await(&obligation, &mut err);
|
self.suggest_remove_await(&obligation, &mut err);
|
||||||
self.suggest_derive(&obligation, &mut err, leaf_trait_predicate);
|
self.suggest_derive(&obligation, &mut err, leaf_trait_predicate);
|
||||||
|
|
||||||
if Some(leaf_trait_ref.def_id()) == tcx.lang_items().try_trait() {
|
if tcx.is_lang_item(leaf_trait_ref.def_id(), LangItem::Try) {
|
||||||
self.suggest_await_before_try(
|
self.suggest_await_before_try(
|
||||||
&mut err,
|
&mut err,
|
||||||
&obligation,
|
&obligation,
|
||||||
@ -1020,7 +1020,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
// doesn't extend the goal kind. This is worth reporting, but we can only do so
|
// doesn't extend the goal kind. This is worth reporting, but we can only do so
|
||||||
// if we actually know which closure this goal comes from, so look at the cause
|
// if we actually know which closure this goal comes from, so look at the cause
|
||||||
// to see if we can extract that information.
|
// to see if we can extract that information.
|
||||||
if Some(trait_ref.def_id()) == self.tcx.lang_items().async_fn_kind_helper()
|
if self.tcx.is_lang_item(trait_ref.def_id(), LangItem::AsyncFnKindHelper)
|
||||||
&& let Some(found_kind) = trait_ref.skip_binder().args.type_at(0).to_opt_closure_kind()
|
&& let Some(found_kind) = trait_ref.skip_binder().args.type_at(0).to_opt_closure_kind()
|
||||||
&& let Some(expected_kind) =
|
&& let Some(expected_kind) =
|
||||||
trait_ref.skip_binder().args.type_at(1).to_opt_closure_kind()
|
trait_ref.skip_binder().args.type_at(1).to_opt_closure_kind()
|
||||||
@ -1744,7 +1744,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
let self_ty = pred.projection_term.self_ty();
|
let self_ty = pred.projection_term.self_ty();
|
||||||
|
|
||||||
with_forced_trimmed_paths! {
|
with_forced_trimmed_paths! {
|
||||||
if Some(pred.projection_term.def_id) == self.tcx.lang_items().fn_once_output() {
|
if self.tcx.is_lang_item(pred.projection_term.def_id,LangItem::FnOnceOutput) {
|
||||||
let fn_kind = self_ty.prefix_string(self.tcx);
|
let fn_kind = self_ty.prefix_string(self.tcx);
|
||||||
let item = match self_ty.kind() {
|
let item = match self_ty.kind() {
|
||||||
ty::FnDef(def, _) => self.tcx.item_name(*def).to_string(),
|
ty::FnDef(def, _) => self.tcx.item_name(*def).to_string(),
|
||||||
@ -1754,7 +1754,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
"expected `{item}` to be a {fn_kind} that returns `{expected_ty}`, but it \
|
"expected `{item}` to be a {fn_kind} that returns `{expected_ty}`, but it \
|
||||||
returns `{normalized_ty}`",
|
returns `{normalized_ty}`",
|
||||||
))
|
))
|
||||||
} else if Some(trait_def_id) == self.tcx.lang_items().future_trait() {
|
} else if self.tcx.is_lang_item(trait_def_id, LangItem::Future) {
|
||||||
Some(format!(
|
Some(format!(
|
||||||
"expected `{self_ty}` to be a future that resolves to `{expected_ty}`, but it \
|
"expected `{self_ty}` to be a future that resolves to `{expected_ty}`, but it \
|
||||||
resolves to `{normalized_ty}`"
|
resolves to `{normalized_ty}`"
|
||||||
@ -1783,7 +1783,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
ty::Bool => Some(0),
|
ty::Bool => Some(0),
|
||||||
ty::Char => Some(1),
|
ty::Char => Some(1),
|
||||||
ty::Str => Some(2),
|
ty::Str => Some(2),
|
||||||
ty::Adt(def, _) if Some(def.did()) == tcx.lang_items().string() => Some(2),
|
ty::Adt(def, _) if tcx.is_lang_item(def.did(), LangItem::String) => Some(2),
|
||||||
ty::Int(..)
|
ty::Int(..)
|
||||||
| ty::Uint(..)
|
| ty::Uint(..)
|
||||||
| ty::Float(..)
|
| ty::Float(..)
|
||||||
@ -2342,7 +2342,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
// avoid inundating the user with unnecessary errors, but we now
|
// avoid inundating the user with unnecessary errors, but we now
|
||||||
// check upstream for type errors and don't add the obligations to
|
// check upstream for type errors and don't add the obligations to
|
||||||
// begin with in those cases.
|
// begin with in those cases.
|
||||||
if self.tcx.lang_items().sized_trait() == Some(trait_ref.def_id()) {
|
if self.tcx.is_lang_item(trait_ref.def_id(), LangItem::Sized) {
|
||||||
match self.tainted_by_errors() {
|
match self.tainted_by_errors() {
|
||||||
None => {
|
None => {
|
||||||
let err = self.emit_inference_failure_err(
|
let err = self.emit_inference_failure_err(
|
||||||
@ -2925,7 +2925,7 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
|
|||||||
|
|
||||||
let (Some(node), true) = (
|
let (Some(node), true) = (
|
||||||
self.tcx.hir().get_if_local(item_def_id),
|
self.tcx.hir().get_if_local(item_def_id),
|
||||||
Some(pred.def_id()) == self.tcx.lang_items().sized_trait(),
|
self.tcx.is_lang_item(pred.def_id(), LangItem::Sized),
|
||||||
) else {
|
) else {
|
||||||
return;
|
return;
|
||||||
};
|
};
|
||||||
|
@ -1015,6 +1015,7 @@ fn assemble_candidates_from_impls<'cx, 'tcx>(
|
|||||||
// not eligible.
|
// not eligible.
|
||||||
let self_ty = selcx.infcx.shallow_resolve(obligation.predicate.self_ty());
|
let self_ty = selcx.infcx.shallow_resolve(obligation.predicate.self_ty());
|
||||||
|
|
||||||
|
let tcx = selcx.tcx();
|
||||||
let lang_items = selcx.tcx().lang_items();
|
let lang_items = selcx.tcx().lang_items();
|
||||||
if [
|
if [
|
||||||
lang_items.coroutine_trait(),
|
lang_items.coroutine_trait(),
|
||||||
@ -1031,7 +1032,7 @@ fn assemble_candidates_from_impls<'cx, 'tcx>(
|
|||||||
.contains(&Some(trait_ref.def_id))
|
.contains(&Some(trait_ref.def_id))
|
||||||
{
|
{
|
||||||
true
|
true
|
||||||
} else if lang_items.async_fn_kind_helper() == Some(trait_ref.def_id) {
|
} else if tcx.is_lang_item(trait_ref.def_id, LangItem::AsyncFnKindHelper) {
|
||||||
// FIXME(async_closures): Validity constraints here could be cleaned up.
|
// FIXME(async_closures): Validity constraints here could be cleaned up.
|
||||||
if obligation.predicate.args.type_at(0).is_ty_var()
|
if obligation.predicate.args.type_at(0).is_ty_var()
|
||||||
|| obligation.predicate.args.type_at(4).is_ty_var()
|
|| obligation.predicate.args.type_at(4).is_ty_var()
|
||||||
@ -1043,7 +1044,7 @@ fn assemble_candidates_from_impls<'cx, 'tcx>(
|
|||||||
obligation.predicate.args.type_at(0).to_opt_closure_kind().is_some()
|
obligation.predicate.args.type_at(0).to_opt_closure_kind().is_some()
|
||||||
&& obligation.predicate.args.type_at(1).to_opt_closure_kind().is_some()
|
&& obligation.predicate.args.type_at(1).to_opt_closure_kind().is_some()
|
||||||
}
|
}
|
||||||
} else if lang_items.discriminant_kind_trait() == Some(trait_ref.def_id) {
|
} else if tcx.is_lang_item(trait_ref.def_id, LangItem::DiscriminantKind) {
|
||||||
match self_ty.kind() {
|
match self_ty.kind() {
|
||||||
ty::Bool
|
ty::Bool
|
||||||
| ty::Char
|
| ty::Char
|
||||||
@ -1080,7 +1081,7 @@ fn assemble_candidates_from_impls<'cx, 'tcx>(
|
|||||||
| ty::Infer(..)
|
| ty::Infer(..)
|
||||||
| ty::Error(_) => false,
|
| ty::Error(_) => false,
|
||||||
}
|
}
|
||||||
} else if lang_items.async_destruct_trait() == Some(trait_ref.def_id) {
|
} else if tcx.is_lang_item(trait_ref.def_id, LangItem::AsyncDestruct) {
|
||||||
match self_ty.kind() {
|
match self_ty.kind() {
|
||||||
ty::Bool
|
ty::Bool
|
||||||
| ty::Char
|
| ty::Char
|
||||||
@ -1116,7 +1117,7 @@ fn assemble_candidates_from_impls<'cx, 'tcx>(
|
|||||||
| ty::Infer(_)
|
| ty::Infer(_)
|
||||||
| ty::Error(_) => false,
|
| ty::Error(_) => false,
|
||||||
}
|
}
|
||||||
} else if lang_items.pointee_trait() == Some(trait_ref.def_id) {
|
} else if tcx.is_lang_item(trait_ref.def_id, LangItem::PointeeTrait) {
|
||||||
let tail = selcx.tcx().struct_tail_with_normalize(
|
let tail = selcx.tcx().struct_tail_with_normalize(
|
||||||
self_ty,
|
self_ty,
|
||||||
|ty| {
|
|ty| {
|
||||||
@ -1300,15 +1301,15 @@ fn confirm_select_candidate<'cx, 'tcx>(
|
|||||||
match impl_source {
|
match impl_source {
|
||||||
ImplSource::UserDefined(data) => confirm_impl_candidate(selcx, obligation, data),
|
ImplSource::UserDefined(data) => confirm_impl_candidate(selcx, obligation, data),
|
||||||
ImplSource::Builtin(BuiltinImplSource::Misc, data) => {
|
ImplSource::Builtin(BuiltinImplSource::Misc, data) => {
|
||||||
let trait_def_id = obligation.predicate.trait_def_id(selcx.tcx());
|
let tcx = selcx.tcx();
|
||||||
let lang_items = selcx.tcx().lang_items();
|
let trait_def_id = obligation.predicate.trait_def_id(tcx);
|
||||||
if lang_items.coroutine_trait() == Some(trait_def_id) {
|
if tcx.is_lang_item(trait_def_id, LangItem::Coroutine) {
|
||||||
confirm_coroutine_candidate(selcx, obligation, data)
|
confirm_coroutine_candidate(selcx, obligation, data)
|
||||||
} else if lang_items.future_trait() == Some(trait_def_id) {
|
} else if tcx.is_lang_item(trait_def_id, LangItem::Future) {
|
||||||
confirm_future_candidate(selcx, obligation, data)
|
confirm_future_candidate(selcx, obligation, data)
|
||||||
} else if lang_items.iterator_trait() == Some(trait_def_id) {
|
} else if tcx.is_lang_item(trait_def_id, LangItem::Iterator) {
|
||||||
confirm_iterator_candidate(selcx, obligation, data)
|
confirm_iterator_candidate(selcx, obligation, data)
|
||||||
} else if lang_items.async_iterator_trait() == Some(trait_def_id) {
|
} else if tcx.is_lang_item(trait_def_id, LangItem::AsyncIterator) {
|
||||||
confirm_async_iterator_candidate(selcx, obligation, data)
|
confirm_async_iterator_candidate(selcx, obligation, data)
|
||||||
} else if selcx.tcx().fn_trait_kind_from_def_id(trait_def_id).is_some() {
|
} else if selcx.tcx().fn_trait_kind_from_def_id(trait_def_id).is_some() {
|
||||||
if obligation.predicate.self_ty().is_closure()
|
if obligation.predicate.self_ty().is_closure()
|
||||||
@ -1320,7 +1321,7 @@ fn confirm_select_candidate<'cx, 'tcx>(
|
|||||||
}
|
}
|
||||||
} else if selcx.tcx().async_fn_trait_kind_from_def_id(trait_def_id).is_some() {
|
} else if selcx.tcx().async_fn_trait_kind_from_def_id(trait_def_id).is_some() {
|
||||||
confirm_async_closure_candidate(selcx, obligation, data)
|
confirm_async_closure_candidate(selcx, obligation, data)
|
||||||
} else if lang_items.async_fn_kind_helper() == Some(trait_def_id) {
|
} else if tcx.is_lang_item(trait_def_id, LangItem::AsyncFnKindHelper) {
|
||||||
confirm_async_fn_kind_helper_candidate(selcx, obligation, data)
|
confirm_async_fn_kind_helper_candidate(selcx, obligation, data)
|
||||||
} else {
|
} else {
|
||||||
confirm_builtin_candidate(selcx, obligation, data)
|
confirm_builtin_candidate(selcx, obligation, data)
|
||||||
@ -1373,10 +1374,9 @@ fn confirm_coroutine_candidate<'cx, 'tcx>(
|
|||||||
coroutine_sig,
|
coroutine_sig,
|
||||||
);
|
);
|
||||||
|
|
||||||
let lang_items = tcx.lang_items();
|
let ty = if tcx.is_lang_item(obligation.predicate.def_id, LangItem::CoroutineReturn) {
|
||||||
let ty = if Some(obligation.predicate.def_id) == lang_items.coroutine_return() {
|
|
||||||
return_ty
|
return_ty
|
||||||
} else if Some(obligation.predicate.def_id) == lang_items.coroutine_yield() {
|
} else if tcx.is_lang_item(obligation.predicate.def_id, LangItem::CoroutineYield) {
|
||||||
yield_ty
|
yield_ty
|
||||||
} else {
|
} else {
|
||||||
span_bug!(
|
span_bug!(
|
||||||
@ -1539,21 +1539,20 @@ fn confirm_builtin_candidate<'cx, 'tcx>(
|
|||||||
) -> Progress<'tcx> {
|
) -> Progress<'tcx> {
|
||||||
let tcx = selcx.tcx();
|
let tcx = selcx.tcx();
|
||||||
let self_ty = obligation.predicate.self_ty();
|
let self_ty = obligation.predicate.self_ty();
|
||||||
let lang_items = tcx.lang_items();
|
|
||||||
let item_def_id = obligation.predicate.def_id;
|
let item_def_id = obligation.predicate.def_id;
|
||||||
let trait_def_id = tcx.trait_of_item(item_def_id).unwrap();
|
let trait_def_id = tcx.trait_of_item(item_def_id).unwrap();
|
||||||
let args = tcx.mk_args(&[self_ty.into()]);
|
let args = tcx.mk_args(&[self_ty.into()]);
|
||||||
let (term, obligations) = if lang_items.discriminant_kind_trait() == Some(trait_def_id) {
|
let (term, obligations) = if tcx.is_lang_item(trait_def_id, LangItem::DiscriminantKind) {
|
||||||
let discriminant_def_id = tcx.require_lang_item(LangItem::Discriminant, None);
|
let discriminant_def_id = tcx.require_lang_item(LangItem::Discriminant, None);
|
||||||
assert_eq!(discriminant_def_id, item_def_id);
|
assert_eq!(discriminant_def_id, item_def_id);
|
||||||
|
|
||||||
(self_ty.discriminant_ty(tcx).into(), Vec::new())
|
(self_ty.discriminant_ty(tcx).into(), Vec::new())
|
||||||
} else if lang_items.async_destruct_trait() == Some(trait_def_id) {
|
} else if tcx.is_lang_item(trait_def_id, LangItem::AsyncDestruct) {
|
||||||
let destructor_def_id = tcx.associated_item_def_ids(trait_def_id)[0];
|
let destructor_def_id = tcx.associated_item_def_ids(trait_def_id)[0];
|
||||||
assert_eq!(destructor_def_id, item_def_id);
|
assert_eq!(destructor_def_id, item_def_id);
|
||||||
|
|
||||||
(self_ty.async_destructor_ty(tcx).into(), Vec::new())
|
(self_ty.async_destructor_ty(tcx).into(), Vec::new())
|
||||||
} else if lang_items.pointee_trait() == Some(trait_def_id) {
|
} else if tcx.is_lang_item(trait_def_id, LangItem::PointeeTrait) {
|
||||||
let metadata_def_id = tcx.require_lang_item(LangItem::Metadata, None);
|
let metadata_def_id = tcx.require_lang_item(LangItem::Metadata, None);
|
||||||
assert_eq!(metadata_def_id, item_def_id);
|
assert_eq!(metadata_def_id, item_def_id);
|
||||||
|
|
||||||
|
@ -55,7 +55,7 @@ pub fn trivial_dropck_outlives<'tcx>(tcx: TyCtxt<'tcx>, ty: Ty<'tcx>) -> bool {
|
|||||||
}
|
}
|
||||||
|
|
||||||
ty::Adt(def, _) => {
|
ty::Adt(def, _) => {
|
||||||
if Some(def.did()) == tcx.lang_items().manually_drop() {
|
if def.is_manually_drop() {
|
||||||
// `ManuallyDrop` never has a dtor.
|
// `ManuallyDrop` never has a dtor.
|
||||||
true
|
true
|
||||||
} else {
|
} else {
|
||||||
|
@ -67,9 +67,9 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
|
|||||||
// Other bounds. Consider both in-scope bounds from fn decl
|
// Other bounds. Consider both in-scope bounds from fn decl
|
||||||
// and applicable impls. There is a certain set of precedence rules here.
|
// and applicable impls. There is a certain set of precedence rules here.
|
||||||
let def_id = obligation.predicate.def_id();
|
let def_id = obligation.predicate.def_id();
|
||||||
let lang_items = self.tcx().lang_items();
|
let tcx = self.tcx();
|
||||||
|
|
||||||
if lang_items.copy_trait() == Some(def_id) {
|
if tcx.is_lang_item(def_id, LangItem::Copy) {
|
||||||
debug!(obligation_self_ty = ?obligation.predicate.skip_binder().self_ty());
|
debug!(obligation_self_ty = ?obligation.predicate.skip_binder().self_ty());
|
||||||
|
|
||||||
// User-defined copy impls are permitted, but only for
|
// User-defined copy impls are permitted, but only for
|
||||||
@ -79,16 +79,16 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
|
|||||||
// For other types, we'll use the builtin rules.
|
// For other types, we'll use the builtin rules.
|
||||||
let copy_conditions = self.copy_clone_conditions(obligation);
|
let copy_conditions = self.copy_clone_conditions(obligation);
|
||||||
self.assemble_builtin_bound_candidates(copy_conditions, &mut candidates);
|
self.assemble_builtin_bound_candidates(copy_conditions, &mut candidates);
|
||||||
} else if lang_items.discriminant_kind_trait() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::DiscriminantKind) {
|
||||||
// `DiscriminantKind` is automatically implemented for every type.
|
// `DiscriminantKind` is automatically implemented for every type.
|
||||||
candidates.vec.push(BuiltinCandidate { has_nested: false });
|
candidates.vec.push(BuiltinCandidate { has_nested: false });
|
||||||
} else if lang_items.async_destruct_trait() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::AsyncDestruct) {
|
||||||
// `AsyncDestruct` is automatically implemented for every type.
|
// `AsyncDestruct` is automatically implemented for every type.
|
||||||
candidates.vec.push(BuiltinCandidate { has_nested: false });
|
candidates.vec.push(BuiltinCandidate { has_nested: false });
|
||||||
} else if lang_items.pointee_trait() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::PointeeTrait) {
|
||||||
// `Pointee` is automatically implemented for every type.
|
// `Pointee` is automatically implemented for every type.
|
||||||
candidates.vec.push(BuiltinCandidate { has_nested: false });
|
candidates.vec.push(BuiltinCandidate { has_nested: false });
|
||||||
} else if lang_items.sized_trait() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::Sized) {
|
||||||
// Sized is never implementable by end-users, it is
|
// Sized is never implementable by end-users, it is
|
||||||
// always automatically computed.
|
// always automatically computed.
|
||||||
|
|
||||||
@ -101,22 +101,22 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
|
|||||||
|
|
||||||
let sized_conditions = self.sized_conditions(obligation);
|
let sized_conditions = self.sized_conditions(obligation);
|
||||||
self.assemble_builtin_bound_candidates(sized_conditions, &mut candidates);
|
self.assemble_builtin_bound_candidates(sized_conditions, &mut candidates);
|
||||||
} else if lang_items.unsize_trait() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::Unsize) {
|
||||||
self.assemble_candidates_for_unsizing(obligation, &mut candidates);
|
self.assemble_candidates_for_unsizing(obligation, &mut candidates);
|
||||||
} else if lang_items.destruct_trait() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::Destruct) {
|
||||||
self.assemble_const_destruct_candidates(obligation, &mut candidates);
|
self.assemble_const_destruct_candidates(obligation, &mut candidates);
|
||||||
} else if lang_items.transmute_trait() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::TransmuteTrait) {
|
||||||
// User-defined transmutability impls are permitted.
|
// User-defined transmutability impls are permitted.
|
||||||
self.assemble_candidates_from_impls(obligation, &mut candidates);
|
self.assemble_candidates_from_impls(obligation, &mut candidates);
|
||||||
self.assemble_candidates_for_transmutability(obligation, &mut candidates);
|
self.assemble_candidates_for_transmutability(obligation, &mut candidates);
|
||||||
} else if lang_items.tuple_trait() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::Tuple) {
|
||||||
self.assemble_candidate_for_tuple(obligation, &mut candidates);
|
self.assemble_candidate_for_tuple(obligation, &mut candidates);
|
||||||
} else if lang_items.pointer_like() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::PointerLike) {
|
||||||
self.assemble_candidate_for_pointer_like(obligation, &mut candidates);
|
self.assemble_candidate_for_pointer_like(obligation, &mut candidates);
|
||||||
} else if lang_items.fn_ptr_trait() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::FnPtrTrait) {
|
||||||
self.assemble_candidates_for_fn_ptr_trait(obligation, &mut candidates);
|
self.assemble_candidates_for_fn_ptr_trait(obligation, &mut candidates);
|
||||||
} else {
|
} else {
|
||||||
if lang_items.clone_trait() == Some(def_id) {
|
if tcx.is_lang_item(def_id, LangItem::Clone) {
|
||||||
// Same builtin conditions as `Copy`, i.e., every type which has builtin support
|
// Same builtin conditions as `Copy`, i.e., every type which has builtin support
|
||||||
// for `Copy` also has builtin support for `Clone`, and tuples/arrays of `Clone`
|
// for `Copy` also has builtin support for `Clone`, and tuples/arrays of `Clone`
|
||||||
// types have builtin support for `Clone`.
|
// types have builtin support for `Clone`.
|
||||||
@ -124,17 +124,17 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
|
|||||||
self.assemble_builtin_bound_candidates(clone_conditions, &mut candidates);
|
self.assemble_builtin_bound_candidates(clone_conditions, &mut candidates);
|
||||||
}
|
}
|
||||||
|
|
||||||
if lang_items.coroutine_trait() == Some(def_id) {
|
if tcx.is_lang_item(def_id, LangItem::Coroutine) {
|
||||||
self.assemble_coroutine_candidates(obligation, &mut candidates);
|
self.assemble_coroutine_candidates(obligation, &mut candidates);
|
||||||
} else if lang_items.future_trait() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::Future) {
|
||||||
self.assemble_future_candidates(obligation, &mut candidates);
|
self.assemble_future_candidates(obligation, &mut candidates);
|
||||||
} else if lang_items.iterator_trait() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::Iterator) {
|
||||||
self.assemble_iterator_candidates(obligation, &mut candidates);
|
self.assemble_iterator_candidates(obligation, &mut candidates);
|
||||||
} else if lang_items.fused_iterator_trait() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::FusedIterator) {
|
||||||
self.assemble_fused_iterator_candidates(obligation, &mut candidates);
|
self.assemble_fused_iterator_candidates(obligation, &mut candidates);
|
||||||
} else if lang_items.async_iterator_trait() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::AsyncIterator) {
|
||||||
self.assemble_async_iterator_candidates(obligation, &mut candidates);
|
self.assemble_async_iterator_candidates(obligation, &mut candidates);
|
||||||
} else if lang_items.async_fn_kind_helper() == Some(def_id) {
|
} else if tcx.is_lang_item(def_id, LangItem::AsyncFnKindHelper) {
|
||||||
self.assemble_async_fn_kind_helper_candidates(obligation, &mut candidates);
|
self.assemble_async_fn_kind_helper_candidates(obligation, &mut candidates);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -755,7 +755,7 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
|
|||||||
candidates.ambiguous = true;
|
candidates.ambiguous = true;
|
||||||
}
|
}
|
||||||
ty::Coroutine(coroutine_def_id, _)
|
ty::Coroutine(coroutine_def_id, _)
|
||||||
if self.tcx().lang_items().unpin_trait() == Some(def_id) =>
|
if self.tcx().is_lang_item(def_id, LangItem::Unpin) =>
|
||||||
{
|
{
|
||||||
match self.tcx().coroutine_movability(coroutine_def_id) {
|
match self.tcx().coroutine_movability(coroutine_def_id) {
|
||||||
hir::Movability::Static => {
|
hir::Movability::Static => {
|
||||||
|
@ -258,16 +258,16 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
|
|||||||
) -> Vec<PredicateObligation<'tcx>> {
|
) -> Vec<PredicateObligation<'tcx>> {
|
||||||
debug!(?obligation, ?has_nested, "confirm_builtin_candidate");
|
debug!(?obligation, ?has_nested, "confirm_builtin_candidate");
|
||||||
|
|
||||||
let lang_items = self.tcx().lang_items();
|
let tcx = self.tcx();
|
||||||
let obligations = if has_nested {
|
let obligations = if has_nested {
|
||||||
let trait_def = obligation.predicate.def_id();
|
let trait_def = obligation.predicate.def_id();
|
||||||
let conditions = if Some(trait_def) == lang_items.sized_trait() {
|
let conditions = if tcx.is_lang_item(trait_def, LangItem::Sized) {
|
||||||
self.sized_conditions(obligation)
|
self.sized_conditions(obligation)
|
||||||
} else if Some(trait_def) == lang_items.copy_trait() {
|
} else if tcx.is_lang_item(trait_def, LangItem::Copy) {
|
||||||
self.copy_clone_conditions(obligation)
|
self.copy_clone_conditions(obligation)
|
||||||
} else if Some(trait_def) == lang_items.clone_trait() {
|
} else if tcx.is_lang_item(trait_def, LangItem::Clone) {
|
||||||
self.copy_clone_conditions(obligation)
|
self.copy_clone_conditions(obligation)
|
||||||
} else if Some(trait_def) == lang_items.fused_iterator_trait() {
|
} else if tcx.is_lang_item(trait_def, LangItem::FusedIterator) {
|
||||||
self.fused_iterator_conditions(obligation)
|
self.fused_iterator_conditions(obligation)
|
||||||
} else {
|
} else {
|
||||||
bug!("unexpected builtin trait {:?}", trait_def)
|
bug!("unexpected builtin trait {:?}", trait_def)
|
||||||
@ -1444,7 +1444,7 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
|
|||||||
| ty::Foreign(_) => {}
|
| ty::Foreign(_) => {}
|
||||||
|
|
||||||
// `ManuallyDrop` is trivially drop
|
// `ManuallyDrop` is trivially drop
|
||||||
ty::Adt(def, _) if Some(def.did()) == tcx.lang_items().manually_drop() => {}
|
ty::Adt(def, _) if def.is_manually_drop() => {}
|
||||||
|
|
||||||
// These types are built-in, so we can fast-track by registering
|
// These types are built-in, so we can fast-track by registering
|
||||||
// nested predicates for their constituent type(s)
|
// nested predicates for their constituent type(s)
|
||||||
|
@ -32,6 +32,7 @@ use rustc_data_structures::stack::ensure_sufficient_stack;
|
|||||||
use rustc_errors::{Diag, EmissionGuarantee};
|
use rustc_errors::{Diag, EmissionGuarantee};
|
||||||
use rustc_hir as hir;
|
use rustc_hir as hir;
|
||||||
use rustc_hir::def_id::DefId;
|
use rustc_hir::def_id::DefId;
|
||||||
|
use rustc_hir::LangItem;
|
||||||
use rustc_infer::infer::relate::TypeRelation;
|
use rustc_infer::infer::relate::TypeRelation;
|
||||||
use rustc_infer::infer::BoundRegionConversionTime;
|
use rustc_infer::infer::BoundRegionConversionTime;
|
||||||
use rustc_infer::infer::BoundRegionConversionTime::HigherRankedType;
|
use rustc_infer::infer::BoundRegionConversionTime::HigherRankedType;
|
||||||
@ -2800,19 +2801,18 @@ impl<'tcx> SelectionContext<'_, 'tcx> {
|
|||||||
let predicates = predicates.instantiate_own(tcx, args);
|
let predicates = predicates.instantiate_own(tcx, args);
|
||||||
let mut obligations = Vec::with_capacity(predicates.len());
|
let mut obligations = Vec::with_capacity(predicates.len());
|
||||||
for (index, (predicate, span)) in predicates.into_iter().enumerate() {
|
for (index, (predicate, span)) in predicates.into_iter().enumerate() {
|
||||||
let cause =
|
let cause = if tcx.is_lang_item(parent_trait_pred.def_id(), LangItem::CoerceUnsized) {
|
||||||
if Some(parent_trait_pred.def_id()) == tcx.lang_items().coerce_unsized_trait() {
|
cause.clone()
|
||||||
cause.clone()
|
} else {
|
||||||
} else {
|
cause.clone().derived_cause(parent_trait_pred, |derived| {
|
||||||
cause.clone().derived_cause(parent_trait_pred, |derived| {
|
ObligationCauseCode::ImplDerived(Box::new(ImplDerivedCause {
|
||||||
ObligationCauseCode::ImplDerived(Box::new(ImplDerivedCause {
|
derived,
|
||||||
derived,
|
impl_or_alias_def_id: def_id,
|
||||||
impl_or_alias_def_id: def_id,
|
impl_def_predicate_index: Some(index),
|
||||||
impl_def_predicate_index: Some(index),
|
span,
|
||||||
span,
|
}))
|
||||||
}))
|
})
|
||||||
})
|
};
|
||||||
};
|
|
||||||
let clause = normalize_with_depth_to(
|
let clause = normalize_with_depth_to(
|
||||||
self,
|
self,
|
||||||
param_env,
|
param_env,
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
use rustc_errors::ErrorGuaranteed;
|
use rustc_errors::ErrorGuaranteed;
|
||||||
use rustc_hir::def_id::DefId;
|
use rustc_hir::def_id::DefId;
|
||||||
|
use rustc_hir::LangItem;
|
||||||
use rustc_infer::infer::TyCtxtInferExt;
|
use rustc_infer::infer::TyCtxtInferExt;
|
||||||
use rustc_middle::bug;
|
use rustc_middle::bug;
|
||||||
use rustc_middle::query::Providers;
|
use rustc_middle::query::Providers;
|
||||||
@ -34,7 +35,7 @@ fn resolve_instance<'tcx>(
|
|||||||
let def = if tcx.intrinsic(def_id).is_some() {
|
let def = if tcx.intrinsic(def_id).is_some() {
|
||||||
debug!(" => intrinsic");
|
debug!(" => intrinsic");
|
||||||
ty::InstanceDef::Intrinsic(def_id)
|
ty::InstanceDef::Intrinsic(def_id)
|
||||||
} else if Some(def_id) == tcx.lang_items().drop_in_place_fn() {
|
} else if tcx.is_lang_item(def_id, LangItem::DropInPlace) {
|
||||||
let ty = args.type_at(0);
|
let ty = args.type_at(0);
|
||||||
|
|
||||||
if ty.needs_drop(tcx, param_env) {
|
if ty.needs_drop(tcx, param_env) {
|
||||||
@ -57,7 +58,7 @@ fn resolve_instance<'tcx>(
|
|||||||
debug!(" => trivial drop glue");
|
debug!(" => trivial drop glue");
|
||||||
ty::InstanceDef::DropGlue(def_id, None)
|
ty::InstanceDef::DropGlue(def_id, None)
|
||||||
}
|
}
|
||||||
} else if Some(def_id) == tcx.lang_items().async_drop_in_place_fn() {
|
} else if tcx.is_lang_item(def_id, LangItem::AsyncDropInPlace) {
|
||||||
let ty = args.type_at(0);
|
let ty = args.type_at(0);
|
||||||
|
|
||||||
if ty.async_drop_glue_morphology(tcx) != AsyncDropGlueMorphology::Noop {
|
if ty.async_drop_glue_morphology(tcx) != AsyncDropGlueMorphology::Noop {
|
||||||
@ -221,8 +222,7 @@ fn resolve_associated_item<'tcx>(
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
traits::ImplSource::Builtin(BuiltinImplSource::Misc, _) => {
|
traits::ImplSource::Builtin(BuiltinImplSource::Misc, _) => {
|
||||||
let lang_items = tcx.lang_items();
|
if tcx.is_lang_item(trait_ref.def_id, LangItem::Clone) {
|
||||||
if Some(trait_ref.def_id) == lang_items.clone_trait() {
|
|
||||||
// FIXME(eddyb) use lang items for methods instead of names.
|
// FIXME(eddyb) use lang items for methods instead of names.
|
||||||
let name = tcx.item_name(trait_item_id);
|
let name = tcx.item_name(trait_item_id);
|
||||||
if name == sym::clone {
|
if name == sym::clone {
|
||||||
@ -248,8 +248,8 @@ fn resolve_associated_item<'tcx>(
|
|||||||
let args = tcx.erase_regions(rcvr_args);
|
let args = tcx.erase_regions(rcvr_args);
|
||||||
Some(ty::Instance::new(trait_item_id, args))
|
Some(ty::Instance::new(trait_item_id, args))
|
||||||
}
|
}
|
||||||
} else if Some(trait_ref.def_id) == lang_items.fn_ptr_trait() {
|
} else if tcx.is_lang_item(trait_ref.def_id, LangItem::FnPtrTrait) {
|
||||||
if lang_items.fn_ptr_addr() == Some(trait_item_id) {
|
if tcx.is_lang_item(trait_item_id, LangItem::FnPtrAddr) {
|
||||||
let self_ty = trait_ref.self_ty();
|
let self_ty = trait_ref.self_ty();
|
||||||
if !matches!(self_ty.kind(), ty::FnPtr(..)) {
|
if !matches!(self_ty.kind(), ty::FnPtr(..)) {
|
||||||
return Ok(None);
|
return Ok(None);
|
||||||
|
Loading…
Reference in New Issue
Block a user