Rollup merge of #132357 - m-ou-se:explicit-abi, r=compiler-errors
Improve missing_abi lint This is for the migration lint for https://github.com/rust-lang/rfcs/pull/3722 It is not yet marked as an edition migration lint, because `Edition2027` doesn't exist yet. The lint now includes a machine applicable suggestion: ``` warning: extern declarations without an explicit ABI are deprecated --> src/main.rs:3:1 | 3 | extern fn a() {} | ^^^^^^ help: explicitly specify the C ABI: `extern "C"` | ```
This commit is contained in:
commit
6b0c8cfedc
@ -2810,6 +2810,8 @@ pub struct ModSpans {
|
|||||||
/// E.g., `extern { .. }` or `extern "C" { .. }`.
|
/// E.g., `extern { .. }` or `extern "C" { .. }`.
|
||||||
#[derive(Clone, Encodable, Decodable, Debug)]
|
#[derive(Clone, Encodable, Decodable, Debug)]
|
||||||
pub struct ForeignMod {
|
pub struct ForeignMod {
|
||||||
|
/// Span of the `extern` keyword.
|
||||||
|
pub extern_span: Span,
|
||||||
/// `unsafe` keyword accepted syntactically for macro DSLs, but not
|
/// `unsafe` keyword accepted syntactically for macro DSLs, but not
|
||||||
/// semantically by Rust.
|
/// semantically by Rust.
|
||||||
pub safety: Safety,
|
pub safety: Safety,
|
||||||
|
@ -525,7 +525,7 @@ pub fn walk_ty<T: MutVisitor>(vis: &mut T, ty: &mut P<Ty>) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn walk_foreign_mod<T: MutVisitor>(vis: &mut T, foreign_mod: &mut ForeignMod) {
|
fn walk_foreign_mod<T: MutVisitor>(vis: &mut T, foreign_mod: &mut ForeignMod) {
|
||||||
let ForeignMod { safety, abi: _, items } = foreign_mod;
|
let ForeignMod { extern_span: _, safety, abi: _, items } = foreign_mod;
|
||||||
visit_safety(vis, safety);
|
visit_safety(vis, safety);
|
||||||
items.flat_map_in_place(|item| vis.flat_map_foreign_item(item));
|
items.flat_map_in_place(|item| vis.flat_map_foreign_item(item));
|
||||||
}
|
}
|
||||||
|
@ -366,7 +366,7 @@ fn walk<'a, V: Visitor<'a>>(
|
|||||||
}
|
}
|
||||||
ModKind::Unloaded => {}
|
ModKind::Unloaded => {}
|
||||||
},
|
},
|
||||||
ItemKind::ForeignMod(ForeignMod { safety: _, abi: _, items }) => {
|
ItemKind::ForeignMod(ForeignMod { extern_span: _, safety: _, abi: _, items }) => {
|
||||||
walk_list!(visitor, visit_foreign_item, items);
|
walk_list!(visitor, visit_foreign_item, items);
|
||||||
}
|
}
|
||||||
ItemKind::GlobalAsm(asm) => try_visit!(visitor.visit_inline_asm(asm)),
|
ItemKind::GlobalAsm(asm) => try_visit!(visitor.visit_inline_asm(asm)),
|
||||||
|
@ -677,9 +677,8 @@ fn visit_ty_common(&mut self, ty: &'a Ty) {
|
|||||||
Self::check_decl_no_pat(&bfty.decl, |span, _, _| {
|
Self::check_decl_no_pat(&bfty.decl, |span, _, _| {
|
||||||
self.dcx().emit_err(errors::PatternFnPointer { span });
|
self.dcx().emit_err(errors::PatternFnPointer { span });
|
||||||
});
|
});
|
||||||
if let Extern::Implicit(_) = bfty.ext {
|
if let Extern::Implicit(extern_span) = bfty.ext {
|
||||||
let sig_span = self.sess.source_map().next_point(ty.span.shrink_to_lo());
|
self.maybe_lint_missing_abi(extern_span, ty.id);
|
||||||
self.maybe_lint_missing_abi(sig_span, ty.id);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TyKind::TraitObject(bounds, ..) => {
|
TyKind::TraitObject(bounds, ..) => {
|
||||||
@ -953,7 +952,7 @@ fn visit_item(&mut self, item: &'a Item) {
|
|||||||
walk_list!(self, visit_attribute, &item.attrs);
|
walk_list!(self, visit_attribute, &item.attrs);
|
||||||
return; // Avoid visiting again.
|
return; // Avoid visiting again.
|
||||||
}
|
}
|
||||||
ItemKind::ForeignMod(ForeignMod { abi, safety, .. }) => {
|
ItemKind::ForeignMod(ForeignMod { extern_span, abi, safety, .. }) => {
|
||||||
self.with_in_extern_mod(*safety, |this| {
|
self.with_in_extern_mod(*safety, |this| {
|
||||||
let old_item = mem::replace(&mut this.extern_mod, Some(item.span));
|
let old_item = mem::replace(&mut this.extern_mod, Some(item.span));
|
||||||
this.visibility_not_permitted(
|
this.visibility_not_permitted(
|
||||||
@ -977,7 +976,7 @@ fn visit_item(&mut self, item: &'a Item) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if abi.is_none() {
|
if abi.is_none() {
|
||||||
this.maybe_lint_missing_abi(item.span, item.id);
|
this.maybe_lint_missing_abi(*extern_span, item.id);
|
||||||
}
|
}
|
||||||
visit::walk_item(this, item);
|
visit::walk_item(this, item);
|
||||||
this.extern_mod = old_item;
|
this.extern_mod = old_item;
|
||||||
@ -1350,13 +1349,13 @@ fn visit_fn(&mut self, fk: FnKind<'a>, span: Span, id: NodeId) {
|
|||||||
if let FnKind::Fn(
|
if let FnKind::Fn(
|
||||||
_,
|
_,
|
||||||
_,
|
_,
|
||||||
FnSig { span: sig_span, header: FnHeader { ext: Extern::Implicit(_), .. }, .. },
|
FnSig { header: FnHeader { ext: Extern::Implicit(extern_span), .. }, .. },
|
||||||
_,
|
_,
|
||||||
_,
|
_,
|
||||||
_,
|
_,
|
||||||
) = fk
|
) = fk
|
||||||
{
|
{
|
||||||
self.maybe_lint_missing_abi(*sig_span, id);
|
self.maybe_lint_missing_abi(*extern_span, id);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Functions without bodies cannot have patterns.
|
// Functions without bodies cannot have patterns.
|
||||||
|
@ -268,7 +268,7 @@ lint_extern_crate_not_idiomatic = `extern crate` is not idiomatic in the new edi
|
|||||||
|
|
||||||
lint_extern_without_abi = extern declarations without an explicit ABI are deprecated
|
lint_extern_without_abi = extern declarations without an explicit ABI are deprecated
|
||||||
.label = ABI should be specified here
|
.label = ABI should be specified here
|
||||||
.help = the default ABI is {$default_abi}
|
.suggestion = explicitly specify the {$default_abi} ABI
|
||||||
|
|
||||||
lint_for_loops_over_fallibles =
|
lint_for_loops_over_fallibles =
|
||||||
for loop over {$article} `{$ref_prefix}{$ty}`. This is more readably written as an `if let` statement
|
for loop over {$article} `{$ref_prefix}{$ty}`. This is more readably written as an `if let` statement
|
||||||
|
@ -2738,11 +2738,9 @@ pub(crate) struct PatternsInFnsWithoutBodySub {
|
|||||||
|
|
||||||
#[derive(LintDiagnostic)]
|
#[derive(LintDiagnostic)]
|
||||||
#[diag(lint_extern_without_abi)]
|
#[diag(lint_extern_without_abi)]
|
||||||
#[help]
|
|
||||||
pub(crate) struct MissingAbi {
|
pub(crate) struct MissingAbi {
|
||||||
#[label]
|
#[suggestion(code = "extern \"{default_abi}\"", applicability = "machine-applicable")]
|
||||||
pub span: Span,
|
pub span: Span,
|
||||||
|
|
||||||
pub default_abi: &'static str,
|
pub default_abi: &'static str,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1194,6 +1194,7 @@ fn parse_item_foreign_mod(
|
|||||||
attrs: &mut AttrVec,
|
attrs: &mut AttrVec,
|
||||||
mut safety: Safety,
|
mut safety: Safety,
|
||||||
) -> PResult<'a, ItemInfo> {
|
) -> PResult<'a, ItemInfo> {
|
||||||
|
let extern_span = self.prev_token.uninterpolated_span();
|
||||||
let abi = self.parse_abi(); // ABI?
|
let abi = self.parse_abi(); // ABI?
|
||||||
// FIXME: This recovery should be tested better.
|
// FIXME: This recovery should be tested better.
|
||||||
if safety == Safety::Default
|
if safety == Safety::Default
|
||||||
@ -1205,6 +1206,7 @@ fn parse_item_foreign_mod(
|
|||||||
let _ = self.eat_keyword(kw::Unsafe);
|
let _ = self.eat_keyword(kw::Unsafe);
|
||||||
}
|
}
|
||||||
let module = ast::ForeignMod {
|
let module = ast::ForeignMod {
|
||||||
|
extern_span,
|
||||||
safety,
|
safety,
|
||||||
abi,
|
abi,
|
||||||
items: self.parse_item_list(attrs, |p| p.parse_foreign_item(ForceCollect::No))?,
|
items: self.parse_item_list(attrs, |p| p.parse_foreign_item(ForceCollect::No))?,
|
||||||
|
@ -2,9 +2,8 @@ error: extern declarations without an explicit ABI are deprecated
|
|||||||
--> $DIR/cli-lint-override.rs:12:1
|
--> $DIR/cli-lint-override.rs:12:1
|
||||||
|
|
|
|
||||||
LL | extern fn foo() {}
|
LL | extern fn foo() {}
|
||||||
| ^^^^^^^^^^^^^^^ ABI should be specified here
|
| ^^^^^^ help: explicitly specify the C ABI: `extern "C"`
|
||||||
|
|
|
|
||||||
= help: the default ABI is C
|
|
||||||
= note: requested on the command line with `-F missing-abi`
|
= note: requested on the command line with `-F missing-abi`
|
||||||
|
|
||||||
error: aborting due to 1 previous error
|
error: aborting due to 1 previous error
|
||||||
|
@ -2,9 +2,8 @@ warning: extern declarations without an explicit ABI are deprecated
|
|||||||
--> $DIR/cli-lint-override.rs:12:1
|
--> $DIR/cli-lint-override.rs:12:1
|
||||||
|
|
|
|
||||||
LL | extern fn foo() {}
|
LL | extern fn foo() {}
|
||||||
| ^^^^^^^^^^^^^^^ ABI should be specified here
|
| ^^^^^^ help: explicitly specify the C ABI: `extern "C"`
|
||||||
|
|
|
|
||||||
= help: the default ABI is C
|
|
||||||
= note: requested on the command line with `--force-warn missing-abi`
|
= note: requested on the command line with `--force-warn missing-abi`
|
||||||
|
|
||||||
warning: 1 warning emitted
|
warning: 1 warning emitted
|
||||||
|
@ -2,9 +2,8 @@ error: extern declarations without an explicit ABI are deprecated
|
|||||||
--> $DIR/cli-lint-override.rs:12:1
|
--> $DIR/cli-lint-override.rs:12:1
|
||||||
|
|
|
|
||||||
LL | extern fn foo() {}
|
LL | extern fn foo() {}
|
||||||
| ^^^^^^^^^^^^^^^ ABI should be specified here
|
| ^^^^^^ help: explicitly specify the C ABI: `extern "C"`
|
||||||
|
|
|
|
||||||
= help: the default ABI is C
|
|
||||||
= note: requested on the command line with `-D missing-abi`
|
= note: requested on the command line with `-D missing-abi`
|
||||||
|
|
||||||
error: aborting due to 1 previous error
|
error: aborting due to 1 previous error
|
||||||
|
Loading…
Reference in New Issue
Block a user