mirror of
https://github.com/rust-lang/rust-analyzer.git
synced 2025-09-27 12:29:21 +00:00
Generally optimize diagnostics performance
This commit is contained in:
parent
94e38261b3
commit
531a270d91
15 changed files with 115 additions and 85 deletions
|
@ -320,13 +320,11 @@ pub fn diagnostics(
|
|||
let module = sema.file_to_module_def(file_id);
|
||||
|
||||
let ctx = DiagnosticsContext { config, sema, resolve };
|
||||
if module.is_none() {
|
||||
handlers::unlinked_file::unlinked_file(&ctx, &mut res, file_id);
|
||||
}
|
||||
|
||||
let mut diags = Vec::new();
|
||||
if let Some(m) = module {
|
||||
m.diagnostics(db, &mut diags, config.style_lints);
|
||||
match module {
|
||||
Some(m) => m.diagnostics(db, &mut diags, config.style_lints),
|
||||
None => handlers::unlinked_file::unlinked_file(&ctx, &mut res, file_id),
|
||||
}
|
||||
|
||||
for diag in diags {
|
||||
|
@ -409,6 +407,11 @@ pub fn diagnostics(
|
|||
res.push(d)
|
||||
}
|
||||
|
||||
res.retain(|d| {
|
||||
!(ctx.config.disabled.contains(d.code.as_str())
|
||||
|| ctx.config.disable_experimental && d.experimental)
|
||||
});
|
||||
|
||||
let mut diagnostics_of_range = res
|
||||
.iter_mut()
|
||||
.filter_map(|it| {
|
||||
|
@ -421,9 +424,14 @@ pub fn diagnostics(
|
|||
})
|
||||
.collect::<FxHashMap<_, _>>();
|
||||
|
||||
if diagnostics_of_range.is_empty() {
|
||||
return res;
|
||||
}
|
||||
|
||||
let mut rustc_stack: FxHashMap<String, Vec<Severity>> = FxHashMap::default();
|
||||
let mut clippy_stack: FxHashMap<String, Vec<Severity>> = FxHashMap::default();
|
||||
|
||||
// FIXME: This becomes quite expensive for big files
|
||||
handle_lint_attributes(
|
||||
&ctx.sema,
|
||||
parse.syntax(),
|
||||
|
@ -432,11 +440,7 @@ pub fn diagnostics(
|
|||
&mut diagnostics_of_range,
|
||||
);
|
||||
|
||||
res.retain(|d| {
|
||||
d.severity != Severity::Allow
|
||||
&& !ctx.config.disabled.contains(d.code.as_str())
|
||||
&& !(ctx.config.disable_experimental && d.experimental)
|
||||
});
|
||||
res.retain(|d| d.severity != Severity::Allow);
|
||||
|
||||
res
|
||||
}
|
||||
|
@ -476,6 +480,7 @@ fn handle_lint_attributes(
|
|||
clippy_stack: &mut FxHashMap<String, Vec<Severity>>,
|
||||
diagnostics_of_range: &mut FxHashMap<InFile<SyntaxNode>, &mut Diagnostic>,
|
||||
) {
|
||||
let _g = tracing::span!(tracing::Level::INFO, "handle_lint_attributes").entered();
|
||||
let file_id = sema.hir_file_for(root);
|
||||
let preorder = root.preorder();
|
||||
for ev in preorder {
|
||||
|
@ -486,24 +491,24 @@ fn handle_lint_attributes(
|
|||
stack.push(severity);
|
||||
});
|
||||
}
|
||||
if let Some(x) =
|
||||
if let Some(it) =
|
||||
diagnostics_of_range.get_mut(&InFile { file_id, value: node.clone() })
|
||||
{
|
||||
const EMPTY_LINTS: &[&str] = &[];
|
||||
let (names, stack) = match x.code {
|
||||
let (names, stack) = match it.code {
|
||||
DiagnosticCode::RustcLint(name) => (
|
||||
RUSTC_LINT_GROUPS_DICT.get(name).map_or(EMPTY_LINTS, |x| &**x),
|
||||
RUSTC_LINT_GROUPS_DICT.get(name).map_or(EMPTY_LINTS, |it| &**it),
|
||||
&mut *rustc_stack,
|
||||
),
|
||||
DiagnosticCode::Clippy(name) => (
|
||||
CLIPPY_LINT_GROUPS_DICT.get(name).map_or(EMPTY_LINTS, |x| &**x),
|
||||
CLIPPY_LINT_GROUPS_DICT.get(name).map_or(EMPTY_LINTS, |it| &**it),
|
||||
&mut *clippy_stack,
|
||||
),
|
||||
_ => continue,
|
||||
};
|
||||
for &name in names {
|
||||
if let Some(s) = stack.get(name).and_then(|x| x.last()) {
|
||||
x.severity = *s;
|
||||
if let Some(s) = stack.get(name).and_then(|it| it.last()) {
|
||||
it.severity = *s;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -571,8 +576,8 @@ fn parse_lint_attribute(
|
|||
if let Some(lint) = lint.as_single_name_ref() {
|
||||
job(rustc_stack.entry(lint.to_string()).or_default(), severity);
|
||||
}
|
||||
if let Some(tool) = lint.qualifier().and_then(|x| x.as_single_name_ref()) {
|
||||
if let Some(name_ref) = &lint.segment().and_then(|x| x.name_ref()) {
|
||||
if let Some(tool) = lint.qualifier().and_then(|it| it.as_single_name_ref()) {
|
||||
if let Some(name_ref) = &lint.segment().and_then(|it| it.name_ref()) {
|
||||
if tool.to_string() == "clippy" {
|
||||
job(clippy_stack.entry(name_ref.to_string()).or_default(), severity);
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue