Auto merge of #94584 - pnkfelix:inject-use-suggestion-sites, r=ekuber
More robust fallback for `use` suggestion Our old way to suggest where to add `use`s would first look for pre-existing `use`s in the relevant crate/module, and if there are *no* uses, it would fallback on trying to use another item as the basis for the suggestion. But this was fragile, as illustrated in issue #87613 This PR instead identifies span of the first token after any inner attributes, and uses *that* as the fallback for the `use` suggestion. Fix #87613
This commit is contained in:
commit
95561b336c
27 changed files with 295 additions and 106 deletions
|
@ -67,7 +67,7 @@ impl Annotatable {
|
|||
Annotatable::Param(ref p) => p.span,
|
||||
Annotatable::FieldDef(ref sf) => sf.span,
|
||||
Annotatable::Variant(ref v) => v.span,
|
||||
Annotatable::Crate(ref c) => c.span,
|
||||
Annotatable::Crate(ref c) => c.spans.inner_span,
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -12,8 +12,8 @@ use rustc_ast::token;
|
|||
use rustc_ast::tokenstream::TokenStream;
|
||||
use rustc_ast::visit::{self, AssocCtxt, Visitor};
|
||||
use rustc_ast::{AssocItemKind, AstLike, AstLikeWrapper, AttrStyle, ExprKind, ForeignItemKind};
|
||||
use rustc_ast::{Inline, ItemKind, MacArgs, MacStmtStyle, MetaItemKind, ModKind, NestedMetaItem};
|
||||
use rustc_ast::{NodeId, PatKind, StmtKind, TyKind};
|
||||
use rustc_ast::{Inline, ItemKind, MacArgs, MacStmtStyle, MetaItemKind, ModKind};
|
||||
use rustc_ast::{NestedMetaItem, NodeId, PatKind, StmtKind, TyKind};
|
||||
use rustc_ast_pretty::pprust;
|
||||
use rustc_data_structures::map_in_place::MapInPlace;
|
||||
use rustc_data_structures::sync::Lrc;
|
||||
|
@ -364,7 +364,7 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
|
|||
}
|
||||
|
||||
pub fn expand_crate(&mut self, krate: ast::Crate) -> ast::Crate {
|
||||
let file_path = match self.cx.source_map().span_to_filename(krate.span) {
|
||||
let file_path = match self.cx.source_map().span_to_filename(krate.spans.inner_span) {
|
||||
FileName::Real(name) => name
|
||||
.into_local_path()
|
||||
.expect("attempting to resolve a file path in an external file"),
|
||||
|
@ -1091,7 +1091,7 @@ impl InvocationCollectorNode for P<ast::Item> {
|
|||
ModKind::Unloaded => {
|
||||
// We have an outline `mod foo;` so we need to parse the file.
|
||||
let old_attrs_len = attrs.len();
|
||||
let ParsedExternalMod { items, inner_span, file_path, dir_path, dir_ownership } =
|
||||
let ParsedExternalMod { items, spans, file_path, dir_path, dir_ownership } =
|
||||
parse_external_mod(
|
||||
&ecx.sess,
|
||||
ident,
|
||||
|
@ -1112,7 +1112,7 @@ impl InvocationCollectorNode for P<ast::Item> {
|
|||
);
|
||||
}
|
||||
|
||||
*mod_kind = ModKind::Loaded(items, Inline::No, inner_span);
|
||||
*mod_kind = ModKind::Loaded(items, Inline::No, spans);
|
||||
node.attrs = attrs;
|
||||
if node.attrs.len() > old_attrs_len {
|
||||
// If we loaded an out-of-line module and added some inner attributes,
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use crate::base::ModuleData;
|
||||
use rustc_ast::ptr::P;
|
||||
use rustc_ast::{token, Attribute, Inline, Item};
|
||||
use rustc_ast::{token, Attribute, Inline, Item, ModSpans};
|
||||
use rustc_errors::{struct_span_err, DiagnosticBuilder, ErrorGuaranteed};
|
||||
use rustc_parse::new_parser_from_file;
|
||||
use rustc_parse::validate_attr;
|
||||
|
@ -28,7 +28,7 @@ pub struct ModulePathSuccess {
|
|||
|
||||
crate struct ParsedExternalMod {
|
||||
pub items: Vec<P<Item>>,
|
||||
pub inner_span: Span,
|
||||
pub spans: ModSpans,
|
||||
pub file_path: PathBuf,
|
||||
pub dir_path: PathBuf,
|
||||
pub dir_ownership: DirOwnership,
|
||||
|
@ -69,13 +69,13 @@ crate fn parse_external_mod(
|
|||
(items, inner_span, mp.file_path)
|
||||
};
|
||||
// (1) ...instead, we return a dummy module.
|
||||
let (items, inner_span, file_path) =
|
||||
let (items, spans, file_path) =
|
||||
result.map_err(|err| err.report(sess, span)).unwrap_or_default();
|
||||
|
||||
// Extract the directory path for submodules of the module.
|
||||
let dir_path = file_path.parent().unwrap_or(&file_path).to_owned();
|
||||
|
||||
ParsedExternalMod { items, inner_span, file_path, dir_path, dir_ownership }
|
||||
ParsedExternalMod { items, spans, file_path, dir_path, dir_ownership }
|
||||
}
|
||||
|
||||
crate fn mod_dir_path(
|
||||
|
|
|
@ -49,7 +49,7 @@ pub fn placeholder(
|
|||
AstFragmentKind::Crate => AstFragment::Crate(ast::Crate {
|
||||
attrs: Default::default(),
|
||||
items: Default::default(),
|
||||
span,
|
||||
spans: ast::ModSpans { inner_span: span, ..Default::default() },
|
||||
id,
|
||||
is_placeholder: true,
|
||||
}),
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue