From 0b95bed83fc8db897f54b350168567f14527e8de Mon Sep 17 00:00:00 2001 From: Paul Daniel Faria Date: Sat, 23 May 2020 17:49:53 -0400 Subject: Add unsafe diagnostics and unsafe highlighting --- crates/ra_hir/src/code_model.rs | 5 +++- crates/ra_hir/src/diagnostics.rs | 50 ++++++++++++++++++++++++++++++++++++++++ 2 files changed, 54 insertions(+), 1 deletion(-) (limited to 'crates/ra_hir') diff --git a/crates/ra_hir/src/code_model.rs b/crates/ra_hir/src/code_model.rs index a379b9f49..131180a63 100644 --- a/crates/ra_hir/src/code_model.rs +++ b/crates/ra_hir/src/code_model.rs @@ -36,6 +36,7 @@ use rustc_hash::FxHashSet; use crate::{ db::{DefDatabase, HirDatabase}, + diagnostics::UnsafeValidator, has_source::HasSource, CallableDef, HirDisplay, InFile, Name, }; @@ -677,7 +678,9 @@ impl Function { let _p = profile("Function::diagnostics"); let infer = db.infer(self.id.into()); infer.add_diagnostics(db, self.id, sink); - let mut validator = ExprValidator::new(self.id, infer, sink); + let mut validator = ExprValidator::new(self.id, infer.clone(), sink); + validator.validate_body(db); + let mut validator = UnsafeValidator::new(&self, infer, sink); validator.validate_body(db); } } diff --git a/crates/ra_hir/src/diagnostics.rs b/crates/ra_hir/src/diagnostics.rs index c82883d0c..562f3fe5c 100644 --- a/crates/ra_hir/src/diagnostics.rs +++ b/crates/ra_hir/src/diagnostics.rs @@ -2,3 +2,53 @@ pub use hir_def::diagnostics::UnresolvedModule; pub use hir_expand::diagnostics::{AstDiagnostic, Diagnostic, DiagnosticSink}; pub use hir_ty::diagnostics::{MissingFields, MissingMatchArms, MissingOkInTailExpr, NoSuchField}; + +use std::sync::Arc; + +use crate::code_model::Function; +use crate::db::HirDatabase; +use crate::has_source::HasSource; +use hir_ty::{ + diagnostics::{MissingUnsafe, UnnecessaryUnsafe}, + expr::unsafe_expressions, + InferenceResult, +}; +use ra_syntax::AstPtr; + +pub struct UnsafeValidator<'a, 'b: 'a> { + func: &'a Function, + infer: Arc, + sink: &'a mut DiagnosticSink<'b>, +} + +impl<'a, 'b> UnsafeValidator<'a, 'b> { + pub fn new( + func: &'a Function, + infer: Arc, + sink: &'a mut DiagnosticSink<'b>, + ) -> UnsafeValidator<'a, 'b> { + UnsafeValidator { func, infer, sink } + } + + pub fn validate_body(&mut self, db: &dyn HirDatabase) { + let def = self.func.id.into(); + let unsafe_expressions = unsafe_expressions(db, self.infer.as_ref(), def); + let func_data = db.function_data(self.func.id); + let unnecessary = func_data.is_unsafe && unsafe_expressions.len() == 0; + let missing = !func_data.is_unsafe && unsafe_expressions.len() > 0; + if !(unnecessary || missing) { + return; + } + + let in_file = self.func.source(db); + let file = in_file.file_id; + let fn_def = AstPtr::new(&in_file.value); + let fn_name = func_data.name.clone().into(); + + if unnecessary { + self.sink.push(UnnecessaryUnsafe { file, fn_def, fn_name }) + } else { + self.sink.push(MissingUnsafe { file, fn_def, fn_name }) + } + } +} -- cgit v1.2.3