1use rustc_abi::ExternAbi;
2use rustc_ast::visit::AssocCtxt;
3use rustc_ast::*;
4use rustc_errors::{E0570, ErrorGuaranteed, struct_span_code_err};
5use rustc_hir::attrs::{AttributeKind, EiiImplResolution};
6use rustc_hir::def::{DefKind, PerNS, Res};
7use rustc_hir::{
8 self as hir, CRATE_OWNER_ID, HirId, ImplItemImplKind, LifetimeSource, PredicateOrigin, Target,
9 find_attr,
10};
11use rustc_middle::span_bug;
12use rustc_middle::ty::data_structures::IndexMap;
13use rustc_middle::ty::{ResolverAstLowering, TyCtxt};
14use rustc_span::def_id::{DefId, LocalDefId};
15use rustc_span::edit_distance::find_best_match_for_name;
16use rustc_span::{DUMMY_SP, DesugaringKind, Ident, Span, Symbol, kw, sym};
17use smallvec::SmallVec;
18use thin_vec::ThinVec;
19use tracing::instrument;
20
21use super::diagnostics::{
22 InvalidAbi, InvalidAbiSuggestion, TupleStructWithDefault, UnionWithDefault,
23};
24use super::stability::{enabled_names, gate_unstable_abi};
25use super::{
26 FnDeclKind, GenericArgsMode, ImplTraitContext, ImplTraitPosition, LoweringContext, ParamMode,
27 RelaxedBoundForbiddenReason, RelaxedBoundPolicy,
28};
29use crate::diagnostics::ConstComptimeFn;
30
31pub(super) struct ItemLowerer<'a, 'hir> {
32 pub(super) tcx: TyCtxt<'hir>,
33 pub(super) resolver: &'a ResolverAstLowering<'hir>,
34}
35
36fn add_ty_alias_where_clause(
40 generics: &mut ast::Generics,
41 after_where_clause: &ast::WhereClause,
42 prefer_first: bool,
43) {
44 generics.where_clause.predicates.extend_from_slice(&after_where_clause.predicates);
45
46 let mut before = (generics.where_clause.has_where_token, generics.where_clause.span);
47 let mut after = (after_where_clause.has_where_token, after_where_clause.span);
48 if !prefer_first {
49 (before, after) = (after, before);
50 }
51 (generics.where_clause.has_where_token, generics.where_clause.span) =
52 if before.0 || !after.0 { before } else { after };
53}
54
55impl<'hir> ItemLowerer<'_, 'hir> {
56 fn with_lctx(
57 &mut self,
58 owner: NodeId,
59 f: impl FnOnce(&mut LoweringContext<'_, 'hir>) -> hir::OwnerNode<'hir>,
60 ) -> hir::MaybeOwner<'hir> {
61 let mut lctx = LoweringContext::new(self.tcx, self.resolver, owner);
62
63 let item = f(&mut lctx);
64 if true {
{
match (&lctx.current_hir_id_owner, &item.def_id()) {
(left_val, right_val) => {
if !(*left_val == *right_val) {
let kind = ::core::panicking::AssertKind::Eq;
::core::panicking::assert_failed(kind, &*left_val,
&*right_val, ::core::option::Option::None);
}
}
}
};
};debug_assert_eq!(lctx.current_hir_id_owner, item.def_id());
65
66 let info = lctx.make_owner_info(item);
67
68 hir::MaybeOwner::Owner(lctx.arena.alloc(info))
69 }
70
71 #[allow(clippy :: suspicious_else_formatting)]
{
let __tracing_attr_span;
let __tracing_attr_guard;
if ::tracing::Level::DEBUG <= ::tracing::level_filters::STATIC_MAX_LEVEL
&&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() ||
{ false } {
__tracing_attr_span =
{
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("lower_crate",
"rustc_ast_lowering::item", ::tracing::Level::DEBUG,
::tracing_core::__macro_support::Option::Some("compiler/rustc_ast_lowering/src/item.rs"),
::tracing_core::__macro_support::Option::Some(71u32),
::tracing_core::__macro_support::Option::Some("rustc_ast_lowering::item"),
::tracing_core::field::FieldSet::new(&[],
::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::SPAN)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let mut interest = ::tracing::subscriber::Interest::never();
if ::tracing::Level::DEBUG <=
::tracing::level_filters::STATIC_MAX_LEVEL &&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() &&
{ interest = __CALLSITE.interest(); !interest.is_never() }
&&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest) {
let meta = __CALLSITE.metadata();
::tracing::Span::new(meta,
&{ meta.fields().value_set_all(&[]) })
} else {
let span =
::tracing::__macro_support::__disabled_span(__CALLSITE.metadata());
{};
span
}
};
__tracing_attr_guard = __tracing_attr_span.enter();
}
#[warn(clippy :: suspicious_else_formatting)]
{
#[allow(unknown_lints, unreachable_code, clippy ::
diverging_sub_expression, clippy :: empty_loop, clippy ::
let_unit_value, clippy :: let_with_type_underscore, clippy ::
needless_return, clippy :: unreachable)]
if false {
let __tracing_attr_fake_return: hir::MaybeOwner<'hir> = loop {};
return __tracing_attr_fake_return;
}
{
self.with_lctx(CRATE_NODE_ID,
|lctx|
{
if true {
{
match (&lctx.current_hir_id_owner, &CRATE_OWNER_ID) {
(left_val, right_val) => {
if !(*left_val == *right_val) {
let kind = ::core::panicking::AssertKind::Eq;
::core::panicking::assert_failed(kind, &*left_val,
&*right_val, ::core::option::Option::None);
}
}
}
};
};
let module = lctx.lower_mod(&c.items, &c.spans);
lctx.lower_attrs(hir::CRATE_HIR_ID, &c.attrs,
c.spans.inner_span, Target::Crate);
hir::OwnerNode::Crate(module)
})
}
}
}#[instrument(level = "debug", skip(self, c))]
72 pub(super) fn lower_crate(&mut self, c: &Crate) -> hir::MaybeOwner<'hir> {
73 self.with_lctx(CRATE_NODE_ID, |lctx| {
74 debug_assert_eq!(lctx.current_hir_id_owner, CRATE_OWNER_ID);
75 let module = lctx.lower_mod(&c.items, &c.spans);
76 lctx.lower_attrs(hir::CRATE_HIR_ID, &c.attrs, c.spans.inner_span, Target::Crate);
77 hir::OwnerNode::Crate(module)
78 })
79 }
80
81 #[allow(clippy :: suspicious_else_formatting)]
{
let __tracing_attr_span;
let __tracing_attr_guard;
if ::tracing::Level::DEBUG <= ::tracing::level_filters::STATIC_MAX_LEVEL
&&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() ||
{ false } {
__tracing_attr_span =
{
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("lower_item",
"rustc_ast_lowering::item", ::tracing::Level::DEBUG,
::tracing_core::__macro_support::Option::Some("compiler/rustc_ast_lowering/src/item.rs"),
::tracing_core::__macro_support::Option::Some(81u32),
::tracing_core::__macro_support::Option::Some("rustc_ast_lowering::item"),
::tracing_core::field::FieldSet::new(&[{
const NAME:
::tracing::__macro_support::FieldName<{
::tracing::__macro_support::FieldName::len("item")
}> =
::tracing::__macro_support::FieldName::new("item");
NAME.as_str()
}], ::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::SPAN)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let mut interest = ::tracing::subscriber::Interest::never();
if ::tracing::Level::DEBUG <=
::tracing::level_filters::STATIC_MAX_LEVEL &&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() &&
{ interest = __CALLSITE.interest(); !interest.is_never() }
&&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest) {
let meta = __CALLSITE.metadata();
::tracing::Span::new(meta,
&{
#[allow(unused_imports)]
use ::tracing::field::{debug, display, Value};
meta.fields().value_set_all(&[(::tracing::__macro_support::Option::Some(&::tracing::field::debug(&item)
as &dyn ::tracing::field::Value))])
})
} else {
let span =
::tracing::__macro_support::__disabled_span(__CALLSITE.metadata());
{};
span
}
};
__tracing_attr_guard = __tracing_attr_span.enter();
}
#[warn(clippy :: suspicious_else_formatting)]
{
#[allow(unknown_lints, unreachable_code, clippy ::
diverging_sub_expression, clippy :: empty_loop, clippy ::
let_unit_value, clippy :: let_with_type_underscore, clippy ::
needless_return, clippy :: unreachable)]
if false {
let __tracing_attr_fake_return: hir::MaybeOwner<'hir> = loop {};
return __tracing_attr_fake_return;
}
{
self.with_lctx(item.id,
|lctx| hir::OwnerNode::Item(lctx.lower_item(item)))
}
}
}#[instrument(level = "debug", skip(self))]
82 pub(super) fn lower_item(&mut self, item: &Item) -> hir::MaybeOwner<'hir> {
83 self.with_lctx(item.id, |lctx| hir::OwnerNode::Item(lctx.lower_item(item)))
84 }
85
86 pub(super) fn lower_trait_item(&mut self, item: &AssocItem) -> hir::MaybeOwner<'hir> {
87 self.with_lctx(item.id, |lctx| hir::OwnerNode::TraitItem(lctx.lower_trait_item(item)))
88 }
89
90 pub(super) fn lower_impl_item(&mut self, item: &AssocItem) -> hir::MaybeOwner<'hir> {
91 self.with_lctx(item.id, |lctx| hir::OwnerNode::ImplItem(lctx.lower_impl_item(item)))
92 }
93
94 pub(super) fn lower_foreign_item(&mut self, item: &ForeignItem) -> hir::MaybeOwner<'hir> {
95 self.with_lctx(item.id, |lctx| hir::OwnerNode::ForeignItem(lctx.lower_foreign_item(item)))
96 }
97}
98
99impl<'hir> LoweringContext<'_, 'hir> {
100 pub(super) fn lower_mod(
101 &mut self,
102 items: &[Box<Item>],
103 spans: &ModSpans,
104 ) -> &'hir hir::Mod<'hir> {
105 self.arena.alloc(hir::Mod {
106 spans: hir::ModSpans {
107 inner_span: self.lower_span(spans.inner_span),
108 inject_use_span: self.lower_span(spans.inject_use_span),
109 },
110 item_ids: self.arena.alloc_from_iter(items.iter().map(|x| self.lower_item_ref(x))),
111 })
112 }
113
114 pub(super) fn lower_item_ref(&mut self, i: &Item) -> hir::ItemId {
115 hir::ItemId { owner_id: self.owner_id(i.id) }
116 }
117
118 fn lower_eii_decl(
119 &mut self,
120 id: NodeId,
121 name: Ident,
122 EiiDecl { foreign_item, impl_unsafe }: &EiiDecl,
123 ) -> Option<hir::attrs::EiiDecl> {
124 self.lower_path_simple_eii(id, foreign_item).map(|did| hir::attrs::EiiDecl {
125 foreign_item: did,
126 impl_unsafe: *impl_unsafe,
127 name,
128 })
129 }
130
131 fn lower_eii_impl(
132 &mut self,
133 EiiImpl {
134 node_id,
135 eii_macro_path,
136 impl_safety,
137 span,
138 inner_span,
139 is_default,
140 known_eii_macro_resolution,
141 }: &EiiImpl,
142 ) -> hir::attrs::EiiImpl {
143 let resolution = if let Some(target) = known_eii_macro_resolution
144 && let Some(foreign_item_did) = self.lower_path_simple_eii(*node_id, target)
145 {
146 EiiImplResolution::Known(foreign_item_did)
147 } else if let Some(macro_did) = self.lower_path_simple_eii(*node_id, eii_macro_path) {
148 EiiImplResolution::Macro(macro_did)
149 } else {
150 EiiImplResolution::Error(
151 self.dcx().span_delayed_bug(*span, "eii never resolved without errors given"),
152 )
153 };
154
155 hir::attrs::EiiImpl {
156 span: self.lower_span(*span),
157 inner_span: self.lower_span(*inner_span),
158 impl_marked_unsafe: self.lower_safety(*impl_safety, hir::Safety::Safe).is_unsafe(),
159 is_default: *is_default,
160 resolution,
161 }
162 }
163
164 fn generate_extra_attrs_for_item_kind(
165 &mut self,
166 id: NodeId,
167 i: &ItemKind,
168 ) -> Vec<hir::Attribute> {
169 match i {
170 ItemKind::Fn(Fn { eii_impls, .. }) | ItemKind::Static(StaticItem { eii_impls, .. })
171 if eii_impls.is_empty() =>
172 {
173 Vec::new()
174 }
175 ItemKind::Fn(Fn { eii_impls, .. }) | ItemKind::Static(StaticItem { eii_impls, .. }) => {
176 ::alloc::boxed::box_assume_init_into_vec_unsafe(::alloc::intrinsics::write_box_via_move(::alloc::boxed::Box::new_uninit(),
[hir::Attribute::Parsed(AttributeKind::EiiImpls(eii_impls.iter().map(|i|
self.lower_eii_impl(i)).collect()))]))vec![hir::Attribute::Parsed(AttributeKind::EiiImpls(
177 eii_impls.iter().map(|i| self.lower_eii_impl(i)).collect(),
178 ))]
179 }
180 ItemKind::MacroDef(name, MacroDef { eii_declaration: Some(target), .. }) => self
181 .lower_eii_decl(id, *name, target)
182 .map(|decl| ::alloc::boxed::box_assume_init_into_vec_unsafe(::alloc::intrinsics::write_box_via_move(::alloc::boxed::Box::new_uninit(),
[hir::Attribute::Parsed(AttributeKind::EiiDeclaration(decl))]))vec![hir::Attribute::Parsed(AttributeKind::EiiDeclaration(decl))])
183 .unwrap_or_default(),
184
185 ItemKind::ExternCrate(..)
186 | ItemKind::Use(..)
187 | ItemKind::Const(..)
188 | ItemKind::ConstBlock(..)
189 | ItemKind::Mod(..)
190 | ItemKind::ForeignMod(..)
191 | ItemKind::GlobalAsm(..)
192 | ItemKind::TyAlias(..)
193 | ItemKind::Enum(..)
194 | ItemKind::Struct(..)
195 | ItemKind::Union(..)
196 | ItemKind::Trait(..)
197 | ItemKind::TraitAlias(..)
198 | ItemKind::Impl(..)
199 | ItemKind::MacCall(..)
200 | ItemKind::MacroDef(..)
201 | ItemKind::Delegation(..)
202 | ItemKind::DelegationMac(..) => Vec::new(),
203 }
204 }
205
206 fn lower_item(&mut self, i: &Item) -> &'hir hir::Item<'hir> {
207 let owner_id = self.current_hir_id_owner;
208 let hir_id: HirId = owner_id.into();
209 let vis_span = self.lower_span(i.vis.span);
210
211 let extra_hir_attributes = self.generate_extra_attrs_for_item_kind(i.id, &i.kind);
212 let attrs = self.lower_attrs_with_extra(
213 hir_id,
214 &i.attrs,
215 i.span,
216 Target::from_ast_item(i),
217 &extra_hir_attributes,
218 );
219
220 let kind = self.lower_item_kind(i.span, i.id, hir_id, attrs, vis_span, &i.kind);
221 let item = hir::Item {
222 owner_id,
223 kind,
224 vis_span,
225 span: self.lower_span(i.span),
226 eii: {
{
'done:
{
for i in attrs {
#[allow(unused_imports)]
use rustc_hir::attrs::AttributeKind::*;
let i: &rustc_hir::Attribute = i;
match i {
rustc_hir::Attribute::Parsed(EiiImpls(..) |
EiiDeclaration(..)) => {
break 'done Some(());
}
rustc_hir::Attribute::Unparsed(..) =>
{}
#[deny(unreachable_patterns)]
_ => {}
}
}
None
}
}.is_some()
}find_attr!(attrs, EiiImpls(..) | EiiDeclaration(..)),
227 };
228 self.arena.alloc(item)
229 }
230
231 fn lower_item_kind(
232 &mut self,
233 span: Span,
234 id: NodeId,
235 hir_id: hir::HirId,
236 attrs: &'hir [hir::Attribute],
237 vis_span: Span,
238 i: &ItemKind,
239 ) -> hir::ItemKind<'hir> {
240 match i {
241 ItemKind::ExternCrate(orig_name, ident) => {
242 let ident = self.lower_ident(*ident);
243 hir::ItemKind::ExternCrate(*orig_name, ident)
244 }
245 ItemKind::Use(use_tree) => {
246 let prefix =
248 Path { segments: ThinVec::new(), span: use_tree.prefix.span.shrink_to_lo() };
249
250 self.lower_use_tree(use_tree, &prefix, id, vis_span, attrs)
251 }
252 ItemKind::Static(ast::StaticItem {
253 ident,
254 ty,
255 safety: _,
256 mutability: m,
257 expr: e,
258 define_opaque,
259 eii_impls: _,
260 }) => {
261 let ident = self.lower_ident(*ident);
262 let ty = self
263 .lower_ty_alloc(ty, ImplTraitContext::Disallowed(ImplTraitPosition::StaticTy));
264 let body_id = self.lower_const_body(span, e.as_deref());
265 self.lower_define_opaque(hir_id, define_opaque);
266 hir::ItemKind::Static(*m, ident, ty, body_id)
267 }
268 ItemKind::Const(ConstItem {
269 defaultness: _,
270 ident,
271 generics,
272 ty,
273 rhs_kind,
274 define_opaque,
275 }) => {
276 let ident = self.lower_ident(*ident);
277 let (generics, (ty, rhs)) = self.lower_generics(
278 generics,
279 ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
280 |this| {
281 let ty = this.lower_ty_alloc(
282 ty,
283 ImplTraitContext::Disallowed(ImplTraitPosition::ConstTy),
284 );
285 let rhs = this.lower_const_item_rhs(rhs_kind, span);
286 (ty, rhs)
287 },
288 );
289 self.lower_define_opaque(hir_id, &define_opaque);
290 hir::ItemKind::Const(ident, generics, ty, rhs)
291 }
292 ItemKind::ConstBlock(ConstBlockItem { span, id, block }) => hir::ItemKind::Const(
293 self.lower_ident(ConstBlockItem::IDENT),
294 hir::Generics::empty(),
295 self.arena.alloc(self.ty_tup(DUMMY_SP, &[])),
296 hir::ConstItemRhs::Body({
297 let body = hir::Expr {
298 hir_id: self.lower_node_id(*id),
299 kind: hir::ExprKind::Block(self.lower_block(block, false), None),
300 span: self.lower_span(*span),
301 };
302 self.record_body(&[], body)
303 }),
304 ),
305 ItemKind::Fn(Fn {
306 sig: FnSig { decl, header, span: fn_sig_span },
307 ident,
308 generics,
309 body,
310 contract,
311 define_opaque,
312 ..
313 }) => {
314 self.with_new_scopes(*fn_sig_span, |this| {
315 let coroutine_kind = header.coroutine_kind;
320 let body_id = this.lower_maybe_coroutine_body(
321 *fn_sig_span,
322 span,
323 hir_id,
324 decl,
325 coroutine_kind,
326 body.as_deref(),
327 attrs,
328 contract.as_deref(),
329 );
330
331 let itctx = ImplTraitContext::Universal;
332 let (generics, decl) = this.lower_generics(generics, itctx, |this| {
333 this.lower_fn_decl(decl, id, *fn_sig_span, FnDeclKind::Fn, coroutine_kind)
334 });
335 let sig = hir::FnSig {
336 decl,
337 header: this.lower_fn_header(*header, hir::Safety::Safe, attrs),
338 span: this.lower_span(*fn_sig_span),
339 };
340 this.lower_define_opaque(hir_id, define_opaque);
341 let ident = this.lower_ident(*ident);
342 hir::ItemKind::Fn {
343 ident,
344 sig,
345 generics,
346 body: body_id,
347 has_body: body.is_some(),
348 }
349 })
350 }
351 ItemKind::Mod(_, ident, mod_kind) => {
352 let ident = self.lower_ident(*ident);
353 match mod_kind {
354 ModKind::Loaded(items, _, spans) => {
355 hir::ItemKind::Mod(ident, self.lower_mod(items, spans))
356 }
357 ModKind::Unloaded => {
::core::panicking::panic_fmt(format_args!("`mod` items should have been loaded by now"));
}panic!("`mod` items should have been loaded by now"),
358 }
359 }
360 ItemKind::ForeignMod(fm) => hir::ItemKind::ForeignMod {
361 abi: fm.abi.map_or(ExternAbi::FALLBACK, |abi| self.lower_abi(abi)),
362 items: self
363 .arena
364 .alloc_from_iter(fm.items.iter().map(|x| self.lower_foreign_item_ref(x))),
365 },
366 ItemKind::GlobalAsm(asm) => {
367 let asm = self.lower_inline_asm(span, asm);
368 let fake_body =
369 self.lower_body(|this| (&[], this.expr(span, hir::ExprKind::InlineAsm(asm))));
370 hir::ItemKind::GlobalAsm { asm, fake_body }
371 }
372 ItemKind::TyAlias(TyAlias { ident, generics, after_where_clause, ty, .. }) => {
373 let ident = self.lower_ident(*ident);
382 let mut generics = generics.clone();
383 add_ty_alias_where_clause(&mut generics, after_where_clause, true);
384 let (generics, ty) = self.lower_generics(
385 &generics,
386 ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
387 |this| match ty {
388 None => {
389 let guar = this.dcx().span_delayed_bug(
390 span,
391 "expected to lower type alias type, but it was missing",
392 );
393 this.arena.alloc(this.ty(span, hir::TyKind::Err(guar)))
394 }
395 Some(ty) => this.lower_ty_alloc(
396 ty,
397 ImplTraitContext::OpaqueTy {
398 origin: hir::OpaqueTyOrigin::TyAlias {
399 parent: this.owner.def_id,
400 in_assoc_ty: false,
401 },
402 },
403 ),
404 },
405 );
406 hir::ItemKind::TyAlias(ident, generics, ty)
407 }
408 ItemKind::Enum(ident, generics, enum_definition) => {
409 let ident = self.lower_ident(*ident);
410 let (generics, variants) = self.lower_generics(
411 generics,
412 ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
413 |this| {
414 this.arena.alloc_from_iter(
415 enum_definition.variants.iter().map(|x| this.lower_variant(i, x)),
416 )
417 },
418 );
419 hir::ItemKind::Enum(ident, generics, hir::EnumDef { variants })
420 }
421 ItemKind::Struct(ident, generics, struct_def) => {
422 let ident = self.lower_ident(*ident);
423 let (generics, struct_def) = self.lower_generics(
424 generics,
425 ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
426 |this| this.lower_variant_data(hir_id, i, struct_def),
427 );
428 hir::ItemKind::Struct(ident, generics, struct_def)
429 }
430 ItemKind::Union(ident, generics, vdata) => {
431 let ident = self.lower_ident(*ident);
432 let (generics, vdata) = self.lower_generics(
433 generics,
434 ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
435 |this| this.lower_variant_data(hir_id, i, vdata),
436 );
437 hir::ItemKind::Union(ident, generics, vdata)
438 }
439 ItemKind::Impl(Impl {
440 generics: ast_generics,
441 of_trait,
442 self_ty: ty,
443 items: impl_items,
444 constness,
445 }) => {
446 let itctx = ImplTraitContext::Universal;
460 let (generics, (of_trait, lowered_ty)) =
461 self.lower_generics(ast_generics, itctx, |this| {
462 let of_trait = of_trait
463 .as_deref()
464 .map(|of_trait| this.lower_trait_impl_header(of_trait));
465
466 let lowered_ty = this.lower_ty_alloc(
467 ty,
468 ImplTraitContext::Disallowed(ImplTraitPosition::ImplSelf),
469 );
470
471 (of_trait, lowered_ty)
472 });
473
474 let new_impl_items = self
475 .arena
476 .alloc_from_iter(impl_items.iter().map(|item| self.lower_impl_item_ref(item)));
477
478 let constness = self.lower_constness(attrs, *constness);
479
480 hir::ItemKind::Impl(hir::Impl {
481 generics,
482 of_trait,
483 self_ty: lowered_ty,
484 items: new_impl_items,
485 constness,
486 })
487 }
488 ItemKind::Trait(Trait {
489 impl_restriction,
490 constness,
491 is_auto,
492 safety,
493 ident,
494 generics,
495 bounds,
496 items,
497 }) => {
498 let constness = self.lower_constness(attrs, *constness);
499 let impl_restriction = self.lower_impl_restriction(impl_restriction);
500 let ident = self.lower_ident(*ident);
501 let (generics, (safety, items, bounds)) = self.lower_generics(
502 generics,
503 ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
504 |this| {
505 let bounds = this.lower_param_bounds(
506 bounds,
507 RelaxedBoundPolicy::Forbidden(RelaxedBoundForbiddenReason::SuperTrait),
508 ImplTraitContext::Disallowed(ImplTraitPosition::Bound),
509 );
510 let items = this.arena.alloc_from_iter(
511 items.iter().map(|item| this.lower_trait_item_ref(item)),
512 );
513 let safety = this.lower_safety(*safety, hir::Safety::Safe);
514 (safety, items, bounds)
515 },
516 );
517 hir::ItemKind::Trait {
518 impl_restriction,
519 constness,
520 is_auto: *is_auto,
521 safety,
522 ident,
523 generics,
524 bounds,
525 items,
526 }
527 }
528 ItemKind::TraitAlias(TraitAlias { constness, ident, generics, bounds }) => {
529 let constness = self.lower_constness(attrs, *constness);
530 let ident = self.lower_ident(*ident);
531 let (generics, bounds) = self.lower_generics(
532 generics,
533 ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
534 |this| {
535 this.lower_param_bounds(
536 bounds,
537 RelaxedBoundPolicy::Forbidden(RelaxedBoundForbiddenReason::TraitAlias),
538 ImplTraitContext::Disallowed(ImplTraitPosition::Bound),
539 )
540 },
541 );
542 hir::ItemKind::TraitAlias(constness, ident, generics, bounds)
543 }
544 ItemKind::MacroDef(ident, MacroDef { body, macro_rules, eii_declaration: _ }) => {
545 let ident = self.lower_ident(*ident);
546 let body = Box::new(self.lower_delim_args(body));
547 let def_id = self.owner.def_id;
548 let def_kind = self.tcx.def_kind(def_id);
549 let DefKind::Macro(macro_kinds) = def_kind else {
550 {
::core::panicking::panic_fmt(format_args!("internal error: entered unreachable code: {0}",
format_args!("expected DefKind::Macro for macro item, found {0}",
def_kind.descr(def_id.to_def_id()))));
};unreachable!(
551 "expected DefKind::Macro for macro item, found {}",
552 def_kind.descr(def_id.to_def_id())
553 );
554 };
555 let macro_def = self.arena.alloc(ast::MacroDef {
556 body,
557 macro_rules: *macro_rules,
558 eii_declaration: None,
559 });
560 hir::ItemKind::Macro(ident, macro_def, macro_kinds)
561 }
562 ItemKind::Delegation(delegation) => {
563 let delegation_results = self.lower_delegation(delegation);
564 hir::ItemKind::Fn {
565 sig: delegation_results.sig,
566 ident: delegation_results.ident,
567 generics: delegation_results.generics,
568 body: delegation_results.body_id,
569 has_body: true,
570 }
571 }
572 ItemKind::MacCall(..) | ItemKind::DelegationMac(..) => {
573 {
::core::panicking::panic_fmt(format_args!("macros should have been expanded by now"));
}panic!("macros should have been expanded by now")
574 }
575 }
576 }
577
578 fn lower_path_simple_eii(&mut self, id: NodeId, path: &Path) -> Option<DefId> {
579 let res = self.get_partial_res(id)?;
580 let Some(did) = res.expect_full_res().opt_def_id() else {
581 self.dcx().span_delayed_bug(path.span, "should have errored in resolve");
582 return None;
583 };
584
585 Some(did)
586 }
587
588 #[allow(clippy :: suspicious_else_formatting)]
{
let __tracing_attr_span;
let __tracing_attr_guard;
if ::tracing::Level::DEBUG <= ::tracing::level_filters::STATIC_MAX_LEVEL
&&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() ||
{ false } {
__tracing_attr_span =
{
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("lower_use_tree",
"rustc_ast_lowering::item", ::tracing::Level::DEBUG,
::tracing_core::__macro_support::Option::Some("compiler/rustc_ast_lowering/src/item.rs"),
::tracing_core::__macro_support::Option::Some(588u32),
::tracing_core::__macro_support::Option::Some("rustc_ast_lowering::item"),
::tracing_core::field::FieldSet::new(&[{
const NAME:
::tracing::__macro_support::FieldName<{
::tracing::__macro_support::FieldName::len("tree")
}> =
::tracing::__macro_support::FieldName::new("tree");
NAME.as_str()
},
{
const NAME:
::tracing::__macro_support::FieldName<{
::tracing::__macro_support::FieldName::len("prefix")
}> =
::tracing::__macro_support::FieldName::new("prefix");
NAME.as_str()
},
{
const NAME:
::tracing::__macro_support::FieldName<{
::tracing::__macro_support::FieldName::len("id")
}> =
::tracing::__macro_support::FieldName::new("id");
NAME.as_str()
},
{
const NAME:
::tracing::__macro_support::FieldName<{
::tracing::__macro_support::FieldName::len("vis_span")
}> =
::tracing::__macro_support::FieldName::new("vis_span");
NAME.as_str()
},
{
const NAME:
::tracing::__macro_support::FieldName<{
::tracing::__macro_support::FieldName::len("attrs")
}> =
::tracing::__macro_support::FieldName::new("attrs");
NAME.as_str()
}], ::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::SPAN)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let mut interest = ::tracing::subscriber::Interest::never();
if ::tracing::Level::DEBUG <=
::tracing::level_filters::STATIC_MAX_LEVEL &&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() &&
{ interest = __CALLSITE.interest(); !interest.is_never() }
&&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest) {
let meta = __CALLSITE.metadata();
::tracing::Span::new(meta,
&{
#[allow(unused_imports)]
use ::tracing::field::{debug, display, Value};
meta.fields().value_set_all(&[(::tracing::__macro_support::Option::Some(&::tracing::field::debug(&tree)
as &dyn ::tracing::field::Value)),
(::tracing::__macro_support::Option::Some(&::tracing::field::debug(&prefix)
as &dyn ::tracing::field::Value)),
(::tracing::__macro_support::Option::Some(&::tracing::field::debug(&id)
as &dyn ::tracing::field::Value)),
(::tracing::__macro_support::Option::Some(&::tracing::field::debug(&vis_span)
as &dyn ::tracing::field::Value)),
(::tracing::__macro_support::Option::Some(&::tracing::field::debug(&attrs)
as &dyn ::tracing::field::Value))])
})
} else {
let span =
::tracing::__macro_support::__disabled_span(__CALLSITE.metadata());
{};
span
}
};
__tracing_attr_guard = __tracing_attr_span.enter();
}
#[warn(clippy :: suspicious_else_formatting)]
{
#[allow(unknown_lints, unreachable_code, clippy ::
diverging_sub_expression, clippy :: empty_loop, clippy ::
let_unit_value, clippy :: let_with_type_underscore, clippy ::
needless_return, clippy :: unreachable)]
if false {
let __tracing_attr_fake_return: hir::ItemKind<'hir> = loop {};
return __tracing_attr_fake_return;
}
{
let path = &tree.prefix;
let segments =
prefix.segments.iter().chain(path.segments.iter()).cloned().collect();
match tree.kind {
UseTreeKind::Simple(rename) => {
let mut ident = tree.ident();
let mut path = Path { segments, span: path.span };
if path.segments.len() > 1 &&
path.segments.last().unwrap().ident.name == kw::SelfLower {
let _ = path.segments.pop();
if rename.is_none() {
ident = path.segments.last().unwrap().ident;
}
}
let res = self.lower_import_res(id, path.span);
let path =
self.lower_use_path(res, &path, ParamMode::Explicit);
let ident = self.lower_ident(ident);
hir::ItemKind::Use(path, hir::UseKind::Single(ident))
}
UseTreeKind::Glob(_) => {
let res = self.expect_full_res(id);
let res = self.lower_res(res);
let res =
match res {
Res::Def(DefKind::Mod | DefKind::Trait, _) => {
PerNS { type_ns: Some(res), value_ns: None, macro_ns: None }
}
Res::Def(DefKind::Enum, _) => {
PerNS { type_ns: None, value_ns: Some(res), macro_ns: None }
}
Res::Err => {
let err = Some(Res::Err);
PerNS { type_ns: err, value_ns: err, macro_ns: err }
}
_ =>
::rustc_middle::util::bug::span_bug_fmt(path.span,
format_args!("bad glob res {0:?}", res)),
};
let path = Path { segments, span: path.span };
let path =
self.lower_use_path(res, &path, ParamMode::Explicit);
hir::ItemKind::Use(path, hir::UseKind::Glob)
}
UseTreeKind::Nested { items: ref trees, .. } => {
let span = prefix.span.to(path.span);
let prefix = Path { segments, span };
for &(ref use_tree, id) in trees {
let owner_id = self.owner_id(id);
self.with_hir_id_owner(id,
|this|
{
let kind =
this.lower_use_tree(use_tree, &prefix, id, vis_span, attrs);
if !attrs.is_empty() {
this.attrs.insert(hir::ItemLocalId::ZERO, attrs);
}
let item =
hir::Item {
owner_id,
kind,
vis_span,
span: this.lower_span(use_tree.span()),
eii: {
{
'done:
{
for i in attrs {
#[allow(unused_imports)]
use rustc_hir::attrs::AttributeKind::*;
let i: &rustc_hir::Attribute = i;
match i {
rustc_hir::Attribute::Parsed(EiiImpls(..) |
EiiDeclaration(..)) => {
break 'done Some(());
}
rustc_hir::Attribute::Unparsed(..) =>
{}
#[deny(unreachable_patterns)]
_ => {}
}
}
None
}
}.is_some()
},
};
hir::OwnerNode::Item(this.arena.alloc(item))
});
}
let path =
if trees.is_empty() &&
!(prefix.segments.is_empty() ||
prefix.segments.len() == 1 &&
prefix.segments[0].ident.name == kw::PathRoot) {
let res = self.lower_import_res(id, span);
self.lower_use_path(res, &prefix, ParamMode::Explicit)
} else {
let span = self.lower_span(span);
self.arena.alloc(hir::UsePath {
res: PerNS::default(),
segments: &[],
span,
})
};
hir::ItemKind::Use(path, hir::UseKind::ListStem)
}
}
}
}
}#[instrument(level = "debug", skip(self))]
589 fn lower_use_tree(
590 &mut self,
591 tree: &UseTree,
592 prefix: &Path,
593 id: NodeId,
594 vis_span: Span,
595 attrs: &'hir [hir::Attribute],
596 ) -> hir::ItemKind<'hir> {
597 let path = &tree.prefix;
598 let segments = prefix.segments.iter().chain(path.segments.iter()).cloned().collect();
599
600 match tree.kind {
601 UseTreeKind::Simple(rename) => {
602 let mut ident = tree.ident();
603
604 let mut path = Path { segments, span: path.span };
606
607 if path.segments.len() > 1
609 && path.segments.last().unwrap().ident.name == kw::SelfLower
610 {
611 let _ = path.segments.pop();
612 if rename.is_none() {
613 ident = path.segments.last().unwrap().ident;
614 }
615 }
616
617 let res = self.lower_import_res(id, path.span);
618 let path = self.lower_use_path(res, &path, ParamMode::Explicit);
619 let ident = self.lower_ident(ident);
620 hir::ItemKind::Use(path, hir::UseKind::Single(ident))
621 }
622 UseTreeKind::Glob(_) => {
623 let res = self.expect_full_res(id);
624 let res = self.lower_res(res);
625 let res = match res {
627 Res::Def(DefKind::Mod | DefKind::Trait, _) => {
628 PerNS { type_ns: Some(res), value_ns: None, macro_ns: None }
629 }
630 Res::Def(DefKind::Enum, _) => {
631 PerNS { type_ns: None, value_ns: Some(res), macro_ns: None }
632 }
633 Res::Err => {
634 let err = Some(Res::Err);
636 PerNS { type_ns: err, value_ns: err, macro_ns: err }
637 }
638 _ => span_bug!(path.span, "bad glob res {:?}", res),
639 };
640 let path = Path { segments, span: path.span };
641 let path = self.lower_use_path(res, &path, ParamMode::Explicit);
642 hir::ItemKind::Use(path, hir::UseKind::Glob)
643 }
644 UseTreeKind::Nested { items: ref trees, .. } => {
645 let span = prefix.span.to(path.span);
670 let prefix = Path { segments, span };
671
672 for &(ref use_tree, id) in trees {
674 let owner_id = self.owner_id(id);
675
676 self.with_hir_id_owner(id, |this| {
682 let kind = this.lower_use_tree(use_tree, &prefix, id, vis_span, attrs);
686 if !attrs.is_empty() {
687 this.attrs.insert(hir::ItemLocalId::ZERO, attrs);
688 }
689
690 let item = hir::Item {
691 owner_id,
692 kind,
693 vis_span,
694 span: this.lower_span(use_tree.span()),
695 eii: find_attr!(attrs, EiiImpls(..) | EiiDeclaration(..)),
696 };
697 hir::OwnerNode::Item(this.arena.alloc(item))
698 });
699 }
700
701 let path = if trees.is_empty()
703 && !(prefix.segments.is_empty()
704 || prefix.segments.len() == 1
705 && prefix.segments[0].ident.name == kw::PathRoot)
706 {
707 let res = self.lower_import_res(id, span);
710 self.lower_use_path(res, &prefix, ParamMode::Explicit)
711 } else {
712 let span = self.lower_span(span);
715 self.arena.alloc(hir::UsePath { res: PerNS::default(), segments: &[], span })
716 };
717 hir::ItemKind::Use(path, hir::UseKind::ListStem)
718 }
719 }
720 }
721
722 fn lower_foreign_item(&mut self, i: &ForeignItem) -> &'hir hir::ForeignItem<'hir> {
723 let owner_id = self.current_hir_id_owner;
724 let hir_id: HirId = owner_id.into();
725 let attrs =
726 self.lower_attrs(hir_id, &i.attrs, i.span, Target::from_foreign_item_kind(&i.kind));
727 let (ident, kind) = match &i.kind {
728 ForeignItemKind::Fn(Fn { sig, ident, generics, define_opaque, .. }) => {
729 let fdec = &sig.decl;
730 let itctx = ImplTraitContext::Universal;
731 let (generics, (decl, fn_args)) = self.lower_generics(generics, itctx, |this| {
732 (
733 this.lower_fn_decl(fdec, i.id, sig.span, FnDeclKind::ExternFn, None),
735 this.lower_fn_params_to_idents(fdec),
736 )
737 });
738
739 let header = self.lower_fn_header(sig.header, hir::Safety::Unsafe, attrs);
741
742 if define_opaque.is_some() {
743 self.dcx().span_err(i.span, "foreign functions cannot define opaque types");
744 }
745
746 (
747 ident,
748 hir::ForeignItemKind::Fn(
749 hir::FnSig { header, decl, span: self.lower_span(sig.span) },
750 fn_args,
751 generics,
752 ),
753 )
754 }
755 ForeignItemKind::Static(StaticItem {
756 ident,
757 ty,
758 mutability,
759 expr: _,
760 safety,
761 define_opaque,
762 eii_impls: _,
763 }) => {
764 let ty = self
765 .lower_ty_alloc(ty, ImplTraitContext::Disallowed(ImplTraitPosition::StaticTy));
766 let safety = self.lower_safety(*safety, hir::Safety::Unsafe);
767 if define_opaque.is_some() {
768 self.dcx().span_err(i.span, "foreign statics cannot define opaque types");
769 }
770 (ident, hir::ForeignItemKind::Static(ty, *mutability, safety))
771 }
772 ForeignItemKind::TyAlias(TyAlias { ident, .. }) => (ident, hir::ForeignItemKind::Type),
773 ForeignItemKind::MacCall(_) => { ::core::panicking::panic_fmt(format_args!("macro shouldn\'t exist here")); }panic!("macro shouldn't exist here"),
774 };
775
776 let item = hir::ForeignItem {
777 owner_id,
778 ident: self.lower_ident(*ident),
779 kind,
780 vis_span: self.lower_span(i.vis.span),
781 span: self.lower_span(i.span),
782 };
783 self.arena.alloc(item)
784 }
785
786 fn lower_foreign_item_ref(&mut self, i: &ForeignItem) -> hir::ForeignItemId {
787 hir::ForeignItemId { owner_id: self.owner_id(i.id) }
788 }
789
790 fn lower_variant(&mut self, item_kind: &ItemKind, v: &Variant) -> hir::Variant<'hir> {
791 if v.ident.name == kw::Underscore && self.tcx.features().unnamed_enum_variants() {
792 self.dcx()
794 .struct_span_fatal(v.span, "unnamed enum variants are not yet implemented")
795 .emit()
796 }
797 let hir_id = self.lower_node_id(v.id);
798 self.lower_attrs(hir_id, &v.attrs, v.span, Target::Variant);
799 hir::Variant {
800 hir_id,
801 def_id: self.local_def_id(v.id),
802 data: self.lower_variant_data(hir_id, item_kind, &v.data),
803 disr_expr: v
804 .disr_expr
805 .as_ref()
806 .map(|e| self.lower_anon_const_to_anon_const(e, e.value.span)),
807 ident: self.lower_ident(v.ident),
808 span: self.lower_span(v.span),
809 }
810 }
811
812 fn lower_variant_data(
813 &mut self,
814 parent_id: hir::HirId,
815 item_kind: &ItemKind,
816 vdata: &VariantData,
817 ) -> hir::VariantData<'hir> {
818 match vdata {
819 VariantData::Struct { fields, recovered } => {
820 let fields = self
821 .arena
822 .alloc_from_iter(fields.iter().enumerate().map(|f| self.lower_field_def(f)));
823
824 if let ItemKind::Union(..) = item_kind {
825 for field in &fields[..] {
826 if let Some(default) = field.default {
827 if self.tcx.features().default_field_values() {
831 self.dcx().emit_err(UnionWithDefault { span: default.span });
832 } else {
833 let _ = self.dcx().span_delayed_bug(
834 default.span,
835 "expected union default field values feature gate error but none \
836 was produced",
837 );
838 }
839 }
840 }
841 }
842
843 hir::VariantData::Struct { fields, recovered: *recovered }
844 }
845 VariantData::Tuple(fields, id) => {
846 let ctor_id = self.lower_node_id(*id);
847 self.alias_attrs(ctor_id, parent_id);
848 let fields = self
849 .arena
850 .alloc_from_iter(fields.iter().enumerate().map(|f| self.lower_field_def(f)));
851 for field in &fields[..] {
852 if let Some(default) = field.default {
853 if self.tcx.features().default_field_values() {
858 self.dcx().emit_err(TupleStructWithDefault { span: default.span });
859 } else {
860 let _ = self.dcx().span_delayed_bug(
861 default.span,
862 "expected `default values on `struct` fields aren't supported` \
863 feature-gate error but none was produced",
864 );
865 }
866 }
867 }
868 hir::VariantData::Tuple(fields, ctor_id, self.local_def_id(*id))
869 }
870 VariantData::Unit(id) => {
871 let ctor_id = self.lower_node_id(*id);
872 self.alias_attrs(ctor_id, parent_id);
873 hir::VariantData::Unit(ctor_id, self.local_def_id(*id))
874 }
875 }
876 }
877
878 pub(super) fn lower_field_def(
879 &mut self,
880 (index, f): (usize, &FieldDef),
881 ) -> hir::FieldDef<'hir> {
882 let ty =
883 self.lower_ty_alloc(&f.ty, ImplTraitContext::Disallowed(ImplTraitPosition::FieldTy));
884 let hir_id = self.lower_node_id(f.id);
885 self.lower_attrs(hir_id, &f.attrs, f.span, Target::Field);
886 hir::FieldDef {
887 span: self.lower_span(f.span),
888 hir_id,
889 def_id: self.local_def_id(f.id),
890 ident: match f.ident {
891 Some(ident) => self.lower_ident(ident),
892 None => Ident::new(sym::integer(index), self.lower_span(f.span)),
894 },
895 vis_span: self.lower_span(f.vis.span),
896 mut_restriction: self.lower_mut_restriction(&f.mut_restriction),
897 default: f
898 .default
899 .as_ref()
900 .map(|v| self.lower_anon_const_to_anon_const(v, v.value.span)),
901 ty,
902 safety: self.lower_safety(f.safety, hir::Safety::Safe),
903 }
904 }
905
906 fn lower_trait_item(&mut self, i: &AssocItem) -> &'hir hir::TraitItem<'hir> {
907 let trait_item_def_id = self.current_hir_id_owner;
908 let hir_id: HirId = trait_item_def_id.into();
909 let attrs = self.lower_attrs(
910 hir_id,
911 &i.attrs,
912 i.span,
913 Target::from_assoc_item_kind(&i.kind, AssocCtxt::Trait),
914 );
915
916 let (ident, generics, kind, has_value) = match &i.kind {
917 AssocItemKind::Const(ConstItem {
918 ident,
919 generics,
920 ty,
921 rhs_kind,
922 define_opaque,
923 ..
924 }) => {
925 let (generics, kind) = self.lower_generics(
926 generics,
927 ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
928 |this| {
929 let ty = this.lower_ty_alloc(
930 ty,
931 ImplTraitContext::Disallowed(ImplTraitPosition::ConstTy),
932 );
933 let rhs = if rhs_kind.has_expr() {
935 Some(this.lower_const_item_rhs(rhs_kind, i.span))
936 } else {
937 None
938 };
939 hir::TraitItemKind::Const(ty, rhs)
940 },
941 );
942
943 if define_opaque.is_some() {
944 if rhs_kind.has_expr() {
945 self.lower_define_opaque(hir_id, &define_opaque);
946 } else {
947 self.dcx().span_err(
948 i.span,
949 "only trait consts with default bodies can define opaque types",
950 );
951 }
952 }
953
954 (*ident, generics, kind, rhs_kind.has_expr())
955 }
956 AssocItemKind::Fn(Fn { sig, ident, generics, body: None, define_opaque, .. }) => {
957 let idents = self.lower_fn_params_to_idents(&sig.decl);
960 let (generics, sig) = self.lower_method_sig(
961 generics,
962 sig,
963 i.id,
964 FnDeclKind::Trait,
965 sig.header.coroutine_kind,
966 attrs,
967 );
968 if define_opaque.is_some() {
969 self.dcx().span_err(
970 i.span,
971 "only trait methods with default bodies can define opaque types",
972 );
973 }
974 (
975 *ident,
976 generics,
977 hir::TraitItemKind::Fn(sig, hir::TraitFn::Required(idents)),
978 false,
979 )
980 }
981 AssocItemKind::Fn(Fn {
982 sig,
983 ident,
984 generics,
985 body: Some(body),
986 contract,
987 define_opaque,
988 ..
989 }) => {
990 let body_id = self.lower_maybe_coroutine_body(
991 sig.span,
992 i.span,
993 hir_id,
994 &sig.decl,
995 sig.header.coroutine_kind,
996 Some(body),
997 attrs,
998 contract.as_deref(),
999 );
1000 let (generics, sig) = self.lower_method_sig(
1001 generics,
1002 sig,
1003 i.id,
1004 FnDeclKind::Trait,
1005 sig.header.coroutine_kind,
1006 attrs,
1007 );
1008 self.lower_define_opaque(hir_id, &define_opaque);
1009 (
1010 *ident,
1011 generics,
1012 hir::TraitItemKind::Fn(sig, hir::TraitFn::Provided(body_id)),
1013 true,
1014 )
1015 }
1016 AssocItemKind::Type(TyAlias {
1017 ident,
1018 generics,
1019 after_where_clause,
1020 bounds,
1021 ty,
1022 ..
1023 }) => {
1024 let mut generics = generics.clone();
1025 add_ty_alias_where_clause(&mut generics, after_where_clause, false);
1026 let (generics, kind) = self.lower_generics(
1027 &generics,
1028 ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
1029 |this| {
1030 let ty = ty.as_ref().map(|x| {
1031 this.lower_ty_alloc(
1032 x,
1033 ImplTraitContext::Disallowed(ImplTraitPosition::AssocTy),
1034 )
1035 });
1036 hir::TraitItemKind::Type(
1037 this.lower_param_bounds(
1038 bounds,
1039 RelaxedBoundPolicy::Allowed(&mut Default::default()),
1040 ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
1041 ),
1042 ty,
1043 )
1044 },
1045 );
1046 (*ident, generics, kind, ty.is_some())
1047 }
1048 AssocItemKind::Delegation(delegation) => {
1049 let delegation_results = self.lower_delegation(delegation);
1050 let item_kind = hir::TraitItemKind::Fn(
1051 delegation_results.sig,
1052 hir::TraitFn::Provided(delegation_results.body_id),
1053 );
1054 (delegation.ident, delegation_results.generics, item_kind, true)
1055 }
1056 AssocItemKind::MacCall(..) | AssocItemKind::DelegationMac(..) => {
1057 {
::core::panicking::panic_fmt(format_args!("macros should have been expanded by now"));
}panic!("macros should have been expanded by now")
1058 }
1059 };
1060
1061 let defaultness = match i.kind.defaultness() {
1062 Defaultness::Final(..) if !#[allow(non_exhaustive_omitted_patterns)] match i.kind {
AssocItemKind::Fn(..) => true,
_ => false,
}matches!(i.kind, AssocItemKind::Fn(..)) => {
1067 Defaultness::Implicit
1068 }
1069 defaultness => defaultness,
1070 };
1071 let (defaultness, _) = self
1072 .lower_defaultness(defaultness, has_value, || hir::Defaultness::Default { has_value });
1073
1074 let item = hir::TraitItem {
1075 owner_id: trait_item_def_id,
1076 ident: self.lower_ident(ident),
1077 generics,
1078 kind,
1079 span: self.lower_span(i.span),
1080 defaultness,
1081 };
1082 self.arena.alloc(item)
1083 }
1084
1085 fn lower_trait_item_ref(&mut self, i: &AssocItem) -> hir::TraitItemId {
1086 hir::TraitItemId { owner_id: self.owner_id(i.id) }
1087 }
1088
1089 pub(crate) fn expr_err(&mut self, span: Span, guar: ErrorGuaranteed) -> hir::Expr<'hir> {
1091 self.expr(span, hir::ExprKind::Err(guar))
1092 }
1093
1094 fn lower_trait_impl_header(
1095 &mut self,
1096 trait_impl_header: &TraitImplHeader,
1097 ) -> &'hir hir::TraitImplHeader<'hir> {
1098 let TraitImplHeader { safety, polarity, defaultness, ref trait_ref } = *trait_impl_header;
1099 let safety = self.lower_safety(safety, hir::Safety::Safe);
1100 let polarity = match polarity {
1101 ImplPolarity::Positive => ImplPolarity::Positive,
1102 ImplPolarity::Negative(s) => ImplPolarity::Negative(self.lower_span(s)),
1103 };
1104 let has_val = true;
1107 let (defaultness, defaultness_span) =
1108 self.lower_defaultness(defaultness, has_val, || hir::Defaultness::Final);
1109 let modifiers = TraitBoundModifiers {
1110 constness: BoundConstness::Never,
1111 asyncness: BoundAsyncness::Normal,
1112 polarity: BoundPolarity::Positive,
1114 };
1115 let trait_ref = self.lower_trait_ref(
1116 modifiers,
1117 trait_ref,
1118 ImplTraitContext::Disallowed(ImplTraitPosition::Trait),
1119 );
1120
1121 self.arena.alloc(hir::TraitImplHeader {
1122 safety,
1123 polarity,
1124 defaultness,
1125 defaultness_span,
1126 trait_ref,
1127 })
1128 }
1129
1130 fn check_pin_drop_sugar_impl_item(
1131 &self,
1132 i: &AssocItem,
1133 ident: Ident,
1134 trait_item: Result<DefId, ErrorGuaranteed>,
1135 ) -> Ident {
1136 if let AssocItemKind::Fn(fn_kind) = &i.kind
1137 && fn_kind.is_pin_drop_sugar()
1138 {
1139 if let Ok(trait_item) = trait_item
1140 && self
1141 .tcx
1142 .lang_items()
1143 .drop_trait()
1144 .is_none_or(|drop_trait| self.tcx.parent(trait_item) != drop_trait)
1145 {
1146 self.dcx()
1147 .struct_span_err(
1148 i.span,
1149 "method `drop` with `&pin mut self` is only supported for the `Drop` trait",
1150 )
1151 .with_span_label(i.span, "not a `Drop::pin_drop` implementation")
1152 .emit();
1153 }
1154 return Ident::new(sym::pin_drop, ident.span);
1155 }
1156
1157 ident
1158 }
1159
1160 fn lower_impl_item(&mut self, i: &AssocItem) -> &'hir hir::ImplItem<'hir> {
1161 let owner_id = self.current_hir_id_owner;
1162 let hir_id: HirId = owner_id.into();
1163 let parent_id = self.tcx.local_parent(owner_id.def_id);
1164 let is_in_trait_impl =
1165 #[allow(non_exhaustive_omitted_patterns)] match self.tcx.def_kind(parent_id) {
DefKind::Impl { of_trait: true } => true,
_ => false,
}matches!(self.tcx.def_kind(parent_id), DefKind::Impl { of_trait: true });
1166
1167 let has_value = true;
1169 let (defaultness, _) =
1170 self.lower_defaultness(i.kind.defaultness(), has_value, || hir::Defaultness::Final);
1171 let attrs = self.lower_attrs(
1172 hir_id,
1173 &i.attrs,
1174 i.span,
1175 Target::from_assoc_item_kind(&i.kind, AssocCtxt::Impl { of_trait: is_in_trait_impl }),
1176 );
1177
1178 let (ident, (generics, kind)) = match &i.kind {
1179 AssocItemKind::Const(ConstItem {
1180 ident,
1181 generics,
1182 ty,
1183 rhs_kind,
1184 define_opaque,
1185 ..
1186 }) => (
1187 *ident,
1188 self.lower_generics(
1189 generics,
1190 ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
1191 |this| {
1192 let ty = this.lower_ty_alloc(
1193 ty,
1194 ImplTraitContext::Disallowed(ImplTraitPosition::ConstTy),
1195 );
1196 this.lower_define_opaque(hir_id, &define_opaque);
1197 let rhs = this.lower_const_item_rhs(rhs_kind, i.span);
1198 hir::ImplItemKind::Const(ty, rhs)
1199 },
1200 ),
1201 ),
1202 AssocItemKind::Fn(Fn {
1203 sig, ident, generics, body, contract, define_opaque, ..
1204 }) => {
1205 let body_id = self.lower_maybe_coroutine_body(
1206 sig.span,
1207 i.span,
1208 hir_id,
1209 &sig.decl,
1210 sig.header.coroutine_kind,
1211 body.as_deref(),
1212 attrs,
1213 contract.as_deref(),
1214 );
1215 let (generics, sig) = self.lower_method_sig(
1216 generics,
1217 sig,
1218 i.id,
1219 if is_in_trait_impl { FnDeclKind::Impl } else { FnDeclKind::Inherent },
1220 sig.header.coroutine_kind,
1221 attrs,
1222 );
1223 self.lower_define_opaque(hir_id, &define_opaque);
1224
1225 (*ident, (generics, hir::ImplItemKind::Fn(sig, body_id)))
1226 }
1227 AssocItemKind::Type(TyAlias { ident, generics, after_where_clause, ty, .. }) => {
1228 let mut generics = generics.clone();
1229 add_ty_alias_where_clause(&mut generics, after_where_clause, false);
1230 (
1231 *ident,
1232 self.lower_generics(
1233 &generics,
1234 ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
1235 |this| match ty {
1236 None => {
1237 let guar = this.dcx().span_delayed_bug(
1238 i.span,
1239 "expected to lower associated type, but it was missing",
1240 );
1241 let ty = this.arena.alloc(this.ty(i.span, hir::TyKind::Err(guar)));
1242 hir::ImplItemKind::Type(ty)
1243 }
1244 Some(ty) => {
1245 let ty = this.lower_ty_alloc(
1246 ty,
1247 ImplTraitContext::OpaqueTy {
1248 origin: hir::OpaqueTyOrigin::TyAlias {
1249 parent: this.owner.def_id,
1250 in_assoc_ty: true,
1251 },
1252 },
1253 );
1254 hir::ImplItemKind::Type(ty)
1255 }
1256 },
1257 ),
1258 )
1259 }
1260 AssocItemKind::Delegation(delegation) => {
1261 let delegation_results = self.lower_delegation(delegation);
1262 (
1263 delegation.ident,
1264 (
1265 delegation_results.generics,
1266 hir::ImplItemKind::Fn(delegation_results.sig, delegation_results.body_id),
1267 ),
1268 )
1269 }
1270 AssocItemKind::MacCall(..) | AssocItemKind::DelegationMac(..) => {
1271 {
::core::panicking::panic_fmt(format_args!("macros should have been expanded by now"));
}panic!("macros should have been expanded by now")
1272 }
1273 };
1274
1275 let span = self.lower_span(i.span);
1276 let (effective_ident, impl_kind) = if is_in_trait_impl {
1277 let trait_item_def_id = self
1278 .get_partial_res(i.id)
1279 .and_then(|r| r.expect_full_res().opt_def_id())
1280 .ok_or_else(|| {
1281 self.dcx()
1282 .span_delayed_bug(span, "could not resolve trait item being implemented")
1283 });
1284 let effective_ident = self.check_pin_drop_sugar_impl_item(i, ident, trait_item_def_id);
1285 (effective_ident, ImplItemImplKind::Trait { defaultness, trait_item_def_id })
1286 } else {
1287 (ident, ImplItemImplKind::Inherent { vis_span: self.lower_span(i.vis.span) })
1288 };
1289
1290 let item = hir::ImplItem {
1291 owner_id,
1292 ident: self.lower_ident(effective_ident),
1293 generics,
1294 impl_kind,
1295 kind,
1296 span,
1297 };
1298 self.arena.alloc(item)
1299 }
1300
1301 fn lower_impl_item_ref(&mut self, i: &AssocItem) -> hir::ImplItemId {
1302 hir::ImplItemId { owner_id: self.owner_id(i.id) }
1303 }
1304
1305 fn lower_defaultness(
1306 &self,
1307 d: Defaultness,
1308 has_value: bool,
1309 implicit: impl FnOnce() -> hir::Defaultness,
1310 ) -> (hir::Defaultness, Option<Span>) {
1311 match d {
1312 Defaultness::Implicit => (implicit(), None),
1313 Defaultness::Default(sp) => {
1314 (hir::Defaultness::Default { has_value }, Some(self.lower_span(sp)))
1315 }
1316 Defaultness::Final(sp) => (hir::Defaultness::Final, Some(self.lower_span(sp))),
1317 }
1318 }
1319
1320 fn record_body(
1321 &mut self,
1322 params: &'hir [hir::Param<'hir>],
1323 value: hir::Expr<'hir>,
1324 ) -> hir::BodyId {
1325 let body = hir::Body { params, value: self.arena.alloc(value) };
1326 let id = body.id();
1327 {
match (&id.hir_id.owner, &self.current_hir_id_owner) {
(left_val, right_val) => {
if !(*left_val == *right_val) {
let kind = ::core::panicking::AssertKind::Eq;
::core::panicking::assert_failed(kind, &*left_val,
&*right_val, ::core::option::Option::None);
}
}
}
};assert_eq!(id.hir_id.owner, self.current_hir_id_owner);
1328 self.bodies.push((id.hir_id.local_id, self.arena.alloc(body)));
1329 id
1330 }
1331
1332 pub(super) fn lower_body(
1333 &mut self,
1334 f: impl FnOnce(&mut Self) -> (&'hir [hir::Param<'hir>], hir::Expr<'hir>),
1335 ) -> hir::BodyId {
1336 let prev_coroutine_kind = self.coroutine_kind.take();
1337 let task_context = self.task_context.take();
1338 let (parameters, result) = f(self);
1339 let body_id = self.record_body(parameters, result);
1340 self.task_context = task_context;
1341 self.coroutine_kind = prev_coroutine_kind;
1342 body_id
1343 }
1344
1345 fn lower_param(&mut self, param: &Param) -> hir::Param<'hir> {
1346 let hir_id = self.lower_node_id(param.id);
1347 self.lower_attrs(hir_id, ¶m.attrs, param.span, Target::Param);
1348 hir::Param {
1349 hir_id,
1350 pat: self.lower_pat(¶m.pat),
1351 ty_span: self.lower_span(param.ty.span),
1352 span: self.lower_span(param.span),
1353 }
1354 }
1355
1356 pub(super) fn lower_fn_body(
1357 &mut self,
1358 decl: &FnDecl,
1359 contract: Option<&FnContract>,
1360 body: impl FnOnce(&mut Self) -> hir::Expr<'hir>,
1361 ) -> hir::BodyId {
1362 self.lower_body(|this| {
1363 let params =
1364 this.arena.alloc_from_iter(decl.inputs.iter().map(|x| this.lower_param(x)));
1365
1366 if let Some(contract) = contract {
1368 (params, this.lower_contract(body, contract))
1369 } else {
1370 (params, body(this))
1371 }
1372 })
1373 }
1374
1375 fn lower_fn_body_block(
1376 &mut self,
1377 decl: &FnDecl,
1378 body: &Block,
1379 contract: Option<&FnContract>,
1380 ) -> hir::BodyId {
1381 self.lower_fn_body(decl, contract, |this| this.lower_block_expr(body))
1382 }
1383
1384 pub(super) fn lower_const_body(&mut self, span: Span, expr: Option<&Expr>) -> hir::BodyId {
1385 self.lower_body(|this| {
1386 (
1387 &[],
1388 match expr {
1389 Some(expr) => this.lower_expr_mut(expr),
1390 None => this.expr_err(span, this.dcx().span_delayed_bug(span, "no block")),
1391 },
1392 )
1393 })
1394 }
1395
1396 fn lower_maybe_coroutine_body(
1399 &mut self,
1400 fn_decl_span: Span,
1401 span: Span,
1402 fn_id: hir::HirId,
1403 decl: &FnDecl,
1404 coroutine_kind: Option<CoroutineKind>,
1405 body: Option<&Block>,
1406 attrs: &'hir [hir::Attribute],
1407 contract: Option<&FnContract>,
1408 ) -> hir::BodyId {
1409 let Some(body) = body else {
1410 return self.lower_fn_body(decl, contract, |this| {
1414 if {
{
'done:
{
for i in attrs {
#[allow(unused_imports)]
use rustc_hir::attrs::AttributeKind::*;
let i: &rustc_hir::Attribute = i;
match i {
rustc_hir::Attribute::Parsed(RustcIntrinsic) => {
break 'done Some(());
}
rustc_hir::Attribute::Unparsed(..) =>
{}
#[deny(unreachable_patterns)]
_ => {}
}
}
None
}
}.is_some()
}find_attr!(attrs, RustcIntrinsic) || this.tcx.is_sdylib_interface_build() {
1415 let span = this.lower_span(span);
1416 let empty_block = hir::Block {
1417 hir_id: this.next_id(),
1418 stmts: &[],
1419 expr: None,
1420 rules: hir::BlockCheckMode::DefaultBlock,
1421 span,
1422 targeted_by_break: false,
1423 };
1424 let loop_ = hir::ExprKind::Loop(
1425 this.arena.alloc(empty_block),
1426 None,
1427 hir::LoopSource::Loop,
1428 span,
1429 );
1430 hir::Expr { hir_id: this.next_id(), kind: loop_, span }
1431 } else {
1432 this.expr_err(span, this.dcx().has_errors().unwrap())
1433 }
1434 });
1435 };
1436 let Some(coroutine_kind) = coroutine_kind else {
1437 return self.lower_fn_body_block(decl, body, contract);
1439 };
1440 self.lower_body(|this| {
1442 let (parameters, expr) = this.lower_coroutine_body_with_moved_arguments(
1443 decl,
1444 |this| this.lower_block_expr(body),
1445 fn_decl_span,
1446 body.span,
1447 coroutine_kind,
1448 hir::CoroutineSource::Fn,
1449 );
1450
1451 let hir_id = expr.hir_id;
1453 this.maybe_forward_track_caller(body.span, fn_id, hir_id);
1454
1455 (parameters, expr)
1456 })
1457 }
1458
1459 pub(crate) fn lower_coroutine_body_with_moved_arguments(
1464 &mut self,
1465 decl: &FnDecl,
1466 lower_body: impl FnOnce(&mut LoweringContext<'_, 'hir>) -> hir::Expr<'hir>,
1467 fn_decl_span: Span,
1468 body_span: Span,
1469 coroutine_kind: CoroutineKind,
1470 coroutine_source: hir::CoroutineSource,
1471 ) -> (&'hir [hir::Param<'hir>], hir::Expr<'hir>) {
1472 let mut parameters: Vec<hir::Param<'_>> = Vec::new();
1473 let mut statements: Vec<hir::Stmt<'_>> = Vec::new();
1474
1475 for (index, parameter) in decl.inputs.iter().enumerate() {
1508 let parameter = self.lower_param(parameter);
1509 let span = parameter.pat.span;
1510
1511 let (ident, is_simple_parameter) = match parameter.pat.kind {
1514 hir::PatKind::Binding(hir::BindingMode(ByRef::No, _), _, ident, _) => (ident, true),
1515 hir::PatKind::Binding(_, _, ident, _) => (ident, false),
1519 hir::PatKind::Wild => (Ident::with_dummy_span(rustc_span::kw::Underscore), false),
1520 _ => {
1521 let name = ::alloc::__export::must_use({
::alloc::fmt::format(format_args!("__arg{0}", index))
})format!("__arg{index}");
1523 let ident = Ident::from_str(&name);
1524
1525 (ident, false)
1526 }
1527 };
1528
1529 let desugared_span = self.mark_span_with_reason(DesugaringKind::Async, span, None);
1530
1531 let stmt_attrs = self.attrs.get(¶meter.hir_id.local_id).copied();
1537 let (new_parameter_pat, new_parameter_id) = self.pat_ident(desugared_span, ident);
1538 let new_parameter = hir::Param {
1539 hir_id: parameter.hir_id,
1540 pat: new_parameter_pat,
1541 ty_span: self.lower_span(parameter.ty_span),
1542 span: self.lower_span(parameter.span),
1543 };
1544
1545 if is_simple_parameter {
1546 let expr = self.expr_ident(desugared_span, ident, new_parameter_id);
1550 let stmt = self.stmt_let_pat(
1551 stmt_attrs,
1552 desugared_span,
1553 Some(expr),
1554 parameter.pat,
1555 hir::LocalSource::AsyncFn,
1556 );
1557 statements.push(stmt);
1558 } else {
1559 let (move_pat, move_id) =
1575 self.pat_ident_binding_mode(desugared_span, ident, hir::BindingMode::MUT);
1576 let move_expr = self.expr_ident(desugared_span, ident, new_parameter_id);
1577 let move_stmt = self.stmt_let_pat(
1578 None,
1579 desugared_span,
1580 Some(move_expr),
1581 move_pat,
1582 hir::LocalSource::AsyncFn,
1583 );
1584
1585 let pattern_expr = self.expr_ident(desugared_span, ident, move_id);
1588 let pattern_stmt = self.stmt_let_pat(
1589 stmt_attrs,
1590 desugared_span,
1591 Some(pattern_expr),
1592 parameter.pat,
1593 hir::LocalSource::AsyncFn,
1594 );
1595
1596 statements.push(move_stmt);
1597 statements.push(pattern_stmt);
1598 };
1599
1600 parameters.push(new_parameter);
1601 }
1602
1603 let mkbody = |this: &mut LoweringContext<'_, 'hir>| {
1604 let user_body = lower_body(this);
1606
1607 let desugared_span =
1609 this.mark_span_with_reason(DesugaringKind::Async, user_body.span, None);
1610 let user_body = this.expr_drop_temps(desugared_span, this.arena.alloc(user_body));
1611
1612 let body = this.block_all(
1622 desugared_span,
1623 this.arena.alloc_from_iter(statements),
1624 Some(user_body),
1625 );
1626
1627 this.expr_block(body)
1628 };
1629 let desugaring_kind = match coroutine_kind {
1630 CoroutineKind::Async { .. } => hir::CoroutineDesugaring::Async,
1631 CoroutineKind::Gen { .. } => hir::CoroutineDesugaring::Gen,
1632 CoroutineKind::AsyncGen { .. } => hir::CoroutineDesugaring::AsyncGen,
1633 };
1634 let closure_id = coroutine_kind.closure_id();
1635
1636 let coroutine_expr = self.make_desugared_coroutine_expr(
1637 CaptureBy::Ref,
1642 closure_id,
1643 None,
1644 fn_decl_span,
1645 body_span,
1646 desugaring_kind,
1647 coroutine_source,
1648 mkbody,
1649 );
1650
1651 let expr = hir::Expr {
1652 hir_id: self.lower_node_id(closure_id),
1653 kind: coroutine_expr,
1654 span: self.lower_span(body_span),
1655 };
1656
1657 (self.arena.alloc_from_iter(parameters), expr)
1658 }
1659
1660 fn lower_method_sig(
1661 &mut self,
1662 generics: &Generics,
1663 sig: &FnSig,
1664 id: NodeId,
1665 kind: FnDeclKind,
1666 coroutine_kind: Option<CoroutineKind>,
1667 attrs: &[hir::Attribute],
1668 ) -> (&'hir hir::Generics<'hir>, hir::FnSig<'hir>) {
1669 let header = self.lower_fn_header(sig.header, hir::Safety::Safe, attrs);
1670 let itctx = ImplTraitContext::Universal;
1671 let (generics, decl) = self.lower_generics(generics, itctx, |this| {
1672 this.lower_fn_decl(&sig.decl, id, sig.span, kind, coroutine_kind)
1673 });
1674 (generics, hir::FnSig { header, decl, span: self.lower_span(sig.span) })
1675 }
1676
1677 pub(super) fn lower_fn_header(
1678 &mut self,
1679 h: FnHeader,
1680 default_safety: hir::Safety,
1681 attrs: &[hir::Attribute],
1682 ) -> hir::FnHeader {
1683 let asyncness = if let Some(CoroutineKind::Async { span, .. }) = h.coroutine_kind {
1684 hir::IsAsync::Async(self.lower_span(span))
1685 } else {
1686 hir::IsAsync::NotAsync
1687 };
1688
1689 let safety = self.lower_safety(h.safety, default_safety);
1690
1691 let safety = if {
{
'done:
{
for i in attrs {
#[allow(unused_imports)]
use rustc_hir::attrs::AttributeKind::*;
let i: &rustc_hir::Attribute = i;
match i {
rustc_hir::Attribute::Parsed(TargetFeature {
was_forced: false, .. }) => {
break 'done Some(());
}
rustc_hir::Attribute::Unparsed(..) =>
{}
#[deny(unreachable_patterns)]
_ => {}
}
}
None
}
}.is_some()
}find_attr!(attrs, TargetFeature { was_forced: false, .. })
1693 && safety.is_safe()
1694 && !self.tcx.sess.target.is_like_wasm
1695 {
1696 hir::HeaderSafety::SafeTargetFeatures
1697 } else {
1698 safety.into()
1699 };
1700
1701 let constness = self.lower_constness(attrs, h.constness);
1702
1703 hir::FnHeader { safety, asyncness, constness, abi: self.lower_extern(h.ext) }
1704 }
1705
1706 pub(super) fn lower_abi(&mut self, abi_str: StrLit) -> ExternAbi {
1707 let ast::StrLit { symbol_unescaped, span, .. } = abi_str;
1708 let extern_abi = symbol_unescaped.as_str().parse().unwrap_or_else(|_| {
1709 self.error_on_invalid_abi(abi_str);
1710 ExternAbi::Rust
1711 });
1712 let tcx = self.tcx;
1713
1714 if !tcx.sess.target.is_abi_supported(extern_abi) {
1716 let mut err = {
tcx.dcx().struct_span_err(span,
::alloc::__export::must_use({
::alloc::fmt::format(format_args!("{0} is not a supported ABI for the current target",
extern_abi))
})).with_code(E0570)
}struct_span_code_err!(
1717 tcx.dcx(),
1718 span,
1719 E0570,
1720 "{extern_abi} is not a supported ABI for the current target",
1721 );
1722
1723 if let ExternAbi::Stdcall { unwind } = extern_abi {
1724 let c_abi = ExternAbi::C { unwind };
1725 let system_abi = ExternAbi::System { unwind };
1726 err.help(::alloc::__export::must_use({
::alloc::fmt::format(format_args!("if you need `extern {0}` on win32 and `extern {1}` everywhere else, use `extern {2}`",
extern_abi, c_abi, system_abi))
})format!("if you need `extern {extern_abi}` on win32 and `extern {c_abi}` everywhere else, \
1727 use `extern {system_abi}`"
1728 ));
1729 }
1730 err.emit();
1731 }
1732 gate_unstable_abi(tcx.sess, tcx.features(), span, extern_abi);
1735 extern_abi
1736 }
1737
1738 pub(super) fn lower_extern(&mut self, ext: Extern) -> ExternAbi {
1739 match ext {
1740 Extern::None => ExternAbi::Rust,
1741 Extern::Implicit(_) => ExternAbi::FALLBACK,
1742 Extern::Explicit(abi, _) => self.lower_abi(abi),
1743 }
1744 }
1745
1746 fn error_on_invalid_abi(&self, abi: StrLit) {
1747 let abi_names = enabled_names(self.tcx.features(), abi.span)
1748 .iter()
1749 .map(|s| Symbol::intern(s))
1750 .collect::<Vec<_>>();
1751 let suggested_name = find_best_match_for_name(&abi_names, abi.symbol_unescaped, None);
1752 self.dcx().emit_err(InvalidAbi {
1753 abi: abi.symbol_unescaped,
1754 span: abi.span,
1755 suggestion: suggested_name.map(|suggested_name| InvalidAbiSuggestion {
1756 span: abi.span,
1757 suggestion: suggested_name.to_string(),
1758 }),
1759 command: "rustc --print=calling-conventions".to_string(),
1760 });
1761 }
1762
1763 pub(super) fn lower_constness(&mut self, attrs: &[hir::Attribute], c: Const) -> hir::Constness {
1767 let mut constness = match c {
1768 Const::Yes(_) => hir::Constness::Const { always: false },
1769 Const::No => hir::Constness::NotConst,
1770 };
1771
1772 if let Some(&attr_span) = {
'done:
{
for i in attrs {
#[allow(unused_imports)]
use rustc_hir::attrs::AttributeKind::*;
let i: &rustc_hir::Attribute = i;
match i {
rustc_hir::Attribute::Parsed(RustcComptime(span)) => {
break 'done Some(span);
}
rustc_hir::Attribute::Unparsed(..) =>
{}
#[deny(unreachable_patterns)]
_ => {}
}
}
None
}
}find_attr!(attrs, RustcComptime(span) => span) {
1773 match std::mem::replace(&mut constness, hir::Constness::Const { always: true }) {
1774 hir::Constness::Const { always: true } => {
1775 {
::core::panicking::panic_fmt(format_args!("internal error: entered unreachable code: {0}",
format_args!("lower_constness cannot produce comptime")));
}unreachable!("lower_constness cannot produce comptime")
1776 }
1777 hir::Constness::Const { always: false } => {
1779 let Const::Yes(span) = c else { ::core::panicking::panic("internal error: entered unreachable code")unreachable!() };
1780 self.dcx().emit_err(ConstComptimeFn { span, attr_span });
1781 }
1782 hir::Constness::NotConst => {}
1784 }
1785 }
1786 constness
1787 }
1788
1789 pub(super) fn lower_safety(&self, s: Safety, default: hir::Safety) -> hir::Safety {
1790 match s {
1791 Safety::Unsafe(_) => hir::Safety::Unsafe,
1792 Safety::Default => default,
1793 Safety::Safe(_) => hir::Safety::Safe,
1794 }
1795 }
1796
1797 fn lower_restriction_kind(&mut self, kind: &RestrictionKind) -> hir::RestrictionKind<'hir> {
1798 match kind {
1799 RestrictionKind::Unrestricted => hir::RestrictionKind::Unrestricted,
1800 RestrictionKind::Restricted { path, id, shorthand: _ } => {
1801 let res = self.get_partial_res(*id);
1802 if let Some(did) = res.and_then(|res| res.expect_full_res().opt_def_id()) {
1803 hir::RestrictionKind::Restricted(self.arena.alloc(hir::Path {
1804 res: did,
1805 segments: self.arena.alloc_from_iter(path.segments.iter().map(|segment| {
1806 self.lower_path_segment(
1807 path.span,
1808 segment,
1809 ParamMode::Explicit,
1810 GenericArgsMode::Err,
1811 ImplTraitContext::Disallowed(ImplTraitPosition::Path),
1812 None,
1813 )
1814 })),
1815 span: self.lower_span(path.span),
1816 }))
1817 } else {
1818 self.dcx().span_delayed_bug(path.span, "should have errored in resolve");
1819 hir::RestrictionKind::Unrestricted
1820 }
1821 }
1822 }
1823 }
1824
1825 pub(super) fn lower_impl_restriction(
1826 &mut self,
1827 r: &ImplRestriction,
1828 ) -> &'hir hir::ImplRestriction<'hir> {
1829 let kind = self.lower_restriction_kind(&r.kind);
1830 self.arena.alloc(hir::ImplRestriction { kind, span: self.lower_span(r.span) })
1831 }
1832
1833 pub(super) fn lower_mut_restriction(
1834 &mut self,
1835 r: &MutRestriction,
1836 ) -> &'hir hir::MutRestriction<'hir> {
1837 let kind = self.lower_restriction_kind(&r.kind);
1838 self.arena.alloc(hir::MutRestriction { kind, span: self.lower_span(r.span) })
1839 }
1840
1841 #[allow(clippy :: suspicious_else_formatting)]
{
let __tracing_attr_span;
let __tracing_attr_guard;
if ::tracing::Level::DEBUG <= ::tracing::level_filters::STATIC_MAX_LEVEL
&&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() ||
{ false } {
__tracing_attr_span =
{
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("lower_generics",
"rustc_ast_lowering::item", ::tracing::Level::DEBUG,
::tracing_core::__macro_support::Option::Some("compiler/rustc_ast_lowering/src/item.rs"),
::tracing_core::__macro_support::Option::Some(1843u32),
::tracing_core::__macro_support::Option::Some("rustc_ast_lowering::item"),
::tracing_core::field::FieldSet::new(&[{
const NAME:
::tracing::__macro_support::FieldName<{
::tracing::__macro_support::FieldName::len("generics")
}> =
::tracing::__macro_support::FieldName::new("generics");
NAME.as_str()
},
{
const NAME:
::tracing::__macro_support::FieldName<{
::tracing::__macro_support::FieldName::len("itctx")
}> =
::tracing::__macro_support::FieldName::new("itctx");
NAME.as_str()
}], ::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::SPAN)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let mut interest = ::tracing::subscriber::Interest::never();
if ::tracing::Level::DEBUG <=
::tracing::level_filters::STATIC_MAX_LEVEL &&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() &&
{ interest = __CALLSITE.interest(); !interest.is_never() }
&&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest) {
let meta = __CALLSITE.metadata();
::tracing::Span::new(meta,
&{
#[allow(unused_imports)]
use ::tracing::field::{debug, display, Value};
meta.fields().value_set_all(&[(::tracing::__macro_support::Option::Some(&::tracing::field::debug(&generics)
as &dyn ::tracing::field::Value)),
(::tracing::__macro_support::Option::Some(&::tracing::field::debug(&itctx)
as &dyn ::tracing::field::Value))])
})
} else {
let span =
::tracing::__macro_support::__disabled_span(__CALLSITE.metadata());
{};
span
}
};
__tracing_attr_guard = __tracing_attr_span.enter();
}
#[warn(clippy :: suspicious_else_formatting)]
{
#[allow(unknown_lints, unreachable_code, clippy ::
diverging_sub_expression, clippy :: empty_loop, clippy ::
let_unit_value, clippy :: let_with_type_underscore, clippy ::
needless_return, clippy :: unreachable)]
if false {
let __tracing_attr_fake_return: (&'hir hir::Generics<'hir>, T) =
loop {};
return __tracing_attr_fake_return;
}
{
if !self.impl_trait_defs.is_empty() {
::core::panicking::panic("assertion failed: self.impl_trait_defs.is_empty()")
};
if !self.impl_trait_bounds.is_empty() {
::core::panicking::panic("assertion failed: self.impl_trait_bounds.is_empty()")
};
let mut predicates: SmallVec<[hir::WherePredicate<'hir>; 4]> =
SmallVec::new();
let mut dedup_map: IndexMap<LocalDefId, _> = Default::default();
predicates.extend(generics.params.iter().filter_map(|param|
{
self.lower_generic_bound_predicate(param.ident, param.id,
¶m.kind, ¶m.bounds, param.colon_span, generics.span,
RelaxedBoundPolicy::Allowed(dedup_map.entry(self.local_def_id(param.id)).or_default()),
itctx, PredicateOrigin::GenericParam)
}));
predicates.extend(generics.where_clause.predicates.iter().map(|predicate|
{
self.lower_where_predicate(predicate, &generics.params,
&mut dedup_map)
}));
let mut params: SmallVec<[hir::GenericParam<'hir>; 4]> =
self.lower_generic_params_mut(&generics.params,
hir::GenericParamSource::Generics).collect();
let extra_lifetimes =
self.owner.extra_lifetime_params(self.owner.id);
params.extend(extra_lifetimes.into_iter().map(|&(ident, node_id,
kind)|
{
self.lifetime_res_to_generic_param(ident, node_id, kind,
hir::GenericParamSource::Generics)
}));
let has_where_clause_predicates =
!generics.where_clause.predicates.is_empty();
let where_clause_span =
self.lower_span(generics.where_clause.span);
let span = self.lower_span(generics.span);
let res = f(self);
let impl_trait_defs = std::mem::take(&mut self.impl_trait_defs);
params.extend(impl_trait_defs.into_iter());
let impl_trait_bounds =
std::mem::take(&mut self.impl_trait_bounds);
predicates.extend(impl_trait_bounds.into_iter());
let lowered_generics =
self.arena.alloc(hir::Generics {
params: self.arena.alloc_from_iter(params),
predicates: self.arena.alloc_from_iter(predicates),
has_where_clause_predicates,
where_clause_span,
span,
});
(lowered_generics, res)
}
}
}#[instrument(level = "debug", skip(self, f))]
1844 fn lower_generics<T>(
1845 &mut self,
1846 generics: &Generics,
1847 itctx: ImplTraitContext,
1848 f: impl FnOnce(&mut Self) -> T,
1849 ) -> (&'hir hir::Generics<'hir>, T) {
1850 assert!(self.impl_trait_defs.is_empty());
1851 assert!(self.impl_trait_bounds.is_empty());
1852
1853 let mut predicates: SmallVec<[hir::WherePredicate<'hir>; 4]> = SmallVec::new();
1854 let mut dedup_map: IndexMap<LocalDefId, _> = Default::default();
1857 predicates.extend(generics.params.iter().filter_map(|param| {
1858 self.lower_generic_bound_predicate(
1859 param.ident,
1860 param.id,
1861 ¶m.kind,
1862 ¶m.bounds,
1863 param.colon_span,
1864 generics.span,
1865 RelaxedBoundPolicy::Allowed(
1866 dedup_map.entry(self.local_def_id(param.id)).or_default(),
1867 ),
1868 itctx,
1869 PredicateOrigin::GenericParam,
1870 )
1871 }));
1872 predicates.extend(generics.where_clause.predicates.iter().map(|predicate| {
1873 self.lower_where_predicate(predicate, &generics.params, &mut dedup_map)
1874 }));
1875
1876 let mut params: SmallVec<[hir::GenericParam<'hir>; 4]> = self
1877 .lower_generic_params_mut(&generics.params, hir::GenericParamSource::Generics)
1878 .collect();
1879
1880 let extra_lifetimes = self.owner.extra_lifetime_params(self.owner.id);
1882 params.extend(extra_lifetimes.into_iter().map(|&(ident, node_id, kind)| {
1883 self.lifetime_res_to_generic_param(
1884 ident,
1885 node_id,
1886 kind,
1887 hir::GenericParamSource::Generics,
1888 )
1889 }));
1890
1891 let has_where_clause_predicates = !generics.where_clause.predicates.is_empty();
1892 let where_clause_span = self.lower_span(generics.where_clause.span);
1893 let span = self.lower_span(generics.span);
1894 let res = f(self);
1895
1896 let impl_trait_defs = std::mem::take(&mut self.impl_trait_defs);
1897 params.extend(impl_trait_defs.into_iter());
1898
1899 let impl_trait_bounds = std::mem::take(&mut self.impl_trait_bounds);
1900 predicates.extend(impl_trait_bounds.into_iter());
1901
1902 let lowered_generics = self.arena.alloc(hir::Generics {
1903 params: self.arena.alloc_from_iter(params),
1904 predicates: self.arena.alloc_from_iter(predicates),
1905 has_where_clause_predicates,
1906 where_clause_span,
1907 span,
1908 });
1909
1910 (lowered_generics, res)
1911 }
1912
1913 pub(super) fn lower_define_opaque(
1914 &mut self,
1915 hir_id: HirId,
1916 define_opaque: &Option<ThinVec<(NodeId, Path)>>,
1917 ) {
1918 {
match (&self.define_opaque, &None) {
(left_val, right_val) => {
if !(*left_val == *right_val) {
let kind = ::core::panicking::AssertKind::Eq;
::core::panicking::assert_failed(kind, &*left_val,
&*right_val, ::core::option::Option::None);
}
}
}
};assert_eq!(self.define_opaque, None);
1919 if !hir_id.is_owner() {
::core::panicking::panic("assertion failed: hir_id.is_owner()")
};assert!(hir_id.is_owner());
1920 let Some(define_opaque) = define_opaque.as_ref() else {
1921 return;
1922 };
1923 let define_opaque = define_opaque.iter().filter_map(|(id, path)| {
1924 let res = self.get_partial_res(*id);
1925 let Some(did) = res.and_then(|res| res.expect_full_res().opt_def_id()) else {
1926 self.dcx().span_delayed_bug(path.span, "should have errored in resolve");
1927 return None;
1928 };
1929 let Some(did) = did.as_local() else {
1930 self.dcx().span_err(
1931 path.span,
1932 "only opaque types defined in the local crate can be defined",
1933 );
1934 return None;
1935 };
1936 Some((self.lower_span(path.span), did))
1937 });
1938 let define_opaque = self.arena.alloc_from_iter(define_opaque);
1939 self.define_opaque = Some(define_opaque);
1940 }
1941
1942 pub(super) fn lower_generic_bound_predicate(
1943 &mut self,
1944 ident: Ident,
1945 id: NodeId,
1946 kind: &GenericParamKind,
1947 bounds: &[GenericBound],
1948 colon_span: Option<Span>,
1949 parent_span: Span,
1950 rbp: RelaxedBoundPolicy<'_>,
1951 itctx: ImplTraitContext,
1952 origin: PredicateOrigin,
1953 ) -> Option<hir::WherePredicate<'hir>> {
1954 if bounds.is_empty() {
1956 return None;
1957 }
1958
1959 let bounds = self.lower_param_bounds(bounds, rbp, itctx);
1960
1961 let param_span = ident.span;
1962
1963 let span_start = colon_span.unwrap_or_else(|| param_span.shrink_to_hi());
1965 let span = bounds.iter().fold(span_start, |span_accum, bound| {
1966 match bound.span().find_ancestor_inside(parent_span) {
1967 Some(bound_span) => span_accum.to(bound_span),
1968 None => span_accum,
1969 }
1970 });
1971 let span = self.lower_span(span);
1972 let hir_id = self.next_id();
1973 let kind = self.arena.alloc(match kind {
1974 GenericParamKind::Const { .. } => return None,
1975 GenericParamKind::Type { .. } => {
1976 let def_id = self.local_def_id(id).to_def_id();
1977 let hir_id = self.next_id();
1978 let res = Res::Def(DefKind::TyParam, def_id);
1979 let ident = self.lower_ident(ident);
1980 let ty_path = self.arena.alloc(hir::Path {
1981 span: self.lower_span(param_span),
1982 res,
1983 segments: self
1984 .arena
1985 .alloc_from_iter([hir::PathSegment::new(ident, hir_id, res)]),
1986 });
1987 let ty_id = self.next_id();
1988 let bounded_ty =
1989 self.ty_path(ty_id, param_span, hir::QPath::Resolved(None, ty_path));
1990 hir::WherePredicateKind::BoundPredicate(hir::WhereBoundPredicate {
1991 bounded_ty: self.arena.alloc(bounded_ty),
1992 bounds,
1993 bound_generic_params: &[],
1994 origin,
1995 })
1996 }
1997 GenericParamKind::Lifetime => {
1998 let lt_id = self.next_node_id();
1999 let lifetime =
2000 self.new_named_lifetime(id, lt_id, ident, LifetimeSource::Other, ident.into());
2001 hir::WherePredicateKind::RegionPredicate(hir::WhereRegionPredicate {
2002 lifetime,
2003 bounds,
2004 in_where_clause: false,
2005 })
2006 }
2007 });
2008 Some(hir::WherePredicate { hir_id, span, kind })
2009 }
2010
2011 fn lower_where_predicate(
2012 &mut self,
2013 pred: &WherePredicate,
2014 params: &[ast::GenericParam],
2015 dedup_map: &mut IndexMap<LocalDefId, IndexMap<DefId, Span>>,
2016 ) -> hir::WherePredicate<'hir> {
2017 let hir_id = self.lower_node_id(pred.id);
2018 let span = self.lower_span(pred.span);
2019 self.lower_attrs(hir_id, &pred.attrs, span, Target::WherePredicate);
2020 let kind = self.arena.alloc(match &pred.kind {
2021 WherePredicateKind::BoundPredicate(WhereBoundPredicate {
2022 bound_generic_params,
2023 bounded_ty,
2024 bounds,
2025 }) => {
2026 let rbp = if bound_generic_params.is_empty()
2027 && let Some(res) =
2028 self.get_partial_res(bounded_ty.id).and_then(|r| r.full_res())
2029 && let Res::Def(DefKind::TyParam, def_id) = res
2030 && params.iter().any(|p| def_id == self.local_def_id(p.id).to_def_id())
2031 {
2032 RelaxedBoundPolicy::Allowed(dedup_map.entry(def_id.expect_local()).or_default())
2033 } else {
2034 RelaxedBoundPolicy::Forbidden(RelaxedBoundForbiddenReason::WhereBound)
2035 };
2036 hir::WherePredicateKind::BoundPredicate(hir::WhereBoundPredicate {
2037 bound_generic_params: self.lower_generic_params(
2038 bound_generic_params,
2039 hir::GenericParamSource::Binder,
2040 ),
2041 bounded_ty: self.lower_ty_alloc(
2042 bounded_ty,
2043 ImplTraitContext::Disallowed(ImplTraitPosition::Bound),
2044 ),
2045 bounds: self.lower_param_bounds(
2046 bounds,
2047 rbp,
2048 ImplTraitContext::Disallowed(ImplTraitPosition::Bound),
2049 ),
2050 origin: PredicateOrigin::WhereClause,
2051 })
2052 }
2053 WherePredicateKind::RegionPredicate(WhereRegionPredicate { lifetime, bounds }) => {
2054 hir::WherePredicateKind::RegionPredicate(hir::WhereRegionPredicate {
2055 lifetime: self.lower_lifetime(
2056 lifetime,
2057 LifetimeSource::Other,
2058 lifetime.ident.into(),
2059 ),
2060 bounds: self.lower_param_bounds(
2061 bounds,
2062 RelaxedBoundPolicy::Allowed(&mut Default::default()),
2063 ImplTraitContext::Disallowed(ImplTraitPosition::Bound),
2064 ),
2065 in_where_clause: true,
2066 })
2067 }
2068 });
2069 hir::WherePredicate { hir_id, span, kind }
2070 }
2071}