From 266f5471272532989332117e8a2e0bacb5b94ccf Mon Sep 17 00:00:00 2001 From: Vadim Petrochenkov Date: Sat, 9 Nov 2019 22:05:20 +0300 Subject: [PATCH] ast: Keep `extern` qualifiers in functions more precisely --- src/librustc/hir/lowering.rs | 2 +- src/librustc/hir/lowering/item.rs | 12 +++++-- src/librustc_parse/parser/item.rs | 35 +++++++++++-------- src/librustc_parse/parser/mod.rs | 24 +++++-------- src/librustc_parse/parser/ty.rs | 4 +-- src/librustc_save_analysis/sig.rs | 17 ++++----- src/libsyntax/ast.rs | 27 ++++++++------ src/libsyntax/feature_gate/check.rs | 16 ++++++--- src/libsyntax/mut_visit.rs | 4 +-- src/libsyntax/print/pprust.rs | 22 ++++++++---- src/libsyntax_ext/deriving/generic/mod.rs | 7 ++-- src/test/ui/proc-macro/span-preservation.rs | 10 ++---- .../ui/proc-macro/span-preservation.stderr | 26 ++++++++------ 13 files changed, 118 insertions(+), 88 deletions(-) diff --git a/src/librustc/hir/lowering.rs b/src/librustc/hir/lowering.rs index ef6a6ae23dc..12f6f66e96b 100644 --- a/src/librustc/hir/lowering.rs +++ b/src/librustc/hir/lowering.rs @@ -1219,7 +1219,7 @@ fn lower_ty_direct(&mut self, t: &Ty, mut itctx: ImplTraitContext<'_>) -> hir::T ImplTraitContext::disallowed(), ), unsafety: f.unsafety, - abi: this.lower_abi(f.abi), + abi: this.lower_extern(f.ext), decl: this.lower_fn_decl(&f.decl, None, false, None), param_names: this.lower_fn_params_to_names(&f.decl), })) diff --git a/src/librustc/hir/lowering/item.rs b/src/librustc/hir/lowering/item.rs index 4cd42927868..2dc7e014445 100644 --- a/src/librustc/hir/lowering/item.rs +++ b/src/librustc/hir/lowering/item.rs @@ -735,7 +735,7 @@ fn lower_foreign_item(&mut self, i: &ForeignItem) -> hir::ForeignItem { fn lower_foreign_mod(&mut self, fm: &ForeignMod) -> hir::ForeignMod { hir::ForeignMod { - abi: self.lower_abi(fm.abi), + abi: fm.abi.map_or(abi::Abi::C, |abi| self.lower_abi(abi)), items: fm.items .iter() .map(|x| self.lower_foreign_item(x)) @@ -1283,7 +1283,7 @@ fn lower_fn_header(&mut self, h: FnHeader) -> hir::FnHeader { unsafety: h.unsafety, asyncness: self.lower_asyncness(h.asyncness.node), constness: h.constness.node, - abi: self.lower_abi(h.abi), + abi: self.lower_extern(h.ext), } } @@ -1294,6 +1294,14 @@ pub(super) fn lower_abi(&mut self, abi: Abi) -> abi::Abi { }) } + pub(super) fn lower_extern(&mut self, ext: Extern) -> abi::Abi { + match ext { + Extern::None => abi::Abi::Rust, + Extern::Implicit => abi::Abi::C, + Extern::Explicit(abi) => self.lower_abi(abi), + } + } + fn error_on_invalid_abi(&self, abi: Abi) { struct_span_err!( self.sess, diff --git a/src/librustc_parse/parser/item.rs b/src/librustc_parse/parser/item.rs index 73099169879..fe86d03c6e7 100644 --- a/src/librustc_parse/parser/item.rs +++ b/src/librustc_parse/parser/item.rs @@ -114,7 +114,7 @@ fn parse_item_implementation( unsafety: Unsafety::Normal, asyncness: respan(fn_span, IsAsync::NotAsync), constness: respan(fn_span, Constness::NotConst), - abi, + ext: Extern::from_abi(abi), }; return self.parse_item_fn(lo, vis, attrs, header); } else if self.check(&token::OpenDelim(token::Brace)) { @@ -143,14 +143,14 @@ fn parse_item_implementation( if self.check_keyword(kw::Extern) { self.sess.gated_spans.gate(sym::const_extern_fn, lo.to(self.token.span)); } - let abi = self.parse_extern_abi()?; + let ext = self.parse_extern()?; self.bump(); // `fn` let header = FnHeader { unsafety, asyncness: respan(const_span, IsAsync::NotAsync), constness: respan(const_span, Constness::Const), - abi, + ext, }; return self.parse_item_fn(lo, vis, attrs, header); } @@ -193,7 +193,7 @@ fn parse_item_implementation( unsafety, asyncness, constness: respan(fn_span, Constness::NotConst), - abi: Abi::new(sym::Rust, fn_span), + ext: Extern::None, }; return self.parse_item_fn(lo, vis, attrs, header); } @@ -230,7 +230,7 @@ fn parse_item_implementation( unsafety: Unsafety::Normal, asyncness: respan(fn_span, IsAsync::NotAsync), constness: respan(fn_span, Constness::NotConst), - abi: Abi::new(sym::Rust, fn_span), + ext: Extern::None, }; return self.parse_item_fn(lo, vis, attrs, header); } @@ -242,14 +242,14 @@ fn parse_item_implementation( self.bump(); // `unsafe` // `{` is also expected after `unsafe`; in case of error, include it in the diagnostic. self.check(&token::OpenDelim(token::Brace)); - let abi = self.parse_extern_abi()?; + let ext = self.parse_extern()?; self.expect_keyword(kw::Fn)?; let fn_span = self.prev_span; let header = FnHeader { unsafety: Unsafety::Unsafe, asyncness: respan(fn_span, IsAsync::NotAsync), constness: respan(fn_span, Constness::NotConst), - abi, + ext, }; return self.parse_item_fn(lo, vis, attrs, header); } @@ -1100,7 +1100,7 @@ fn parse_crate_name_with_dashes(&mut self) -> PResult<'a, ast::Ident> { fn parse_item_foreign_mod( &mut self, lo: Span, - abi: Abi, + abi: Option, visibility: Visibility, mut attrs: Vec, extern_sp: Span, @@ -1775,9 +1775,16 @@ fn parse_item_fn( attrs: Vec, header: FnHeader, ) -> PResult<'a, Option>> { + let is_c_abi = match header.ext { + ast::Extern::None => false, + ast::Extern::Implicit => true, + ast::Extern::Explicit(abi) => abi.symbol == sym::C, + }; let (ident, decl, generics) = self.parse_fn_sig(ParamCfg { is_self_allowed: false, - allow_c_variadic: header.abi.symbol == sym::C && header.unsafety == Unsafety::Unsafe, + // FIXME: Parsing should not depend on ABI or unsafety and + // the variadic parameter should always be parsed. + allow_c_variadic: is_c_abi && header.unsafety == Unsafety::Unsafe, is_name_required: |_| true, })?; let (inner_attrs, body) = self.parse_inner_attrs_and_block()?; @@ -1905,11 +1912,11 @@ fn parse_fn_front_matter(&mut self) -> PResult<'a, FnHeader> { } let asyncness = respan(self.prev_span, asyncness); let unsafety = self.parse_unsafety(); - let (constness, unsafety, abi) = if is_const_fn { - (respan(const_span, Constness::Const), unsafety, Abi::default()) + let (constness, unsafety, ext) = if is_const_fn { + (respan(const_span, Constness::Const), unsafety, Extern::None) } else { - let abi = self.parse_extern_abi()?; - (respan(self.prev_span, Constness::NotConst), unsafety, abi) + let ext = self.parse_extern()?; + (respan(self.prev_span, Constness::NotConst), unsafety, ext) }; if !self.eat_keyword(kw::Fn) { // It is possible for `expect_one_of` to recover given the contents of @@ -1917,7 +1924,7 @@ fn parse_fn_front_matter(&mut self) -> PResult<'a, FnHeader> { // account for this. if !self.expect_one_of(&[], &[])? { unreachable!() } } - Ok(FnHeader { constness, unsafety, asyncness, abi }) + Ok(FnHeader { constness, unsafety, asyncness, ext }) } /// Parse the "signature", including the identifier, parameters, and generics of a function. diff --git a/src/librustc_parse/parser/mod.rs b/src/librustc_parse/parser/mod.rs index f62f0c9a268..2d05a696791 100644 --- a/src/librustc_parse/parser/mod.rs +++ b/src/librustc_parse/parser/mod.rs @@ -15,7 +15,7 @@ use crate::lexer::UnmatchedBrace; use syntax::ast::{ - self, Abi, DUMMY_NODE_ID, AttrStyle, Attribute, CrateSugar, Ident, + self, Abi, DUMMY_NODE_ID, AttrStyle, Attribute, CrateSugar, Extern, Ident, IsAsync, MacDelimiter, Mutability, StrStyle, Visibility, VisibilityKind, Unsafety, }; @@ -1212,23 +1212,20 @@ fn recover_incorrect_vis_restriction(&mut self) -> PResult<'a, ()> { } /// Parses `extern string_literal?`. - /// If `extern` is not found, the Rust ABI is used. - /// If `extern` is found and a `string_literal` does not follow, the C ABI is used. - fn parse_extern_abi(&mut self) -> PResult<'a, Abi> { + fn parse_extern(&mut self) -> PResult<'a, Extern> { Ok(if self.eat_keyword(kw::Extern) { - self.parse_opt_abi()? + Extern::from_abi(self.parse_opt_abi()?) } else { - Abi::default() + Extern::None }) } /// Parses a string literal as an ABI spec. - /// If one is not found, the "C" ABI is used. - fn parse_opt_abi(&mut self) -> PResult<'a, Abi> { - let span = if self.token.can_begin_literal_or_bool() { + fn parse_opt_abi(&mut self) -> PResult<'a, Option> { + if self.token.can_begin_literal_or_bool() { let ast::Lit { span, kind, .. } = self.parse_lit()?; match kind { - ast::LitKind::Str(symbol, _) => return Ok(Abi::new(symbol, span)), + ast::LitKind::Str(symbol, _) => return Ok(Some(Abi { symbol, span })), ast::LitKind::Err(_) => {} _ => { self.struct_span_err(span, "non-string ABI literal") @@ -1241,11 +1238,8 @@ fn parse_opt_abi(&mut self) -> PResult<'a, Abi> { .emit(); } } - span - } else { - self.prev_span - }; - Ok(Abi::new(sym::C, span)) + } + Ok(None) } /// We are parsing `async fn`. If we are on Rust 2015, emit an error. diff --git a/src/librustc_parse/parser/ty.rs b/src/librustc_parse/parser/ty.rs index 4c7d1006183..8e6bc29be52 100644 --- a/src/librustc_parse/parser/ty.rs +++ b/src/librustc_parse/parser/ty.rs @@ -287,7 +287,7 @@ fn parse_ty_bare_fn(&mut self, generic_params: Vec) -> PResult<'a, */ let unsafety = self.parse_unsafety(); - let abi = self.parse_extern_abi()?; + let ext = self.parse_extern()?; self.expect_keyword(kw::Fn)?; let cfg = ParamCfg { is_self_allowed: false, @@ -296,7 +296,7 @@ fn parse_ty_bare_fn(&mut self, generic_params: Vec) -> PResult<'a, }; let decl = self.parse_fn_decl(cfg, false)?; Ok(TyKind::BareFn(P(BareFnTy { - abi, + ext, unsafety, generic_params, decl, diff --git a/src/librustc_save_analysis/sig.rs b/src/librustc_save_analysis/sig.rs index 50dfac62024..255938a193c 100644 --- a/src/librustc_save_analysis/sig.rs +++ b/src/librustc_save_analysis/sig.rs @@ -30,9 +30,8 @@ use rls_data::{SigElement, Signature}; use rustc::hir::def::{Res, DefKind}; -use syntax::ast::{self, NodeId}; +use syntax::ast::{self, Extern, NodeId}; use syntax::print::pprust; -use syntax_pos::sym; pub fn item_signature(item: &ast::Item, scx: &SaveContext<'_, '_>) -> Option { if !scx.config.signatures { @@ -157,9 +156,11 @@ fn text_sig(text: String) -> Signature { } } -fn push_abi(text: &mut String, abi: ast::Abi) { - if abi.symbol != sym::Rust { - text.push_str(&format!("extern \"{}\" ", abi.symbol)); +fn push_extern(text: &mut String, ext: Extern) { + match ext { + Extern::None => {} + Extern::Implicit => text.push_str("extern "), + Extern::Explicit(abi) => text.push_str(&format!("extern \"{}\" ", abi.symbol)), } } @@ -237,7 +238,7 @@ fn make(&self, offset: usize, _parent_id: Option, scx: &SaveContext<'_, if f.unsafety == ast::Unsafety::Unsafe { text.push_str("unsafe "); } - push_abi(&mut text, f.abi); + push_extern(&mut text, f.ext); text.push_str("fn("); let mut defs = vec![]; @@ -387,7 +388,7 @@ fn make(&self, offset: usize, _parent_id: Option, scx: &SaveContext<'_, if header.unsafety == ast::Unsafety::Unsafe { text.push_str("unsafe "); } - push_abi(&mut text, header.abi); + push_extern(&mut text, header.ext); text.push_str("fn "); let mut sig = name_and_generics(text, offset, generics, self.id, self.ident, scx)?; @@ -936,7 +937,7 @@ fn make_method_signature( if m.header.unsafety == ast::Unsafety::Unsafe { text.push_str("unsafe "); } - push_abi(&mut text, m.header.abi); + push_extern(&mut text, m.header.ext); text.push_str("fn "); let mut sig = name_and_generics(text, 0, generics, id, ident, scx)?; diff --git a/src/libsyntax/ast.rs b/src/libsyntax/ast.rs index d358efbe543..575795758ae 100644 --- a/src/libsyntax/ast.rs +++ b/src/libsyntax/ast.rs @@ -1745,7 +1745,7 @@ pub struct Ty { #[derive(Clone, RustcEncodable, RustcDecodable, Debug)] pub struct BareFnTy { pub unsafety: Unsafety, - pub abi: Abi, + pub ext: Extern, pub generic_params: Vec, pub decl: P, } @@ -2128,7 +2128,7 @@ pub struct Mod { /// E.g., `extern { .. }` or `extern C { .. }`. #[derive(Clone, RustcEncodable, RustcDecodable, Debug)] pub struct ForeignMod { - pub abi: Abi, + pub abi: Option, pub items: Vec, } @@ -2420,15 +2420,20 @@ pub struct Abi { pub span: Span, } -impl Abi { - pub fn new(symbol: Symbol, span: Span) -> Self { - Self { symbol, span } - } +/// `extern` qualifier on a function item or function type. +#[derive(Clone, Copy, RustcEncodable, RustcDecodable, Debug)] +pub enum Extern { + None, + Implicit, + Explicit(Abi), } -impl Default for Abi { - fn default() -> Self { - Self::new(sym::Rust, DUMMY_SP) +impl Extern { + pub fn from_abi(abi: Option) -> Extern { + match abi { + Some(abi) => Extern::Explicit(abi), + None => Extern::Implicit, + } } } @@ -2441,7 +2446,7 @@ pub struct FnHeader { pub unsafety: Unsafety, pub asyncness: Spanned, pub constness: Spanned, - pub abi: Abi, + pub ext: Extern, } impl Default for FnHeader { @@ -2450,7 +2455,7 @@ fn default() -> FnHeader { unsafety: Unsafety::Normal, asyncness: dummy_spanned(IsAsync::NotAsync), constness: dummy_spanned(Constness::NotConst), - abi: Abi::default(), + ext: Extern::None, } } } diff --git a/src/libsyntax/feature_gate/check.rs b/src/libsyntax/feature_gate/check.rs index bd836eee42a..d90fa9addf7 100644 --- a/src/libsyntax/feature_gate/check.rs +++ b/src/libsyntax/feature_gate/check.rs @@ -258,6 +258,12 @@ fn check_abi(&self, abi: ast::Abi) { } } + fn check_extern(&self, ext: ast::Extern) { + if let ast::Extern::Explicit(abi) = ext { + self.check_abi(abi); + } + } + fn maybe_report_invalid_custom_discriminants(&self, variants: &[ast::Variant]) { let has_fields = variants.iter().any(|variant| match variant.data { VariantData::Tuple(..) | VariantData::Struct(..) => true, @@ -388,7 +394,9 @@ fn visit_name(&mut self, sp: Span, name: ast::Name) { fn visit_item(&mut self, i: &'a ast::Item) { match i.kind { ast::ItemKind::ForeignMod(ref foreign_module) => { - self.check_abi(foreign_module.abi); + if let Some(abi) = foreign_module.abi { + self.check_abi(abi); + } } ast::ItemKind::Fn(..) => { @@ -511,7 +519,7 @@ fn visit_foreign_item(&mut self, i: &'a ast::ForeignItem) { fn visit_ty(&mut self, ty: &'a ast::Ty) { match ty.kind { ast::TyKind::BareFn(ref bare_fn_ty) => { - self.check_abi(bare_fn_ty.abi); + self.check_extern(bare_fn_ty.ext); } ast::TyKind::Never => { gate_feature_post!(&self, never_type, ty.span, @@ -605,7 +613,7 @@ fn visit_fn(&mut self, // Stability of const fn methods are covered in // `visit_trait_item` and `visit_impl_item` below; this is // because default methods don't pass through this point. - self.check_abi(header.abi); + self.check_extern(header.ext); } if fn_decl.c_variadic() { @@ -639,7 +647,7 @@ fn visit_trait_item(&mut self, ti: &'a ast::TraitItem) { match ti.kind { ast::TraitItemKind::Method(ref sig, ref block) => { if block.is_none() { - self.check_abi(sig.header.abi); + self.check_extern(sig.header.ext); } if sig.decl.c_variadic() { gate_feature_post!(&self, c_variadic, ti.span, diff --git a/src/libsyntax/mut_visit.rs b/src/libsyntax/mut_visit.rs index f4ef993edb9..da3c885b860 100644 --- a/src/libsyntax/mut_visit.rs +++ b/src/libsyntax/mut_visit.rs @@ -441,7 +441,7 @@ pub fn noop_visit_ty(ty: &mut P, vis: &mut T) { vis.visit_mt(mt); } TyKind::BareFn(bft) => { - let BareFnTy { unsafety: _, abi: _, generic_params, decl } = bft.deref_mut(); + let BareFnTy { unsafety: _, ext: _, generic_params, decl } = bft.deref_mut(); generic_params.flat_map_in_place(|param| vis.flat_map_generic_param(param)); vis.visit_fn_decl(decl); } @@ -974,7 +974,7 @@ pub fn noop_flat_map_impl_item(mut item: ImplItem, visitor: &mut } pub fn noop_visit_fn_header(header: &mut FnHeader, vis: &mut T) { - let FnHeader { unsafety: _, asyncness, constness: _, abi: _ } = header; + let FnHeader { unsafety: _, asyncness, constness: _, ext: _ } = header; vis.visit_asyncness(&mut asyncness.node); } diff --git a/src/libsyntax/print/pprust.rs b/src/libsyntax/print/pprust.rs index ef65a744e83..de28bd6cf83 100644 --- a/src/libsyntax/print/pprust.rs +++ b/src/libsyntax/print/pprust.rs @@ -1013,7 +1013,7 @@ pub fn print_type(&mut self, ty: &ast::Ty) { self.pclose(); } ast::TyKind::BareFn(ref f) => { - self.print_ty_fn(f.abi, + self.print_ty_fn(f.ext, f.unsafety, &f.decl, None, @@ -1232,7 +1232,9 @@ fn print_associated_type(&mut self, } ast::ItemKind::ForeignMod(ref nmod) => { self.head("extern"); - self.print_abi(nmod.abi); + if let Some(abi) = nmod.abi { + self.print_abi(abi); + } self.bopen(); self.print_foreign_mod(nmod, &item.attrs); self.bclose(item.span); @@ -2805,7 +2807,7 @@ pub fn print_mutability(&mut self, mutbl: ast::Mutability) { } crate fn print_ty_fn(&mut self, - abi: ast::Abi, + ext: ast::Extern, unsafety: ast::Unsafety, decl: &ast::FnDecl, name: Option, @@ -2825,7 +2827,7 @@ pub fn print_mutability(&mut self, mutbl: ast::Mutability) { span: syntax_pos::DUMMY_SP, }; self.print_fn(decl, - ast::FnHeader { unsafety, abi, ..ast::FnHeader::default() }, + ast::FnHeader { unsafety, ext, ..ast::FnHeader::default() }, name, &generics, &source_map::dummy_spanned(ast::VisibilityKind::Inherited)); @@ -2866,9 +2868,15 @@ pub fn print_mutability(&mut self, mutbl: ast::Mutability) { self.print_asyncness(header.asyncness.node); self.print_unsafety(header.unsafety); - if header.abi.symbol != sym::Rust { - self.word_nbsp("extern"); - self.print_abi(header.abi); + match header.ext { + ast::Extern::None => {} + ast::Extern::Implicit => { + self.word_nbsp("extern"); + } + ast::Extern::Explicit(abi) => { + self.word_nbsp("extern"); + self.print_abi(abi); + } } self.s.word("fn") diff --git a/src/libsyntax_ext/deriving/generic/mod.rs b/src/libsyntax_ext/deriving/generic/mod.rs index b24306def74..b6bf2f88161 100644 --- a/src/libsyntax_ext/deriving/generic/mod.rs +++ b/src/libsyntax_ext/deriving/generic/mod.rs @@ -182,7 +182,7 @@ use std::vec; use rustc_data_structures::thin_vec::ThinVec; -use syntax::ast::{self, Abi, BinOpKind, EnumDef, Expr, Generics, Ident, PatKind}; +use syntax::ast::{self, BinOpKind, EnumDef, Expr, Generics, Ident, PatKind}; use syntax::ast::{VariantData, GenericParamKind, GenericArg}; use syntax::attr; use syntax::source_map::respan; @@ -737,7 +737,6 @@ fn expand_struct_def(&self, self, type_ident, generics, - sym::Rust, explicit_self, tys, body) @@ -792,7 +791,6 @@ fn expand_enum_def(&self, self, type_ident, generics, - sym::Rust, explicit_self, tys, body) @@ -918,7 +916,6 @@ fn create_method(&self, trait_: &TraitDef<'_>, type_ident: Ident, generics: &Generics, - abi: Symbol, explicit_self: Option, arg_types: Vec<(Ident, P)>, body: P) @@ -953,7 +950,7 @@ fn create_method(&self, let sig = ast::FnSig { header: ast::FnHeader { unsafety, - abi: Abi::new(abi, trait_lo_sp), + ext: ast::Extern::None, ..ast::FnHeader::default() }, decl: fn_decl, diff --git a/src/test/ui/proc-macro/span-preservation.rs b/src/test/ui/proc-macro/span-preservation.rs index 55835cb88f4..8b8e12fcba6 100644 --- a/src/test/ui/proc-macro/span-preservation.rs +++ b/src/test/ui/proc-macro/span-preservation.rs @@ -1,9 +1,8 @@ -//~ ERROR mismatched types -// aux-build:test-macros.rs - // For each of these, we should get the appropriate type mismatch error message, // and the function should be echoed. +// aux-build:test-macros.rs + #[macro_use] extern crate test_macros; @@ -35,12 +34,9 @@ struct Bar { let y = Foo { a: 10, b: 10isize }; //~ ERROR has no field named `b` } -// FIXME: This doesn't work at the moment. See the one below. The pretty-printer -// injects a "C" between `extern` and `fn` which causes a "probably_eq" -// `TokenStream` mismatch. The lack of `"C"` should be preserved in the AST. #[recollect_attr] extern fn bar() { - 0 + 0 //~ ERROR mismatched types } #[recollect_attr] diff --git a/src/test/ui/proc-macro/span-preservation.stderr b/src/test/ui/proc-macro/span-preservation.stderr index 0290f4b2cc9..9e9271f529c 100644 --- a/src/test/ui/proc-macro/span-preservation.stderr +++ b/src/test/ui/proc-macro/span-preservation.stderr @@ -1,10 +1,5 @@ error[E0308]: mismatched types - | - = note: expected type `()` - found type `{integer}` - -error[E0308]: mismatched types - --> $DIR/span-preservation.rs:12:20 + --> $DIR/span-preservation.rs:11:20 | LL | let x: usize = "hello"; | ^^^^^^^ expected usize, found reference @@ -13,7 +8,7 @@ LL | let x: usize = "hello"; found type `&'static str` error[E0308]: mismatched types - --> $DIR/span-preservation.rs:18:29 + --> $DIR/span-preservation.rs:17:29 | LL | fn b(x: Option) -> usize { | ----- expected `usize` because of return type @@ -22,13 +17,13 @@ LL | Some(x) => { return x }, | ^ expected usize, found isize error[E0308]: mismatched types - --> $DIR/span-preservation.rs:34:22 + --> $DIR/span-preservation.rs:33:22 | LL | let x = Foo { a: 10isize }; | ^^^^^^^ expected usize, found isize error[E0560]: struct `c::Foo` has no field named `b` - --> $DIR/span-preservation.rs:35:26 + --> $DIR/span-preservation.rs:34:26 | LL | let y = Foo { a: 10, b: 10isize }; | ^ `c::Foo` does not have this field @@ -36,7 +31,18 @@ LL | let y = Foo { a: 10, b: 10isize }; = note: available fields are: `a` error[E0308]: mismatched types - --> $DIR/span-preservation.rs:48:5 + --> $DIR/span-preservation.rs:39:5 + | +LL | extern fn bar() { + | - possibly return type missing here? +LL | 0 + | ^ expected (), found integer + | + = note: expected type `()` + found type `{integer}` + +error[E0308]: mismatched types + --> $DIR/span-preservation.rs:44:5 | LL | extern "C" fn baz() { | - possibly return type missing here? -- 2.44.0