From 474835704568c4d494206282082d79f57068b060 Mon Sep 17 00:00:00 2001 From: Maybe Waffle Date: Wed, 21 Dec 2022 18:17:42 +0000 Subject: [PATCH 1/4] Drive-by cleanup: fully qualify `ast::Expr` in `hir` --- crates/hir/src/lib.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/crates/hir/src/lib.rs b/crates/hir/src/lib.rs index b841e580b6c..2933d488a18 100644 --- a/crates/hir/src/lib.rs +++ b/crates/hir/src/lib.rs @@ -74,7 +74,7 @@ use rustc_hash::FxHashSet; use stdx::{impl_from, never}; use syntax::{ - ast::{self, Expr, HasAttrs as _, HasDocComments, HasName}, + ast::{self, HasAttrs as _, HasDocComments, HasName}, AstNode, AstPtr, SmolStr, SyntaxNodePtr, TextRange, T, }; @@ -1074,7 +1074,7 @@ pub(crate) fn variant_data(self, db: &dyn HirDatabase) -> Arc { db.enum_data(self.parent.id).variants[self.id].variant_data.clone() } - pub fn value(self, db: &dyn HirDatabase) -> Option { + pub fn value(self, db: &dyn HirDatabase) -> Option { self.source(db)?.value.expr() } From 3bfe7040e8321e8fbe3c5bdc8660dae1488838d1 Mon Sep 17 00:00:00 2001 From: Maybe Waffle Date: Wed, 21 Dec 2022 18:18:12 +0000 Subject: [PATCH 2/4] Add an option to hide adjustment hints outside of unsafe blocks --- crates/hir/src/lib.rs | 7 +- crates/ide/src/inlay_hints.rs | 2 + crates/ide/src/inlay_hints/adjustment.rs | 160 ++++++++++++++++++++++- crates/ide/src/static_index.rs | 1 + crates/rust-analyzer/src/config.rs | 5 + docs/user/generated_config.adoc | 5 + editors/code/package.json | 5 + 7 files changed, 181 insertions(+), 4 deletions(-) diff --git a/crates/hir/src/lib.rs b/crates/hir/src/lib.rs index 2933d488a18..7c2829c855c 100644 --- a/crates/hir/src/lib.rs +++ b/crates/hir/src/lib.rs @@ -50,8 +50,8 @@ per_ns::PerNs, resolver::{HasResolver, Resolver}, src::HasSource as _, - AdtId, AssocItemId, AssocItemLoc, AttrDefId, ConstId, ConstParamId, DefWithBodyId, EnumId, - EnumVariantId, FunctionId, GenericDefId, HasModule, ImplId, ItemContainerId, LifetimeParamId, + AdtId, AssocItemId, AssocItemLoc, AttrDefId, ConstId, ConstParamId, EnumId, EnumVariantId, + FunctionId, GenericDefId, HasModule, ImplId, ItemContainerId, LifetimeParamId, LocalEnumVariantId, LocalFieldId, Lookup, MacroExpander, MacroId, ModuleId, StaticId, StructId, TraitId, TypeAliasId, TypeOrConstParamId, TypeParamId, UnionId, }; @@ -107,13 +107,16 @@ hir_def::{ adt::StructKind, attr::{Attr, Attrs, AttrsWithOwner, Documentation}, + body::{Body, BodySourceMap}, builtin_attr::AttributeTemplate, + expr::Expr, find_path::PrefixKind, import_map, nameres::ModuleSource, path::{ModPath, PathKind}, type_ref::{Mutability, TypeRef}, visibility::Visibility, + DefWithBodyId, }, hir_expand::{ name::{known, Name}, diff --git a/crates/ide/src/inlay_hints.rs b/crates/ide/src/inlay_hints.rs index 152f31b3a57..eca76d05fde 100644 --- a/crates/ide/src/inlay_hints.rs +++ b/crates/ide/src/inlay_hints.rs @@ -28,6 +28,7 @@ pub struct InlayHintsConfig { pub parameter_hints: bool, pub chaining_hints: bool, pub adjustment_hints: AdjustmentHints, + pub adjustment_hints_hide_outside_unsafe: bool, pub closure_return_type_hints: ClosureReturnTypeHints, pub binding_mode_hints: bool, pub lifetime_elision_hints: LifetimeElisionHints, @@ -343,6 +344,7 @@ mod tests { lifetime_elision_hints: LifetimeElisionHints::Never, closure_return_type_hints: ClosureReturnTypeHints::Never, adjustment_hints: AdjustmentHints::Never, + adjustment_hints_hide_outside_unsafe: false, binding_mode_hints: false, hide_named_constructor_hints: false, hide_closure_initialization_hints: false, diff --git a/crates/ide/src/inlay_hints/adjustment.rs b/crates/ide/src/inlay_hints/adjustment.rs index b2bec10d05d..c853b924b2f 100644 --- a/crates/ide/src/inlay_hints/adjustment.rs +++ b/crates/ide/src/inlay_hints/adjustment.rs @@ -3,10 +3,17 @@ //! let _: u32 = /* */ loop {}; //! let _: &u32 = /* &* */ &mut 0; //! ``` -use hir::{Adjust, AutoBorrow, Mutability, OverloadedDeref, PointerCast, Safety, Semantics}; +use either::Either; +use hir::{ + db::DefDatabase, Adjust, AutoBorrow, InFile, Mutability, OverloadedDeref, PointerCast, Safety, + Semantics, +}; use ide_db::RootDatabase; -use syntax::ast::{self, AstNode}; +use syntax::{ + ast::{self, AstNode}, + SyntaxNode, +}; use crate::{AdjustmentHints, InlayHint, InlayHintsConfig, InlayKind}; @@ -16,6 +23,10 @@ pub(super) fn hints( config: &InlayHintsConfig, expr: &ast::Expr, ) -> Option<()> { + if config.adjustment_hints_hide_outside_unsafe && !is_inside_unsafe(sema, expr.syntax()) { + return None; + } + if config.adjustment_hints == AdjustmentHints::Never { return None; } @@ -110,6 +121,59 @@ pub(super) fn hints( Some(()) } +fn is_inside_unsafe(sema: &Semantics<'_, RootDatabase>, node: &SyntaxNode) -> bool { + let item_or_variant = |ancestor: SyntaxNode| { + if ast::Item::can_cast(ancestor.kind()) { + ast::Item::cast(ancestor).map(Either::Left) + } else { + ast::Variant::cast(ancestor).map(Either::Right) + } + }; + let Some(enclosing_item) = node.ancestors().find_map(item_or_variant) else { return false }; + + let def = match &enclosing_item { + Either::Left(ast::Item::Fn(it)) => { + sema.to_def(it).map(<_>::into).map(hir::DefWithBodyId::FunctionId) + } + Either::Left(ast::Item::Const(it)) => { + sema.to_def(it).map(<_>::into).map(hir::DefWithBodyId::ConstId) + } + Either::Left(ast::Item::Static(it)) => { + sema.to_def(it).map(<_>::into).map(hir::DefWithBodyId::StaticId) + } + Either::Left(_) => None, + Either::Right(it) => sema.to_def(it).map(<_>::into).map(hir::DefWithBodyId::VariantId), + }; + let Some(def) = def else { return false }; + let enclosing_node = enclosing_item.as_ref().either(|i| i.syntax(), |v| v.syntax()); + + if ast::Fn::cast(enclosing_node.clone()).and_then(|f| f.unsafe_token()).is_some() { + return true; + } + + let (body, source_map) = sema.db.body_with_source_map(def); + + let file_id = sema.hir_file_for(node); + + let Some(mut parent) = node.parent() else { return false }; + loop { + if &parent == enclosing_node { + break false; + } + + if let Some(parent) = ast::Expr::cast(parent.clone()) { + if let Some(expr_id) = source_map.node_expr(InFile { file_id, value: &parent }) { + if let hir::Expr::Unsafe { .. } = body[expr_id] { + break true; + } + } + } + + let Some(parent_) = parent.parent() else { break false }; + parent = parent_; + } +} + #[cfg(test)] mod tests { use crate::{ @@ -233,4 +297,96 @@ fn or_else() { "#, ) } + + #[test] + fn adjustment_hints_unsafe_only() { + check_with_config( + InlayHintsConfig { + adjustment_hints: AdjustmentHints::Always, + adjustment_hints_hide_outside_unsafe: true, + ..DISABLED_CONFIG + }, + r#" +unsafe fn enabled() { + f(&&()); + //^^^^& + //^^^^* + //^^^^* +} + +fn disabled() { + f(&&()); +} + +fn mixed() { + f(&&()); + + unsafe { + f(&&()); + //^^^^& + //^^^^* + //^^^^* + } +} + +const _: () = { + f(&&()); + + unsafe { + f(&&()); + //^^^^& + //^^^^* + //^^^^* + } +}; + +static STATIC: () = { + f(&&()); + + unsafe { + f(&&()); + //^^^^& + //^^^^* + //^^^^* + } +}; + +enum E { + Disable = { f(&&()); 0 }, + Enable = unsafe { f(&&()); 1 }, + //^^^^& + //^^^^* + //^^^^* +} + +const fn f(_: &()) {} + "#, + ) + } + + #[test] + fn adjustment_hints_unsafe_only_with_item() { + check_with_config( + InlayHintsConfig { + adjustment_hints: AdjustmentHints::Always, + adjustment_hints_hide_outside_unsafe: true, + ..DISABLED_CONFIG + }, + r#" +fn a() { + struct Struct; + impl Struct { + fn by_ref(&self) {} + } + + _ = Struct.by_ref(); + + _ = unsafe { Struct.by_ref() }; + //^^^^^^( + //^^^^^^& + //^^^^^^) +} + "#, + ); + } } diff --git a/crates/ide/src/static_index.rs b/crates/ide/src/static_index.rs index 2380cf7381c..4f1946ed487 100644 --- a/crates/ide/src/static_index.rs +++ b/crates/ide/src/static_index.rs @@ -113,6 +113,7 @@ fn add_file(&mut self, file_id: FileId) { closure_return_type_hints: crate::ClosureReturnTypeHints::WithBlock, lifetime_elision_hints: crate::LifetimeElisionHints::Never, adjustment_hints: crate::AdjustmentHints::Never, + adjustment_hints_hide_outside_unsafe: false, hide_named_constructor_hints: false, hide_closure_initialization_hints: false, param_names_for_lifetime_elision_hints: false, diff --git a/crates/rust-analyzer/src/config.rs b/crates/rust-analyzer/src/config.rs index 835b37c98e2..35d0d8f9772 100644 --- a/crates/rust-analyzer/src/config.rs +++ b/crates/rust-analyzer/src/config.rs @@ -329,6 +329,8 @@ struct ConfigData { inlayHints_closureReturnTypeHints_enable: ClosureReturnTypeHintsDef = "\"never\"", /// Whether to show inlay hints for type adjustments. inlayHints_expressionAdjustmentHints_enable: AdjustmentHintsDef = "\"never\"", + /// Whether to hide inlay hints for type adjustments outside of `unsafe` blocks. + inlayHints_expressionAdjustmentHints_hideOutsideUnsafe: bool = "false", /// Whether to show inlay type hints for elided lifetimes in function signatures. inlayHints_lifetimeElisionHints_enable: LifetimeElisionDef = "\"never\"", /// Whether to prefer using parameter names as the name for elided lifetime hints if possible. @@ -1224,6 +1226,9 @@ pub fn inlay_hints(&self) -> InlayHintsConfig { }, AdjustmentHintsDef::Reborrow => ide::AdjustmentHints::ReborrowOnly, }, + adjustment_hints_hide_outside_unsafe: self + .data + .inlayHints_expressionAdjustmentHints_hideOutsideUnsafe, binding_mode_hints: self.data.inlayHints_bindingModeHints_enable, param_names_for_lifetime_elision_hints: self .data diff --git a/docs/user/generated_config.adoc b/docs/user/generated_config.adoc index db41c7bf109..7cff2cbb6a4 100644 --- a/docs/user/generated_config.adoc +++ b/docs/user/generated_config.adoc @@ -459,6 +459,11 @@ Whether to show inlay type hints for return types of closures. -- Whether to show inlay hints for type adjustments. -- +[[rust-analyzer.inlayHints.expressionAdjustmentHints.hideOutsideUnsafe]]rust-analyzer.inlayHints.expressionAdjustmentHints.hideOutsideUnsafe (default: `false`):: ++ +-- +Whether to hide inlay hints for type adjustments outside of `unsafe` blocks. +-- [[rust-analyzer.inlayHints.lifetimeElisionHints.enable]]rust-analyzer.inlayHints.lifetimeElisionHints.enable (default: `"never"`):: + -- diff --git a/editors/code/package.json b/editors/code/package.json index f9b0e28dadb..21d65321d2f 100644 --- a/editors/code/package.json +++ b/editors/code/package.json @@ -975,6 +975,11 @@ "Only show auto borrow and dereference adjustment hints." ] }, + "rust-analyzer.inlayHints.expressionAdjustmentHints.hideOutsideUnsafe": { + "markdownDescription": "Whether to hide inlay hints for type adjustments outside of `unsafe` blocks.", + "default": false, + "type": "boolean" + }, "rust-analyzer.inlayHints.lifetimeElisionHints.enable": { "markdownDescription": "Whether to show inlay type hints for elided lifetimes in function signatures.", "default": "never", From 608dc492ea9adaed2ae0cfee03fd5a6e398032c5 Mon Sep 17 00:00:00 2001 From: Maybe Waffle Date: Wed, 21 Dec 2022 20:34:49 +0000 Subject: [PATCH 3/4] Move `is_inside_unsafe` to `Semantics` impl --- crates/hir/src/lib.rs | 7 +-- crates/hir/src/semantics.rs | 73 ++++++++++++++++++++++-- crates/ide/src/inlay_hints/adjustment.rs | 67 +--------------------- 3 files changed, 74 insertions(+), 73 deletions(-) diff --git a/crates/hir/src/lib.rs b/crates/hir/src/lib.rs index 7c2829c855c..2933d488a18 100644 --- a/crates/hir/src/lib.rs +++ b/crates/hir/src/lib.rs @@ -50,8 +50,8 @@ per_ns::PerNs, resolver::{HasResolver, Resolver}, src::HasSource as _, - AdtId, AssocItemId, AssocItemLoc, AttrDefId, ConstId, ConstParamId, EnumId, EnumVariantId, - FunctionId, GenericDefId, HasModule, ImplId, ItemContainerId, LifetimeParamId, + AdtId, AssocItemId, AssocItemLoc, AttrDefId, ConstId, ConstParamId, DefWithBodyId, EnumId, + EnumVariantId, FunctionId, GenericDefId, HasModule, ImplId, ItemContainerId, LifetimeParamId, LocalEnumVariantId, LocalFieldId, Lookup, MacroExpander, MacroId, ModuleId, StaticId, StructId, TraitId, TypeAliasId, TypeOrConstParamId, TypeParamId, UnionId, }; @@ -107,16 +107,13 @@ hir_def::{ adt::StructKind, attr::{Attr, Attrs, AttrsWithOwner, Documentation}, - body::{Body, BodySourceMap}, builtin_attr::AttributeTemplate, - expr::Expr, find_path::PrefixKind, import_map, nameres::ModuleSource, path::{ModPath, PathKind}, type_ref::{Mutability, TypeRef}, visibility::Visibility, - DefWithBodyId, }, hir_expand::{ name::{known, Name}, diff --git a/crates/hir/src/semantics.rs b/crates/hir/src/semantics.rs index 2ed62372ae2..8d75e01029b 100644 --- a/crates/hir/src/semantics.rs +++ b/crates/hir/src/semantics.rs @@ -5,11 +5,14 @@ use std::{cell::RefCell, fmt, iter, mem, ops}; use base_db::{FileId, FileRange}; +use either::Either; use hir_def::{ - body, macro_id_to_def_id, + body, + expr::Expr, + macro_id_to_def_id, resolver::{self, HasResolver, Resolver, TypeNs}, type_ref::Mutability, - AsMacroCall, FunctionId, MacroId, TraitId, VariantId, + AsMacroCall, DefWithBodyId, FunctionId, MacroId, TraitId, VariantId, }; use hir_expand::{ db::AstDatabase, @@ -438,8 +441,7 @@ pub fn record_pattern_missing_fields(&self, pattern: &ast::RecordPat) -> Vec<(Fi } pub fn to_def(&self, src: &T) -> Option { - let src = self.imp.find_file(src.syntax()).with_value(src).cloned(); - T::to_def(&self.imp, src) + self.imp.to_def(src) } pub fn to_module_def(&self, file: FileId) -> Option { @@ -481,6 +483,11 @@ pub fn is_unsafe_ref_expr(&self, ref_expr: &ast::RefExpr) -> bool { pub fn is_unsafe_ident_pat(&self, ident_pat: &ast::IdentPat) -> bool { self.imp.is_unsafe_ident_pat(ident_pat) } + + /// Returns `true` if the `node` is inside an `unsafe` context. + pub fn is_inside_unsafe(&self, node: &SyntaxNode) -> bool { + self.imp.is_inside_unsafe(node) + } } impl<'db> SemanticsImpl<'db> { @@ -1243,6 +1250,11 @@ fn with_ctx) -> T, T>(&self, f: F) -> T { f(&mut ctx) } + fn to_def(&self, src: &T) -> Option { + let src = self.find_file(src.syntax()).with_value(src).cloned(); + T::to_def(&self, src) + } + fn to_module_def(&self, file: FileId) -> impl Iterator { self.with_ctx(|ctx| ctx.file_to_def(file)).into_iter().map(Module::from) } @@ -1458,6 +1470,59 @@ fn is_unsafe_ident_pat(&self, ident_pat: &ast::IdentPat) -> bool { .map(|ty| ty.original.is_packed(self.db)) .unwrap_or(false) } + + fn is_inside_unsafe(&self, node: &SyntaxNode) -> bool { + let item_or_variant = |ancestor: SyntaxNode| { + if ast::Item::can_cast(ancestor.kind()) { + ast::Item::cast(ancestor).map(Either::Left) + } else { + ast::Variant::cast(ancestor).map(Either::Right) + } + }; + let Some(enclosing_item) = node.ancestors().find_map(item_or_variant) else { return false }; + + let def = match &enclosing_item { + Either::Left(ast::Item::Fn(it)) => { + self.to_def(it).map(<_>::into).map(DefWithBodyId::FunctionId) + } + Either::Left(ast::Item::Const(it)) => { + self.to_def(it).map(<_>::into).map(DefWithBodyId::ConstId) + } + Either::Left(ast::Item::Static(it)) => { + self.to_def(it).map(<_>::into).map(DefWithBodyId::StaticId) + } + Either::Left(_) => None, + Either::Right(it) => self.to_def(it).map(<_>::into).map(DefWithBodyId::VariantId), + }; + let Some(def) = def else { return false }; + let enclosing_node = enclosing_item.as_ref().either(|i| i.syntax(), |v| v.syntax()); + + if ast::Fn::cast(enclosing_node.clone()).and_then(|f| f.unsafe_token()).is_some() { + return true; + } + + let (body, source_map) = self.db.body_with_source_map(def); + + let file_id = self.find_file(node).file_id; + + let Some(mut parent) = node.parent() else { return false }; + loop { + if &parent == enclosing_node { + break false; + } + + if let Some(parent) = ast::Expr::cast(parent.clone()) { + if let Some(expr_id) = source_map.node_expr(InFile { file_id, value: &parent }) { + if let Expr::Unsafe { .. } = body[expr_id] { + break true; + } + } + } + + let Some(parent_) = parent.parent() else { break false }; + parent = parent_; + } + } } fn macro_call_to_macro_id( diff --git a/crates/ide/src/inlay_hints/adjustment.rs b/crates/ide/src/inlay_hints/adjustment.rs index c853b924b2f..e7ebaa1d468 100644 --- a/crates/ide/src/inlay_hints/adjustment.rs +++ b/crates/ide/src/inlay_hints/adjustment.rs @@ -3,17 +3,9 @@ //! let _: u32 = /* */ loop {}; //! let _: &u32 = /* &* */ &mut 0; //! ``` -use either::Either; -use hir::{ - db::DefDatabase, Adjust, AutoBorrow, InFile, Mutability, OverloadedDeref, PointerCast, Safety, - Semantics, -}; +use hir::{Adjust, AutoBorrow, Mutability, OverloadedDeref, PointerCast, Safety, Semantics}; use ide_db::RootDatabase; - -use syntax::{ - ast::{self, AstNode}, - SyntaxNode, -}; +use syntax::ast::{self, AstNode}; use crate::{AdjustmentHints, InlayHint, InlayHintsConfig, InlayKind}; @@ -23,7 +15,7 @@ pub(super) fn hints( config: &InlayHintsConfig, expr: &ast::Expr, ) -> Option<()> { - if config.adjustment_hints_hide_outside_unsafe && !is_inside_unsafe(sema, expr.syntax()) { + if config.adjustment_hints_hide_outside_unsafe && !sema.is_inside_unsafe(expr.syntax()) { return None; } @@ -121,59 +113,6 @@ pub(super) fn hints( Some(()) } -fn is_inside_unsafe(sema: &Semantics<'_, RootDatabase>, node: &SyntaxNode) -> bool { - let item_or_variant = |ancestor: SyntaxNode| { - if ast::Item::can_cast(ancestor.kind()) { - ast::Item::cast(ancestor).map(Either::Left) - } else { - ast::Variant::cast(ancestor).map(Either::Right) - } - }; - let Some(enclosing_item) = node.ancestors().find_map(item_or_variant) else { return false }; - - let def = match &enclosing_item { - Either::Left(ast::Item::Fn(it)) => { - sema.to_def(it).map(<_>::into).map(hir::DefWithBodyId::FunctionId) - } - Either::Left(ast::Item::Const(it)) => { - sema.to_def(it).map(<_>::into).map(hir::DefWithBodyId::ConstId) - } - Either::Left(ast::Item::Static(it)) => { - sema.to_def(it).map(<_>::into).map(hir::DefWithBodyId::StaticId) - } - Either::Left(_) => None, - Either::Right(it) => sema.to_def(it).map(<_>::into).map(hir::DefWithBodyId::VariantId), - }; - let Some(def) = def else { return false }; - let enclosing_node = enclosing_item.as_ref().either(|i| i.syntax(), |v| v.syntax()); - - if ast::Fn::cast(enclosing_node.clone()).and_then(|f| f.unsafe_token()).is_some() { - return true; - } - - let (body, source_map) = sema.db.body_with_source_map(def); - - let file_id = sema.hir_file_for(node); - - let Some(mut parent) = node.parent() else { return false }; - loop { - if &parent == enclosing_node { - break false; - } - - if let Some(parent) = ast::Expr::cast(parent.clone()) { - if let Some(expr_id) = source_map.node_expr(InFile { file_id, value: &parent }) { - if let hir::Expr::Unsafe { .. } = body[expr_id] { - break true; - } - } - } - - let Some(parent_) = parent.parent() else { break false }; - parent = parent_; - } -} - #[cfg(test)] mod tests { use crate::{ From 1038db5f1d79155860bd9e1487c0df34ec542b39 Mon Sep 17 00:00:00 2001 From: Waffle Maybe Date: Thu, 22 Dec 2022 02:52:52 +0400 Subject: [PATCH 4/4] Apply suggestions from code review Co-authored-by: Lukas Wirth --- crates/hir/src/semantics.rs | 17 +++++++---------- crates/ide/src/inlay_hints/adjustment.rs | 2 +- 2 files changed, 8 insertions(+), 11 deletions(-) diff --git a/crates/hir/src/semantics.rs b/crates/hir/src/semantics.rs index 8d75e01029b..569c2bfb9e6 100644 --- a/crates/hir/src/semantics.rs +++ b/crates/hir/src/semantics.rs @@ -485,8 +485,8 @@ pub fn is_unsafe_ident_pat(&self, ident_pat: &ast::IdentPat) -> bool { } /// Returns `true` if the `node` is inside an `unsafe` context. - pub fn is_inside_unsafe(&self, node: &SyntaxNode) -> bool { - self.imp.is_inside_unsafe(node) + pub fn is_inside_unsafe(&self, expr: &ast::Expr) -> bool { + self.imp.is_inside_unsafe(expr) } } @@ -1471,7 +1471,7 @@ fn is_unsafe_ident_pat(&self, ident_pat: &ast::IdentPat) -> bool { .unwrap_or(false) } - fn is_inside_unsafe(&self, node: &SyntaxNode) -> bool { + fn is_inside_unsafe(&self, expr: &ast::Expr) -> bool { let item_or_variant = |ancestor: SyntaxNode| { if ast::Item::can_cast(ancestor.kind()) { ast::Item::cast(ancestor).map(Either::Left) @@ -1479,9 +1479,10 @@ fn is_inside_unsafe(&self, node: &SyntaxNode) -> bool { ast::Variant::cast(ancestor).map(Either::Right) } }; - let Some(enclosing_item) = node.ancestors().find_map(item_or_variant) else { return false }; + let Some(enclosing_item) = expr.syntax().ancestors().find_map(item_or_variant) else { return false }; let def = match &enclosing_item { + Either::Left(ast::Item::Fn(it)) if it.unsafe_token().is_some() => return true, Either::Left(ast::Item::Fn(it)) => { self.to_def(it).map(<_>::into).map(DefWithBodyId::FunctionId) } @@ -1497,15 +1498,11 @@ fn is_inside_unsafe(&self, node: &SyntaxNode) -> bool { let Some(def) = def else { return false }; let enclosing_node = enclosing_item.as_ref().either(|i| i.syntax(), |v| v.syntax()); - if ast::Fn::cast(enclosing_node.clone()).and_then(|f| f.unsafe_token()).is_some() { - return true; - } - let (body, source_map) = self.db.body_with_source_map(def); - let file_id = self.find_file(node).file_id; + let file_id = self.find_file(expr.syntax()).file_id; - let Some(mut parent) = node.parent() else { return false }; + let Some(mut parent) = expr.syntax().parent() else { return false }; loop { if &parent == enclosing_node { break false; diff --git a/crates/ide/src/inlay_hints/adjustment.rs b/crates/ide/src/inlay_hints/adjustment.rs index e7ebaa1d468..1c13f31cf24 100644 --- a/crates/ide/src/inlay_hints/adjustment.rs +++ b/crates/ide/src/inlay_hints/adjustment.rs @@ -15,7 +15,7 @@ pub(super) fn hints( config: &InlayHintsConfig, expr: &ast::Expr, ) -> Option<()> { - if config.adjustment_hints_hide_outside_unsafe && !sema.is_inside_unsafe(expr.syntax()) { + if config.adjustment_hints_hide_outside_unsafe && !sema.is_inside_unsafe(expr) { return None; }