Unnamed repository; edit this file 'description' to name the repository.
Merge pull request #22133 from ChayimFriedman2/remove-more-arcs
internal: Remove more arcs
Chayim Refael Friedman 2 weeks ago
parent e3847c8 · parent 9ece3bc · commit 64cdaeb
-rw-r--r--crates/hir-def/src/nameres/attr_resolution.rs3
-rw-r--r--crates/hir-def/src/nameres/tests/incremental.rs48
-rw-r--r--crates/hir-expand/src/db.rs101
-rw-r--r--crates/hir-expand/src/declarative.rs9
-rw-r--r--crates/hir-expand/src/eager.rs9
-rw-r--r--crates/hir-expand/src/fixup.rs14
-rw-r--r--crates/hir-expand/src/lib.rs6
-rw-r--r--crates/hir-ty/src/consteval.rs3
-rw-r--r--crates/hir-ty/src/db.rs43
-rw-r--r--crates/hir-ty/src/display.rs2
-rw-r--r--crates/hir-ty/src/layout.rs4
-rw-r--r--crates/hir-ty/src/layout/adt.rs2
-rw-r--r--crates/hir-ty/src/layout/target.rs6
-rw-r--r--crates/hir-ty/src/mir.rs3
-rw-r--r--crates/hir-ty/src/mir/borrowck.rs82
-rw-r--r--crates/hir-ty/src/mir/eval.rs183
-rw-r--r--crates/hir-ty/src/mir/eval/shim.rs20
-rw-r--r--crates/hir-ty/src/mir/eval/shim/simd.rs4
-rw-r--r--crates/hir-ty/src/mir/lower.rs26
-rw-r--r--crates/hir-ty/src/mir/monomorphization.rs25
-rw-r--r--crates/hir-ty/src/mir/pretty.rs2
-rw-r--r--crates/hir/src/lib.rs22
-rw-r--r--crates/hir/src/term_search/tactics.rs5
-rw-r--r--crates/ide/src/hover/render.rs10
-rw-r--r--crates/ide/src/view_memory_layout.rs2
25 files changed, 344 insertions, 290 deletions
diff --git a/crates/hir-def/src/nameres/attr_resolution.rs b/crates/hir-def/src/nameres/attr_resolution.rs
index 062b55fcef..5aabd7dbc6 100644
--- a/crates/hir-def/src/nameres/attr_resolution.rs
+++ b/crates/hir-def/src/nameres/attr_resolution.rs
@@ -9,7 +9,6 @@ use hir_expand::{
};
use span::SyntaxContext;
use syntax::ast;
-use triomphe::Arc;
use crate::{
AstIdWithPath, MacroId, ModuleId, UnresolvedMacro,
@@ -126,7 +125,7 @@ pub(super) fn attr_macro_as_call_id(
krate,
MacroCallKind::Attr {
ast_id: item_attr.ast_id,
- attr_args: arg.map(Arc::new),
+ attr_args: arg.map(Box::new),
censored_attr_ids,
},
macro_attr.ctxt,
diff --git a/crates/hir-def/src/nameres/tests/incremental.rs b/crates/hir-def/src/nameres/tests/incremental.rs
index 60ec3035fa..08f672aa0c 100644
--- a/crates/hir-def/src/nameres/tests/incremental.rs
+++ b/crates/hir-def/src/nameres/tests/incremental.rs
@@ -227,7 +227,7 @@ pub struct S {}
"ast_id_map",
"parse",
"real_span_map",
- "decl_macro_expander_shim",
+ "DeclarativeMacroExpander::expander_",
"file_item_tree_query",
"ast_id_map",
"parse",
@@ -240,7 +240,7 @@ pub struct S {}
"file_item_tree_query",
"ast_id_map",
"parse_macro_expansion",
- "macro_arg_shim",
+ "macro_arg",
]
"#]],
expect![[r#"
@@ -249,7 +249,7 @@ pub struct S {}
"ast_id_map",
"file_item_tree_query",
"real_span_map",
- "macro_arg_shim",
+ "macro_arg",
"parse_macro_expansion",
"ast_id_map",
"file_item_tree_query",
@@ -303,8 +303,8 @@ fn f() { foo }
"file_item_tree_query",
"ast_id_map",
"parse_macro_expansion",
- "expand_proc_macro_shim",
- "macro_arg_shim",
+ "expand_proc_macro",
+ "macro_arg",
"proc_macro_span_shim",
]
"#]],
@@ -314,8 +314,8 @@ fn f() { foo }
"ast_id_map",
"file_item_tree_query",
"real_span_map",
- "macro_arg_shim",
- "expand_proc_macro_shim",
+ "macro_arg",
+ "expand_proc_macro",
"parse_macro_expansion",
"ast_id_map",
"file_item_tree_query",
@@ -415,7 +415,7 @@ pub struct S {}
"ast_id_map",
"parse",
"real_span_map",
- "decl_macro_expander_shim",
+ "DeclarativeMacroExpander::expander_",
"file_item_tree_query",
"ast_id_map",
"parse",
@@ -428,19 +428,19 @@ pub struct S {}
"file_item_tree_query",
"ast_id_map",
"parse_macro_expansion",
- "macro_arg_shim",
- "decl_macro_expander_shim",
+ "macro_arg",
+ "DeclarativeMacroExpander::expander_",
"macro_def_shim",
"file_item_tree_query",
"ast_id_map",
"parse_macro_expansion",
- "macro_arg_shim",
+ "macro_arg",
"macro_def_shim",
"file_item_tree_query",
"ast_id_map",
"parse_macro_expansion",
- "expand_proc_macro_shim",
- "macro_arg_shim",
+ "expand_proc_macro",
+ "macro_arg",
"proc_macro_span_shim",
]
"#]],
@@ -450,10 +450,10 @@ pub struct S {}
"ast_id_map",
"file_item_tree_query",
"real_span_map",
- "macro_arg_shim",
- "decl_macro_expander_shim",
- "macro_arg_shim",
- "macro_arg_shim",
+ "macro_arg",
+ "DeclarativeMacroExpander::expander_",
+ "macro_arg",
+ "macro_arg",
]
"#]],
);
@@ -526,7 +526,7 @@ m!(Z);
"ast_id_map",
"parse",
"real_span_map",
- "decl_macro_expander_shim",
+ "DeclarativeMacroExpander::expander_",
"file_item_tree_query",
"ast_id_map",
"parse",
@@ -539,15 +539,15 @@ m!(Z);
"file_item_tree_query",
"ast_id_map",
"parse_macro_expansion",
- "macro_arg_shim",
+ "macro_arg",
"file_item_tree_query",
"ast_id_map",
"parse_macro_expansion",
- "macro_arg_shim",
+ "macro_arg",
"file_item_tree_query",
"ast_id_map",
"parse_macro_expansion",
- "macro_arg_shim",
+ "macro_arg",
]
"#]],
);
@@ -575,9 +575,9 @@ m!(Z);
"ast_id_map",
"file_item_tree_query",
"real_span_map",
- "macro_arg_shim",
- "macro_arg_shim",
- "macro_arg_shim",
+ "macro_arg",
+ "macro_arg",
+ "macro_arg",
]
"#]],
);
diff --git a/crates/hir-expand/src/db.rs b/crates/hir-expand/src/db.rs
index 57c78748f8..4b26c1f0e5 100644
--- a/crates/hir-expand/src/db.rs
+++ b/crates/hir-expand/src/db.rs
@@ -3,6 +3,7 @@
use base_db::{Crate, SourceDatabase};
use mbe::MatchedArmIndex;
use span::{AstIdMap, Edition, Span, SyntaxContext};
+use std::borrow::Cow;
use syntax::{AstNode, Parse, SyntaxError, SyntaxNode, SyntaxToken, T, ast};
use syntax_bridge::{DocCommentDesugarMode, syntax_node_to_token_tree};
use triomphe::Arc;
@@ -21,7 +22,7 @@ use crate::{
tt,
};
/// This is just to ensure the types of smart_macro_arg and macro_arg are the same
-type MacroArgResult = (Arc<tt::TopSubtree>, SyntaxFixupUndoInfo, Span);
+type MacroArgResult = (tt::TopSubtree, SyntaxFixupUndoInfo, Span);
/// Total limit on the number of tokens produced by any macro invocation.
///
/// If an invocation produces more tokens than this limit, it will not be stored in the database and
@@ -30,10 +31,10 @@ type MacroArgResult = (Arc<tt::TopSubtree>, SyntaxFixupUndoInfo, Span);
/// Actual max for `analysis-stats .` at some point: 30672.
const TOKEN_LIMIT: usize = 2_097_152;
-#[derive(Debug, Clone, Eq, PartialEq)]
-pub enum TokenExpander {
+#[derive(Debug, Clone, Copy, Eq, PartialEq)]
+pub enum TokenExpander<'db> {
/// Old-style `macro_rules` or the new macros 2.0
- DeclarativeMacro(Arc<DeclarativeMacroExpander>),
+ DeclarativeMacro(&'db DeclarativeMacroExpander),
/// Stuff like `line!` and `file!`.
BuiltIn(BuiltinFnLikeExpander),
/// Built-in eagerly expanded fn-like macros (`include!`, `concat!`, etc.)
@@ -99,34 +100,37 @@ pub trait ExpandDatabase: SourceDatabase {
/// subtree.
#[deprecated = "calling this is incorrect, call `macro_arg_considering_derives` instead"]
#[salsa::invoke(macro_arg)]
- fn macro_arg(&self, id: MacroCallId) -> MacroArgResult;
+ #[salsa::transparent]
+ fn macro_arg(&self, id: MacroCallId) -> &MacroArgResult;
#[salsa::transparent]
- fn macro_arg_considering_derives(
- &self,
+ fn macro_arg_considering_derives<'db>(
+ &'db self,
id: MacroCallId,
kind: &MacroCallKind,
- ) -> MacroArgResult;
+ ) -> &'db MacroArgResult;
/// Fetches the expander for this macro.
#[salsa::transparent]
#[salsa::invoke(TokenExpander::macro_expander)]
- fn macro_expander(&self, id: MacroDefId) -> TokenExpander;
+ fn macro_expander(&self, id: MacroDefId) -> TokenExpander<'_>;
/// Fetches (and compiles) the expander of this decl macro.
#[salsa::invoke(DeclarativeMacroExpander::expander)]
+ #[salsa::transparent]
fn decl_macro_expander(
&self,
def_crate: Crate,
id: AstId<ast::Macro>,
- ) -> Arc<DeclarativeMacroExpander>;
+ ) -> &DeclarativeMacroExpander;
/// Special case of the previous query for procedural macros. We can't LRU
/// proc macros, since they are not deterministic in general, and
/// non-determinism breaks salsa in a very, very, very bad way.
/// @edwin0cheng heroically debugged this once! See #4315 for details
#[salsa::invoke(expand_proc_macro)]
- fn expand_proc_macro(&self, call: MacroCallId) -> ExpandResult<Arc<tt::TopSubtree>>;
+ #[salsa::transparent]
+ fn expand_proc_macro(&self, call: MacroCallId) -> &ExpandResult<tt::TopSubtree>;
/// Retrieves the span to be used for a proc-macro expansions spans.
/// This is a firewall query as it requires parsing the file, which we don't want proc-macros to
/// directly depend on as that would cause to frequent invalidations, mainly because of the
@@ -135,12 +139,12 @@ pub trait ExpandDatabase: SourceDatabase {
#[salsa::invoke_interned(proc_macro_span)]
fn proc_macro_span(&self, fun: AstId<ast::Fn>) -> Span;
- /// Firewall query that returns the errors from the `parse_macro_expansion` query.
#[salsa::invoke(parse_macro_expansion_error)]
+ #[salsa::transparent]
fn parse_macro_expansion_error(
&self,
macro_call: MacroCallId,
- ) -> Option<Arc<ExpandResult<Arc<[SyntaxError]>>>>;
+ ) -> Option<ExpandResult<Arc<[SyntaxError]>>>;
#[salsa::transparent]
fn syntax_context(&self, file: HirFileId, edition: Edition) -> SyntaxContext;
@@ -179,7 +183,7 @@ pub fn expand_speculative(
token_to_map: SyntaxToken,
) -> Option<(SyntaxNode, Vec<(SyntaxToken, u8)>)> {
let loc = db.lookup_intern_macro_call(actual_macro_call);
- let (_, _, span) = db.macro_arg_considering_derives(actual_macro_call, &loc.kind);
+ let (_, _, span) = *db.macro_arg_considering_derives(actual_macro_call, &loc.kind);
let span_map = RealSpanMap::absolute(span.anchor.file_id);
let span_map = SpanMap::RealSpanMap(&span_map);
@@ -369,14 +373,7 @@ fn parse_macro_expansion(
let expand_to = loc.expand_to();
let mbe::ValueResult { value: (tt, matched_arm), err } = macro_expand(db, macro_file, loc);
- let (parse, mut rev_token_map) = token_tree_to_syntax_node(
- db,
- match &tt {
- CowArc::Arc(it) => it,
- CowArc::Owned(it) => it,
- },
- expand_to,
- );
+ let (parse, mut rev_token_map) = token_tree_to_syntax_node(db, &tt, expand_to);
rev_token_map.matched_arm = matched_arm;
ExpandResult { value: (parse, rev_token_map), err }
@@ -385,10 +382,10 @@ fn parse_macro_expansion(
fn parse_macro_expansion_error(
db: &dyn ExpandDatabase,
macro_call_id: MacroCallId,
-) -> Option<Arc<ExpandResult<Arc<[SyntaxError]>>>> {
+) -> Option<ExpandResult<Arc<[SyntaxError]>>> {
let e: ExpandResult<Arc<[SyntaxError]>> =
db.parse_macro_expansion(macro_call_id).as_ref().map(|it| Arc::from(it.0.errors()));
- if e.value.is_empty() && e.err.is_none() { None } else { Some(Arc::new(e)) }
+ if e.value.is_empty() && e.err.is_none() { None } else { Some(e) }
}
pub(crate) fn parse_with_map(
@@ -411,11 +408,11 @@ pub(crate) fn parse_with_map(
///
/// This is not connected to the database so it does not cached the result. However, the inner [macro_arg] query is
#[allow(deprecated)] // we are macro_arg_considering_derives
-fn macro_arg_considering_derives(
- db: &dyn ExpandDatabase,
+fn macro_arg_considering_derives<'db>(
+ db: &'db dyn ExpandDatabase,
id: MacroCallId,
kind: &MacroCallKind,
-) -> MacroArgResult {
+) -> &'db MacroArgResult {
match kind {
// Get the macro arg for the derive macro
MacroCallKind::Derive { derive_macro_id, .. } => db.macro_arg(*derive_macro_id),
@@ -424,6 +421,7 @@ fn macro_arg_considering_derives(
}
}
+#[salsa_macros::tracked(returns(ref))]
fn macro_arg(db: &dyn ExpandDatabase, id: MacroCallId) -> MacroArgResult {
let loc = db.lookup_intern_macro_call(id);
@@ -449,10 +447,10 @@ fn macro_arg(db: &dyn ExpandDatabase, id: MacroCallId) -> MacroArgResult {
let dummy_tt = |kind| {
(
- Arc::new(tt::TopSubtree::from_token_trees(
+ tt::TopSubtree::from_token_trees(
tt::Delimiter { open: span, close: span, kind },
tt::TokenTreesView::empty(),
- )),
+ ),
SyntaxFixupUndoInfo::default(),
span,
)
@@ -501,7 +499,7 @@ fn macro_arg(db: &dyn ExpandDatabase, id: MacroCallId) -> MacroArgResult {
// proc macros expect their inputs without parentheses, MBEs expect it with them included
tt.set_top_subtree_delimiter_kind(tt::DelimiterKind::Invisible);
}
- return (Arc::new(tt), SyntaxFixupUndoInfo::NONE, span);
+ return (tt, SyntaxFixupUndoInfo::NONE, span);
}
// MacroCallKind::Derive should not be here. As we are getting the argument for the derive macro
MacroCallKind::Derive { .. } => {
@@ -536,11 +534,11 @@ fn macro_arg(db: &dyn ExpandDatabase, id: MacroCallId) -> MacroArgResult {
tt.set_top_subtree_delimiter_kind(tt::DelimiterKind::Invisible);
}
- (Arc::new(tt), undo_info, span)
+ (tt, undo_info, span)
}
-impl TokenExpander {
- fn macro_expander(db: &dyn ExpandDatabase, id: MacroDefId) -> TokenExpander {
+impl<'db> TokenExpander<'db> {
+ fn macro_expander(db: &'db dyn ExpandDatabase, id: MacroDefId) -> TokenExpander<'db> {
match id.kind {
MacroDefKind::Declarative(ast_id, _) => {
TokenExpander::DeclarativeMacro(db.decl_macro_expander(id.krate, ast_id))
@@ -554,27 +552,26 @@ impl TokenExpander {
}
}
-enum CowArc<T> {
- Arc(Arc<T>),
- Owned(T),
-}
-
fn macro_expand(
db: &dyn ExpandDatabase,
macro_call_id: MacroCallId,
loc: MacroCallLoc,
-) -> ExpandResult<(CowArc<tt::TopSubtree>, MatchedArmIndex)> {
+) -> ExpandResult<(Cow<'_, tt::TopSubtree>, MatchedArmIndex)> {
let _p = tracing::info_span!("macro_expand").entered();
let (ExpandResult { value: (tt, matched_arm), err }, span) = match loc.def.kind {
MacroDefKind::ProcMacro(..) => {
- return db.expand_proc_macro(macro_call_id).map(CowArc::Arc).zip_val(None);
+ return db
+ .expand_proc_macro(macro_call_id)
+ .as_ref()
+ .map(|it| (Cow::Borrowed(it), None));
}
_ => {
let (macro_arg, undo_info, span) =
db.macro_arg_considering_derives(macro_call_id, &loc.kind);
+ let span = *span;
- let arg = &*macro_arg;
+ let arg = macro_arg;
let res = match loc.def.kind {
MacroDefKind::Declarative(id, _) => db
.decl_macro_expander(loc.def.krate, id)
@@ -594,7 +591,7 @@ fn macro_expand(
// As such we just return the input subtree here.
let eager = match &loc.kind {
MacroCallKind::FnLike { eager: None, .. } => {
- return ExpandResult::ok(CowArc::Arc(macro_arg.clone())).zip_val(None);
+ return ExpandResult::ok(Cow::Borrowed(macro_arg)).zip_val(None);
}
MacroCallKind::FnLike { eager: Some(eager), .. } => Some(&**eager),
_ => None,
@@ -610,7 +607,7 @@ fn macro_expand(
}
MacroDefKind::BuiltInAttr(_, it) => {
let mut res = it.expand(db, macro_call_id, arg, span);
- fixup::reverse_fixups(&mut res.value, &undo_info);
+ fixup::reverse_fixups(&mut res.value, undo_info);
res.zip_val(None)
}
MacroDefKind::ProcMacro(_, _, _) => unreachable!(),
@@ -624,12 +621,12 @@ fn macro_expand(
// Set a hard limit for the expanded tt
if let Err(value) = check_tt_count(&tt) {
return value
- .map(|()| CowArc::Owned(tt::TopSubtree::empty(tt::DelimSpan::from_single(span))))
+ .map(|()| Cow::Owned(tt::TopSubtree::empty(tt::DelimSpan::from_single(span))))
.zip_val(matched_arm);
}
}
- ExpandResult { value: (CowArc::Owned(tt), matched_arm), err }
+ ExpandResult { value: (Cow::Owned(tt), matched_arm), err }
}
fn proc_macro_span(db: &dyn ExpandDatabase, ast: AstId<ast::Fn>) -> Span {
@@ -643,10 +640,8 @@ fn proc_macro_span(db: &dyn ExpandDatabase, ast: AstId<ast::Fn>) -> Span {
span_map.span_for_range(range)
}
-fn expand_proc_macro(
- db: &dyn ExpandDatabase,
- id: MacroCallId,
-) -> ExpandResult<Arc<tt::TopSubtree>> {
+#[salsa_macros::tracked(returns(ref))]
+fn expand_proc_macro(db: &dyn ExpandDatabase, id: MacroCallId) -> ExpandResult<tt::TopSubtree> {
let loc = db.lookup_intern_macro_call(id);
let (macro_arg, undo_info, span) = db.macro_arg_considering_derives(id, &loc.kind);
@@ -666,7 +661,7 @@ fn expand_proc_macro(
db,
loc.def.krate,
loc.krate,
- &macro_arg,
+ macro_arg,
attr_arg,
span_with_def_site_ctxt(db, span, id.into(), loc.def.edition),
span_with_call_site_ctxt(db, span, id.into(), loc.def.edition),
@@ -676,12 +671,12 @@ fn expand_proc_macro(
// Set a hard limit for the expanded tt
if let Err(value) = check_tt_count(&tt) {
- return value.map(|()| Arc::new(tt::TopSubtree::empty(tt::DelimSpan::from_single(span))));
+ return value.map(|()| tt::TopSubtree::empty(tt::DelimSpan::from_single(*span)));
}
- fixup::reverse_fixups(&mut tt, &undo_info);
+ fixup::reverse_fixups(&mut tt, undo_info);
- ExpandResult { value: Arc::new(tt), err }
+ ExpandResult { value: tt, err }
}
pub(crate) fn token_tree_to_syntax_node(
diff --git a/crates/hir-expand/src/declarative.rs b/crates/hir-expand/src/declarative.rs
index aa745a2ccd..ead10a51a8 100644
--- a/crates/hir-expand/src/declarative.rs
+++ b/crates/hir-expand/src/declarative.rs
@@ -10,7 +10,6 @@ use syntax::{
ast::{self, HasAttrs},
};
use syntax_bridge::DocCommentDesugarMode;
-use triomphe::Arc;
use crate::{
AstId, ExpandError, ExpandErrorKind, ExpandResult, HirFileId, Lookup, MacroCallId,
@@ -78,12 +77,16 @@ impl DeclarativeMacroExpander {
.map_err(Into::into),
}
}
+}
+#[salsa::tracked]
+impl DeclarativeMacroExpander {
+ #[salsa::tracked(returns(ref))]
pub(crate) fn expander(
db: &dyn ExpandDatabase,
def_crate: Crate,
id: AstId<ast::Macro>,
- ) -> Arc<DeclarativeMacroExpander> {
+ ) -> DeclarativeMacroExpander {
let (root, map) = crate::db::parse_with_map(db, id.file_id);
let root = root.syntax_node();
@@ -177,6 +180,6 @@ impl DeclarativeMacroExpander {
HirFileId::MacroFile(macro_file) => macro_file.lookup(db).ctxt,
HirFileId::FileId(file) => SyntaxContext::root(file.edition(db)),
});
- Arc::new(DeclarativeMacroExpander { mac, transparency, edition })
+ DeclarativeMacroExpander { mac, transparency, edition }
}
}
diff --git a/crates/hir-expand/src/eager.rs b/crates/hir-expand/src/eager.rs
index 6e95ff01c3..dddef17ce7 100644
--- a/crates/hir-expand/src/eager.rs
+++ b/crates/hir-expand/src/eager.rs
@@ -22,7 +22,6 @@ use base_db::Crate;
use span::SyntaxContext;
use syntax::{AstPtr, Parse, SyntaxElement, SyntaxNode, TextSize, WalkEvent, ted};
use syntax_bridge::DocCommentDesugarMode;
-use triomphe::Arc;
use crate::{
AstId, EagerCallInfo, ExpandError, ExpandResult, ExpandTo, ExpansionSpanMap, InFile,
@@ -92,7 +91,7 @@ pub fn expand_eager_macro_input(
let mut subtree = syntax_bridge::syntax_node_to_token_tree(
&expanded_eager_input,
arg_map,
- span,
+ *span,
DocCommentDesugarMode::Mbe,
);
@@ -104,11 +103,11 @@ pub fn expand_eager_macro_input(
kind: MacroCallKind::FnLike {
ast_id,
expand_to,
- eager: Some(Arc::new(EagerCallInfo {
- arg: Arc::new(subtree),
+ eager: Some(Box::new(EagerCallInfo {
+ arg: subtree,
arg_id,
error: err.clone(),
- span,
+ span: *span,
})),
},
ctxt: call_site,
diff --git a/crates/hir-expand/src/fixup.rs b/crates/hir-expand/src/fixup.rs
index b51ec39ce7..939104b709 100644
--- a/crates/hir-expand/src/fixup.rs
+++ b/crates/hir-expand/src/fixup.rs
@@ -14,7 +14,7 @@ use syntax::{
match_ast,
};
use syntax_bridge::DocCommentDesugarMode;
-use triomphe::Arc;
+use thin_vec::ThinVec;
use tt::{Spacing, TransformTtAction, transform_tt};
use crate::{
@@ -35,8 +35,7 @@ pub(crate) struct SyntaxFixups {
/// This is the information needed to reverse the fixups.
#[derive(Clone, Debug, Default, PartialEq, Eq)]
pub struct SyntaxFixupUndoInfo {
- // FIXME: ThinArc<[Subtree]>
- original: Option<Arc<Box<[TopSubtree]>>>,
+ original: Option<ThinVec<TopSubtree>>,
}
impl SyntaxFixupUndoInfo {
@@ -59,7 +58,7 @@ pub(crate) fn fixup_syntax(
let mut append = FxHashMap::<SyntaxElement, _>::default();
let mut remove = FxHashSet::<SyntaxElement>::default();
let mut preorder = node.preorder();
- let mut original = Vec::new();
+ let mut original = ThinVec::new();
let dummy_range = FIXUP_DUMMY_RANGE;
let fake_span = |range| {
let span = span_map.span_for_range(range);
@@ -317,13 +316,12 @@ pub(crate) fn fixup_syntax(
}
}
}
+ original.shrink_to_fit();
let needs_fixups = !append.is_empty() || !original.is_empty();
SyntaxFixups {
append,
remove,
- undo_info: SyntaxFixupUndoInfo {
- original: needs_fixups.then(|| Arc::new(original.into_boxed_slice())),
- },
+ undo_info: SyntaxFixupUndoInfo { original: needs_fixups.then_some(original) },
}
}
@@ -340,7 +338,7 @@ fn has_error_to_handle(node: &SyntaxNode) -> bool {
}
pub(crate) fn reverse_fixups(tt: &mut TopSubtree, undo_info: &SyntaxFixupUndoInfo) {
- let Some(undo_info) = undo_info.original.as_deref() else { return };
+ let Some(undo_info) = &undo_info.original else { return };
let undo_info = &**undo_info;
let top_subtree = tt.top_subtree();
let open_span = top_subtree.delimiter.open;
diff --git a/crates/hir-expand/src/lib.rs b/crates/hir-expand/src/lib.rs
index fc2a07435b..403e544bf8 100644
--- a/crates/hir-expand/src/lib.rs
+++ b/crates/hir-expand/src/lib.rs
@@ -279,7 +279,7 @@ impl MacroDefKind {
#[derive(Debug, Clone, PartialEq, Eq, Hash)]
pub struct EagerCallInfo {
/// The expanded argument of the eager macro.
- arg: Arc<tt::TopSubtree>,
+ arg: tt::TopSubtree,
/// Call id of the eager macro's input file (this is the macro file for its fully expanded input).
arg_id: MacroCallId,
error: Option<ExpandError>,
@@ -296,7 +296,7 @@ pub enum MacroCallKind {
/// for the eager input macro file.
// FIXME: This is being interned, subtrees can vary quickly differing just slightly causing
// leakage problems here
- eager: Option<Arc<EagerCallInfo>>,
+ eager: Option<Box<EagerCallInfo>>,
},
Derive {
ast_id: AstId<ast::Adt>,
@@ -311,7 +311,7 @@ pub enum MacroCallKind {
Attr {
ast_id: AstId<ast::Item>,
// FIXME: This shouldn't be here, we can derive this from `invoc_attr_index`.
- attr_args: Option<Arc<tt::TopSubtree>>,
+ attr_args: Option<Box<tt::TopSubtree>>,
/// This contains the list of all *active* attributes (derives and attr macros) preceding this
/// attribute, including this attribute. You can retrieve the [`AttrId`] of the current attribute
/// by calling [`invoc_attr()`] on this.
diff --git a/crates/hir-ty/src/consteval.rs b/crates/hir-ty/src/consteval.rs
index 80e7e05d76..87633ad4aa 100644
--- a/crates/hir-ty/src/consteval.rs
+++ b/crates/hir-ty/src/consteval.rs
@@ -16,7 +16,6 @@ use rustc_abi::Size;
use rustc_apfloat::Float;
use rustc_type_ir::inherent::IntoKind;
use stdx::never;
-use triomphe::Arc;
use crate::{
LifetimeElisionKind, ParamEnvAndCrate, TyLoweringContext,
@@ -300,7 +299,7 @@ pub(crate) fn eval_to_const<'db>(expr: ExprId, ctx: &mut InferenceContext<'_, 'd
if let Some(body_owner) = ctx.owner.as_def_with_body()
&& let Ok(mir_body) =
lower_body_to_mir(ctx.db, body_owner, Body::of(ctx.db, body_owner), &infer, expr)
- && let Ok((Ok(result), _)) = interpret_mir(ctx.db, Arc::new(mir_body), true, None)
+ && let Ok((Ok(result), _)) = interpret_mir(ctx.db, &mir_body, true, None)
{
return Const::new_from_allocation(
ctx.interner(),
diff --git a/crates/hir-ty/src/db.rs b/crates/hir-ty/src/db.rs
index 2e130c1028..5dba53a761 100644
--- a/crates/hir-ty/src/db.rs
+++ b/crates/hir-ty/src/db.rs
@@ -37,33 +37,44 @@ pub trait HirDatabase: DefDatabase + std::fmt::Debug {
// FXME: Collapse `mir_body_for_closure` into `mir_body`
// and `monomorphized_mir_body_for_closure` into `monomorphized_mir_body`
- #[salsa::invoke(crate::mir::mir_body_query)]
- #[salsa::cycle(cycle_result = crate::mir::mir_body_cycle_result)]
- fn mir_body(&self, def: DefWithBodyId) -> Result<Arc<MirBody>, MirLowerError>;
+ #[salsa::transparent]
+ fn mir_body(&self, def: DefWithBodyId) -> Result<&MirBody, MirLowerError> {
+ crate::mir::mir_body_query(self, def).as_ref().map_err(|err| err.clone())
+ }
- #[salsa::invoke(crate::mir::mir_body_for_closure_query)]
- fn mir_body_for_closure(&self, def: InternedClosureId) -> Result<Arc<MirBody>, MirLowerError>;
+ #[salsa::transparent]
+ fn mir_body_for_closure(&self, def: InternedClosureId) -> Result<&MirBody, MirLowerError> {
+ crate::mir::mir_body_for_closure_query(self, def).as_ref().map_err(|err| err.clone())
+ }
- #[salsa::invoke(crate::mir::monomorphized_mir_body_query)]
- #[salsa::cycle(cycle_result = crate::mir::monomorphized_mir_body_cycle_result)]
+ #[salsa::transparent]
fn monomorphized_mir_body(
&self,
def: DefWithBodyId,
subst: StoredGenericArgs,
env: StoredParamEnvAndCrate,
- ) -> Result<Arc<MirBody>, MirLowerError>;
+ ) -> Result<&MirBody, MirLowerError> {
+ crate::mir::monomorphized_mir_body_query(self, def, subst, env)
+ .as_ref()
+ .map_err(|err| err.clone())
+ }
- #[salsa::invoke(crate::mir::monomorphized_mir_body_for_closure_query)]
+ #[salsa::transparent]
fn monomorphized_mir_body_for_closure(
&self,
def: InternedClosureId,
subst: StoredGenericArgs,
env: StoredParamEnvAndCrate,
- ) -> Result<Arc<MirBody>, MirLowerError>;
+ ) -> Result<&MirBody, MirLowerError> {
+ crate::mir::monomorphized_mir_body_for_closure_query(self, def, subst, env)
+ .as_ref()
+ .map_err(|err| err.clone())
+ }
- #[salsa::invoke(crate::mir::borrowck_query)]
- #[salsa::lru(2024)]
- fn borrowck(&self, def: DefWithBodyId) -> Result<Arc<[BorrowckResult]>, MirLowerError>;
+ #[salsa::transparent]
+ fn borrowck(&self, def: DefWithBodyId) -> Result<&[BorrowckResult], MirLowerError> {
+ crate::mir::borrowck_query(self, def).as_ref().map(|it| &**it).map_err(|err| err.clone())
+ }
#[salsa::invoke(crate::consteval::const_eval)]
#[salsa::transparent]
@@ -110,8 +121,10 @@ pub trait HirDatabase: DefDatabase + std::fmt::Debug {
env: StoredParamEnvAndCrate,
) -> Result<Arc<Layout>, LayoutError>;
- #[salsa::invoke(crate::layout::target_data_layout_query)]
- fn target_data_layout(&self, krate: Crate) -> Result<Arc<TargetDataLayout>, TargetLoadError>;
+ #[salsa::transparent]
+ fn target_data_layout(&self, krate: Crate) -> Result<&TargetDataLayout, TargetLoadError> {
+ crate::layout::target_data_layout_query(self, krate).as_ref().map_err(|err| err.clone())
+ }
#[salsa::invoke(crate::dyn_compatibility::dyn_compatibility_of_trait_query)]
fn dyn_compatibility_of_trait(&self, trait_: TraitId) -> Option<DynCompatibilityViolation>;
diff --git a/crates/hir-ty/src/display.rs b/crates/hir-ty/src/display.rs
index 2df190bb7a..c300388c5e 100644
--- a/crates/hir-ty/src/display.rs
+++ b/crates/hir-ty/src/display.rs
@@ -974,7 +974,7 @@ fn render_const_scalar_inner<'db>(
return f.write_str("<target-layout-not-available>");
};
let Some((var_id, var_layout)) =
- detect_variant_from_bytes(&layout, f.db, &target_data_layout, b, e)
+ detect_variant_from_bytes(&layout, f.db, target_data_layout, b, e)
else {
return f.write_str("<failed-to-detect-variant>");
};
diff --git a/crates/hir-ty/src/layout.rs b/crates/hir-ty/src/layout.rs
index d2759ddeeb..da0be818f6 100644
--- a/crates/hir-ty/src/layout.rs
+++ b/crates/hir-ty/src/layout.rs
@@ -167,7 +167,7 @@ pub fn layout_of_ty_query(
let Ok(target) = db.target_data_layout(krate) else {
return Err(LayoutError::TargetLayoutNotAvailable);
};
- let dl = &*target;
+ let dl = target;
let cx = LayoutCx::new(dl);
let infer_ctxt = interner.infer_ctxt().build(TypingMode::PostAnalysis);
let cause = ObligationCause::dummy();
@@ -187,7 +187,7 @@ pub fn layout_of_ty_query(
repr.packed(),
&args,
trait_env.as_ref(),
- &target,
+ target,
);
}
}
diff --git a/crates/hir-ty/src/layout/adt.rs b/crates/hir-ty/src/layout/adt.rs
index 6090ddfd45..e77fb139be 100644
--- a/crates/hir-ty/src/layout/adt.rs
+++ b/crates/hir-ty/src/layout/adt.rs
@@ -29,7 +29,7 @@ pub fn layout_of_adt_query(
let Ok(target) = db.target_data_layout(krate) else {
return Err(LayoutError::TargetLayoutNotAvailable);
};
- let dl = &*target;
+ let dl = target;
let cx = LayoutCx::new(dl);
let handle_variant = |def: VariantId, var: &VariantFields| {
var.fields()
diff --git a/crates/hir-ty/src/layout/target.rs b/crates/hir-ty/src/layout/target.rs
index 1752b56b0f..26fa73e76b 100644
--- a/crates/hir-ty/src/layout/target.rs
+++ b/crates/hir-ty/src/layout/target.rs
@@ -3,17 +3,17 @@
use base_db::{Crate, target::TargetLoadError};
use hir_def::layout::TargetDataLayout;
use rustc_abi::{AddressSpace, AlignFromBytesError, TargetDataLayoutError};
-use triomphe::Arc;
use crate::db::HirDatabase;
+#[salsa_macros::tracked(returns(ref))]
pub fn target_data_layout_query(
db: &dyn HirDatabase,
krate: Crate,
-) -> Result<Arc<TargetDataLayout>, TargetLoadError> {
+) -> Result<TargetDataLayout, TargetLoadError> {
match &krate.workspace_data(db).target {
Ok(target) => match TargetDataLayout::parse_from_llvm_datalayout_string(&target.data_layout, AddressSpace::ZERO) {
- Ok(it) => Ok(Arc::new(it)),
+ Ok(it) => Ok(it),
Err(e) => {
Err(match e {
TargetDataLayoutError::InvalidAddressSpace { addr_space, cause, err } => {
diff --git a/crates/hir-ty/src/mir.rs b/crates/hir-ty/src/mir.rs
index a8e06f3a2b..67cc67fd39 100644
--- a/crates/hir-ty/src/mir.rs
+++ b/crates/hir-ty/src/mir.rs
@@ -47,9 +47,6 @@ pub use monomorphization::{
monomorphized_mir_body_for_closure_query, monomorphized_mir_body_query,
};
-pub(crate) use lower::mir_body_cycle_result;
-pub(crate) use monomorphization::monomorphized_mir_body_cycle_result;
-
use super::consteval::try_const_usize;
pub type BasicBlockId = Idx<BasicBlock>;
diff --git a/crates/hir-ty/src/mir/borrowck.rs b/crates/hir-ty/src/mir/borrowck.rs
index 17715d3fcd..dcd06ae25f 100644
--- a/crates/hir-ty/src/mir/borrowck.rs
+++ b/crates/hir-ty/src/mir/borrowck.rs
@@ -5,11 +5,11 @@
use std::iter;
+use either::Either;
use hir_def::{DefWithBodyId, ExpressionStoreOwnerId, HasModule};
use la_arena::ArenaMap;
use rustc_hash::FxHashMap;
use stdx::never;
-use triomphe::Arc;
use crate::{
closure_analysis::ProjectionKind as HirProjectionKind,
@@ -57,68 +57,86 @@ pub struct BorrowRegion {
#[derive(Debug, Clone, PartialEq, Eq)]
pub struct BorrowckResult {
- pub mir_body: Arc<MirBody>,
+ owner: Either<DefWithBodyId, InternedClosureId>,
pub mutability_of_locals: ArenaMap<LocalId, MutabilityReason>,
pub moved_out_of_ref: Vec<MovedOutOfRef>,
pub partially_moved: Vec<PartiallyMoved>,
pub borrow_regions: Vec<BorrowRegion>,
}
-fn all_mir_bodies(
- db: &dyn HirDatabase,
+impl BorrowckResult {
+ pub fn mir_body<'db>(&self, db: &'db dyn HirDatabase) -> &'db MirBody {
+ match self.owner {
+ Either::Left(it) => db.mir_body(it).unwrap(),
+ Either::Right(it) => db.mir_body_for_closure(it).unwrap(),
+ }
+ }
+}
+
+fn all_mir_bodies<'db>(
+ db: &'db dyn HirDatabase,
def: DefWithBodyId,
- mut cb: impl FnMut(Arc<MirBody>) -> BorrowckResult,
- mut merge_from_closures: impl FnMut(&mut BorrowckResult, &BorrowckResult),
-) -> Result<Arc<[BorrowckResult]>, MirLowerError> {
- fn for_closure(
- db: &dyn HirDatabase,
+ mut cb: impl FnMut(&'db MirBody, Either<DefWithBodyId, InternedClosureId>) -> BorrowckResult,
+ mut merge_from_closures: impl FnMut(
+ (&mut BorrowckResult, &'db MirBody),
+ (&BorrowckResult, &'db MirBody),
+ ),
+) -> Result<Box<[BorrowckResult]>, MirLowerError> {
+ fn for_closure<'db>(
+ db: &'db dyn HirDatabase,
c: InternedClosureId,
- results: &mut Vec<BorrowckResult>,
- cb: &mut impl FnMut(Arc<MirBody>) -> BorrowckResult,
- merge_from_closures: &mut impl FnMut(&mut BorrowckResult, &BorrowckResult),
+ results: &mut Vec<(BorrowckResult, &'db MirBody)>,
+ cb: &mut impl FnMut(&'db MirBody, Either<DefWithBodyId, InternedClosureId>) -> BorrowckResult,
+ merge_from_closures: &mut impl FnMut(
+ (&mut BorrowckResult, &'db MirBody),
+ (&BorrowckResult, &'db MirBody),
+ ),
) -> Result<(), MirLowerError> {
match db.mir_body_for_closure(c) {
Ok(body) => {
let parent_index = results.len();
- results.push(cb(body.clone()));
+ results.push((cb(body, Either::Right(c)), body));
body.closures
.iter()
.try_for_each(|&it| for_closure(db, it, results, cb, merge_from_closures))?;
merge(results, merge_from_closures, parent_index);
Ok(())
}
- Err(e) => Err(e),
+ Err(e) => Err(e.clone()),
}
}
- fn merge(
- results: &mut [BorrowckResult],
- merge: &mut impl FnMut(&mut BorrowckResult, &BorrowckResult),
+ fn merge<'db>(
+ results: &mut [(BorrowckResult, &'db MirBody)],
+ merge: &mut impl FnMut((&mut BorrowckResult, &'db MirBody), (&BorrowckResult, &'db MirBody)),
parent_index: usize,
) {
let (parent_and_before, children) = results.split_at_mut(parent_index + 1);
- let parent = &mut parent_and_before[parent_and_before.len() - 1];
- children.iter().for_each(|child| merge(parent, child));
+ let (parent, parent_mir_body) = &mut parent_and_before[parent_and_before.len() - 1];
+ children.iter().for_each(|(child, child_mir_body)| {
+ merge((parent, parent_mir_body), (child, child_mir_body))
+ });
}
let mut results = Vec::new();
match db.mir_body(def) {
Ok(body) => {
- results.push(cb(body.clone()));
+ results.push((cb(body, Either::Left(def)), body));
body.closures.iter().try_for_each(|&it| {
for_closure(db, it, &mut results, &mut cb, &mut merge_from_closures)
})?;
merge(&mut results, &mut merge_from_closures, 0);
- Ok(results.into())
+ Ok(results.into_iter().map(|(it, _)| it).collect())
}
- Err(e) => Err(e),
+ Err(e) => Err(e.clone()),
}
}
+#[salsa_macros::tracked(returns(ref), lru = 2024)]
pub fn borrowck_query(
db: &dyn HirDatabase,
def: DefWithBodyId,
-) -> Result<Arc<[BorrowckResult]>, MirLowerError> {
+) -> Result<Box<[BorrowckResult]>, MirLowerError> {
let _p = tracing::info_span!("borrowck_query").entered();
let module = def.module(db);
let interner = DbInterner::new_with(db, module.krate(db));
@@ -128,20 +146,20 @@ pub fn borrowck_query(
let res = all_mir_bodies(
db,
def,
- |body| {
+ |body, owner| {
// FIXME(next-solver): Opaques.
let infcx = interner.infer_ctxt().build(typing_mode);
BorrowckResult {
- mutability_of_locals: mutability_of_locals(&infcx, env, &body),
- moved_out_of_ref: moved_out_of_ref(&infcx, env, &body),
- partially_moved: partially_moved(&infcx, env, &body),
- borrow_regions: borrow_regions(db, &body),
- mir_body: body,
+ owner,
+ mutability_of_locals: mutability_of_locals(&infcx, env, body),
+ moved_out_of_ref: moved_out_of_ref(&infcx, env, body),
+ partially_moved: partially_moved(&infcx, env, body),
+ borrow_regions: borrow_regions(db, body),
}
},
- |parent, child| {
- for (upvar, child_locals) in &child.mir_body.upvar_locals {
- let Some(&parent_local) = parent.mir_body.binding_locals.get(*upvar) else {
+ |(parent, parent_mir_body), (child, child_mir_body)| {
+ for (upvar, child_locals) in &child_mir_body.upvar_locals {
+ let Some(&parent_local) = parent_mir_body.binding_locals.get(*upvar) else {
continue;
};
for (child_local, capture_place) in child_locals {
diff --git a/crates/hir-ty/src/mir/eval.rs b/crates/hir-ty/src/mir/eval.rs
index 87d64e567e..104b90eaf5 100644
--- a/crates/hir-ty/src/mir/eval.rs
+++ b/crates/hir-ty/src/mir/eval.rs
@@ -156,26 +156,26 @@ impl TlsData {
}
}
-struct StackFrame {
- locals: Locals,
+struct StackFrame<'a> {
+ locals: Locals<'a>,
destination: Option<BasicBlockId>,
prev_stack_ptr: usize,
span: (MirSpan, DefWithBodyId),
}
#[derive(Clone)]
-enum MirOrDynIndex {
- Mir(Arc<MirBody>),
+enum MirOrDynIndex<'a> {
+ Mir(&'a MirBody),
Dyn(usize),
}
-pub struct Evaluator<'db> {
+pub struct Evaluator<'a, 'db> {
db: &'db dyn HirDatabase,
param_env: ParamEnvAndCrate<'db>,
- target_data_layout: Arc<TargetDataLayout>,
+ target_data_layout: &'db TargetDataLayout,
stack: Vec<u8>,
heap: Vec<u8>,
- code_stack: Vec<StackFrame>,
+ code_stack: Vec<StackFrame<'a>>,
/// Stores the global location of the statics. We const evaluate every static first time we need it
/// and see it's missing, then we add it to this to reuse.
static_locations: FxHashMap<StaticId, Address>,
@@ -190,11 +190,11 @@ pub struct Evaluator<'db> {
layout_cache: RefCell<FxHashMap<Ty<'db>, Arc<Layout>>>,
projected_ty_cache: RefCell<FxHashMap<(Ty<'db>, PlaceElem), Ty<'db>>>,
not_special_fn_cache: RefCell<FxHashSet<FunctionId>>,
- mir_or_dyn_index_cache: RefCell<FxHashMap<(FunctionId, GenericArgs<'db>), MirOrDynIndex>>,
+ mir_or_dyn_index_cache: RefCell<FxHashMap<(FunctionId, GenericArgs<'db>), MirOrDynIndex<'a>>>,
/// Constantly dropping and creating `Locals` is very costly. We store
/// old locals that we normally want to drop here, to reuse their allocations
/// later.
- unused_locals_store: RefCell<FxHashMap<DefWithBodyId, Vec<Locals>>>,
+ unused_locals_store: RefCell<FxHashMap<DefWithBodyId, Vec<Locals<'a>>>>,
cached_ptr_size: usize,
cached_fn_trait_func: Option<FunctionId>,
cached_fn_mut_trait_func: Option<FunctionId>,
@@ -237,17 +237,21 @@ impl Interval {
Self { addr, size }
}
- fn get<'a, 'db>(&self, memory: &'a Evaluator<'db>) -> Result<'db, &'a [u8]> {
+ fn get<'b, 'a, 'db: 'a>(&self, memory: &'b Evaluator<'a, 'db>) -> Result<'db, &'b [u8]> {
memory.read_memory(self.addr, self.size)
}
- fn write_from_bytes<'db>(&self, memory: &mut Evaluator<'db>, bytes: &[u8]) -> Result<'db, ()> {
+ fn write_from_bytes<'a, 'db: 'a>(
+ &self,
+ memory: &mut Evaluator<'a, 'db>,
+ bytes: &[u8],
+ ) -> Result<'db, ()> {
memory.write_memory(self.addr, bytes)
}
- fn write_from_interval<'db>(
+ fn write_from_interval<'a, 'db: 'a>(
&self,
- memory: &mut Evaluator<'db>,
+ memory: &mut Evaluator<'a, 'db>,
interval: Interval,
) -> Result<'db, ()> {
memory.copy_from_interval(self.addr, interval)
@@ -259,16 +263,22 @@ impl Interval {
}
impl<'db> IntervalAndTy<'db> {
- fn get<'a>(&self, memory: &'a Evaluator<'db>) -> Result<'db, &'a [u8]> {
+ fn get<'b, 'a>(&self, memory: &'b Evaluator<'a, 'db>) -> Result<'db, &'b [u8]>
+ where
+ 'db: 'a,
+ {
memory.read_memory(self.interval.addr, self.interval.size)
}
- fn new(
+ fn new<'a>(
addr: Address,
ty: Ty<'db>,
- evaluator: &Evaluator<'db>,
- locals: &Locals,
- ) -> Result<'db, IntervalAndTy<'db>> {
+ evaluator: &Evaluator<'a, 'db>,
+ locals: &Locals<'a>,
+ ) -> Result<'db, IntervalAndTy<'db>>
+ where
+ 'db: 'a,
+ {
let size = evaluator.size_of_sized(ty, locals, "type of interval")?;
Ok(IntervalAndTy { interval: Interval { addr, size }, ty })
}
@@ -286,7 +296,7 @@ impl From<Interval> for IntervalOrOwned {
}
impl IntervalOrOwned {
- fn get<'a, 'db>(&'a self, memory: &'a Evaluator<'db>) -> Result<'db, &'a [u8]> {
+ fn get<'b, 'a, 'db: 'a>(&'b self, memory: &'b Evaluator<'a, 'db>) -> Result<'db, &'b [u8]> {
Ok(match self {
IntervalOrOwned::Owned(o) => o,
IntervalOrOwned::Borrowed(b) => b.get(memory)?,
@@ -576,9 +586,9 @@ impl DropFlags {
}
#[derive(Debug)]
-struct Locals {
+struct Locals<'a> {
ptr: ArenaMap<LocalId, Interval>,
- body: Arc<MirBody>,
+ body: &'a MirBody,
drop_flags: DropFlags,
}
@@ -596,9 +606,9 @@ impl MirOutput {
}
}
-pub fn interpret_mir<'db>(
+pub fn interpret_mir<'a, 'db: 'a>(
db: &'db dyn HirDatabase,
- body: Arc<MirBody>,
+ body: &MirBody,
// FIXME: This is workaround. Ideally, const generics should have a separate body (issue #7434), but now
// they share their body with their parent, so in MIR lowering we have locals of the parent body, which
// might have placeholders. With this argument, we (wrongly) assume that every placeholder type has
@@ -613,7 +623,7 @@ pub fn interpret_mir<'db>(
if evaluator.ptr_size() != size_of::<usize>() {
not_supported!("targets with different pointer size from host");
}
- let interval = evaluator.interpret_mir(body.clone(), None.into_iter())?;
+ let interval = evaluator.interpret_mir(body, None.into_iter())?;
let bytes = interval.get(&evaluator)?;
let mut memory_map = evaluator.create_memory_map(
bytes,
@@ -638,13 +648,13 @@ const EXECUTION_LIMIT: usize = 100_000;
#[cfg(not(test))]
const EXECUTION_LIMIT: usize = 10_000_000;
-impl<'db> Evaluator<'db> {
+impl<'a, 'db: 'a> Evaluator<'a, 'db> {
pub fn new(
db: &'db dyn HirDatabase,
owner: DefWithBodyId,
assert_placeholder_ty_is_unused: bool,
trait_env: Option<ParamEnvAndCrate<'db>>,
- ) -> Result<'db, Evaluator<'db>> {
+ ) -> Result<'db, Evaluator<'a, 'db>> {
let module = owner.module(db);
let crate_id = module.krate(db);
let target_data_layout = match db.target_data_layout(crate_id) {
@@ -705,11 +715,11 @@ impl<'db> Evaluator<'db> {
self.infcx.interner.lang_items()
}
- fn place_addr(&self, p: &Place, locals: &Locals) -> Result<'db, Address> {
+ fn place_addr(&self, p: &Place, locals: &Locals<'a>) -> Result<'db, Address> {
Ok(self.place_addr_and_ty_and_metadata(p, locals)?.0)
}
- fn place_interval(&self, p: &Place, locals: &Locals) -> Result<'db, Interval> {
+ fn place_interval(&self, p: &Place, locals: &Locals<'a>) -> Result<'db, Interval> {
let place_addr_and_ty = self.place_addr_and_ty_and_metadata(p, locals)?;
Ok(Interval {
addr: place_addr_and_ty.0,
@@ -736,10 +746,10 @@ impl<'db> Evaluator<'db> {
r
}
- fn place_addr_and_ty_and_metadata<'a>(
- &'a self,
+ fn place_addr_and_ty_and_metadata<'b>(
+ &'b self,
p: &Place,
- locals: &'a Locals,
+ locals: &'b Locals<'a>,
) -> Result<'db, (Address, Ty<'db>, Option<IntervalOrOwned>)> {
let mut addr = locals.ptr[p.local].addr;
let mut ty: Ty<'db> = locals.body.locals[p.local].ty.as_ref();
@@ -873,11 +883,11 @@ impl<'db> Evaluator<'db> {
self.layout(Ty::new_adt(self.interner(), adt, subst))
}
- fn place_ty<'a>(&'a self, p: &Place, locals: &'a Locals) -> Result<'db, Ty<'db>> {
+ fn place_ty<'b>(&'b self, p: &Place, locals: &'b Locals<'a>) -> Result<'db, Ty<'db>> {
Ok(self.place_addr_and_ty_and_metadata(p, locals)?.1)
}
- fn operand_ty(&self, o: &Operand, locals: &Locals) -> Result<'db, Ty<'db>> {
+ fn operand_ty(&self, o: &Operand, locals: &Locals<'a>) -> Result<'db, Ty<'db>> {
Ok(match &o.kind {
OperandKind::Copy(p) | OperandKind::Move(p) => self.place_ty(p, locals)?,
OperandKind::Constant { konst: _, ty } => ty.as_ref(),
@@ -898,7 +908,7 @@ impl<'db> Evaluator<'db> {
fn operand_ty_and_eval(
&mut self,
o: &Operand,
- locals: &mut Locals,
+ locals: &mut Locals<'a>,
) -> Result<'db, IntervalAndTy<'db>> {
Ok(IntervalAndTy {
interval: self.eval_operand(o, locals)?,
@@ -908,7 +918,7 @@ impl<'db> Evaluator<'db> {
fn interpret_mir(
&mut self,
- body: Arc<MirBody>,
+ body: &'a MirBody,
args: impl Iterator<Item = IntervalOrOwned>,
) -> Result<'db, Interval> {
if let Some(it) = self.stack_depth_limit.checked_sub(1) {
@@ -917,8 +927,8 @@ impl<'db> Evaluator<'db> {
return Err(MirEvalError::StackOverflow);
}
let mut current_block_idx = body.start_block;
- let (mut locals, prev_stack_ptr) = self.create_locals_for_body(&body, None)?;
- self.fill_locals_for_body(&body, &mut locals, args)?;
+ let (mut locals, prev_stack_ptr) = self.create_locals_for_body(body, None)?;
+ self.fill_locals_for_body(body, &mut locals, args)?;
let prev_code_stack = mem::take(&mut self.code_stack);
let span = (MirSpan::Unknown, body.owner);
self.code_stack.push(StackFrame { locals, destination: None, prev_stack_ptr, span });
@@ -1073,7 +1083,7 @@ impl<'db> Evaluator<'db> {
fn fill_locals_for_body(
&mut self,
body: &MirBody,
- locals: &mut Locals,
+ locals: &mut Locals<'a>,
args: impl Iterator<Item = IntervalOrOwned>,
) -> Result<'db, ()> {
let mut remain_args = body.param_locals.len();
@@ -1096,19 +1106,15 @@ impl<'db> Evaluator<'db> {
fn create_locals_for_body(
&mut self,
- body: &Arc<MirBody>,
+ body: &'a MirBody,
destination: Option<Interval>,
- ) -> Result<'db, (Locals, usize)> {
+ ) -> Result<'db, (Locals<'a>, usize)> {
let mut locals =
match self.unused_locals_store.borrow_mut().entry(body.owner).or_default().pop() {
- None => Locals {
- ptr: ArenaMap::new(),
- body: body.clone(),
- drop_flags: DropFlags::default(),
- },
+ None => Locals { ptr: ArenaMap::new(), body, drop_flags: DropFlags::default() },
Some(mut l) => {
l.drop_flags.clear();
- l.body = body.clone();
+ l.body = body;
l
}
};
@@ -1145,7 +1151,7 @@ impl<'db> Evaluator<'db> {
Ok((locals, prev_stack_pointer))
}
- fn eval_rvalue(&mut self, r: &Rvalue, locals: &mut Locals) -> Result<'db, IntervalOrOwned> {
+ fn eval_rvalue(&mut self, r: &Rvalue, locals: &mut Locals<'a>) -> Result<'db, IntervalOrOwned> {
use IntervalOrOwned::*;
Ok(match r {
Rvalue::Use(it) => Borrowed(self.eval_operand(it, locals)?),
@@ -1662,7 +1668,7 @@ impl<'db> Evaluator<'db> {
Ok(r)
}
Variants::Multiple { tag, tag_encoding, variants, .. } => {
- let size = tag.size(&*self.target_data_layout).bytes_usize();
+ let size = tag.size(self.target_data_layout).bytes_usize();
let offset = layout.fields.offset(0).bytes_usize(); // The only field on enum variants is the tag field
let is_signed = tag.is_signed();
match tag_encoding {
@@ -1804,7 +1810,7 @@ impl<'db> Evaluator<'db> {
&mut self,
it: VariantId,
subst: GenericArgs<'db>,
- locals: &Locals,
+ locals: &Locals<'a>,
) -> Result<'db, (usize, Arc<Layout>, Option<(usize, usize, i128)>)> {
let adt = it.adt_id(self.db);
if let DefWithBodyId::VariantId(f) = locals.body.owner
@@ -1851,7 +1857,7 @@ impl<'db> Evaluator<'db> {
if have_tag {
Some((
layout.fields.offset(0).bytes_usize(),
- tag.size(&*self.target_data_layout).bytes_usize(),
+ tag.size(self.target_data_layout).bytes_usize(),
discriminant,
))
} else {
@@ -1898,7 +1904,7 @@ impl<'db> Evaluator<'db> {
Ok(result)
}
- fn eval_operand(&mut self, it: &Operand, locals: &mut Locals) -> Result<'db, Interval> {
+ fn eval_operand(&mut self, it: &Operand, locals: &mut Locals<'a>) -> Result<'db, Interval> {
Ok(match &it.kind {
OperandKind::Copy(p) | OperandKind::Move(p) => {
locals.drop_flags.remove_place(p, &locals.body.projection_store);
@@ -2051,7 +2057,7 @@ impl<'db> Evaluator<'db> {
#[allow(clippy::double_parens)]
fn allocate_const_in_heap(
&mut self,
- locals: &Locals,
+ locals: &Locals<'a>,
konst: Const<'db>,
) -> Result<'db, Interval> {
match konst.kind() {
@@ -2089,7 +2095,7 @@ impl<'db> Evaluator<'db> {
fn allocate_allocation_in_heap(
&mut self,
- locals: &Locals,
+ locals: &Locals<'a>,
allocation: Allocation<'db>,
) -> Result<'db, Interval> {
let AllocationData { ty, memory: ref v, ref memory_map } = *allocation;
@@ -2128,7 +2134,7 @@ impl<'db> Evaluator<'db> {
Ok(Interval::new(addr, size))
}
- fn eval_place(&mut self, p: &Place, locals: &Locals) -> Result<'db, Interval> {
+ fn eval_place(&mut self, p: &Place, locals: &Locals<'a>) -> Result<'db, Interval> {
let addr = self.place_addr(p, locals)?;
Ok(Interval::new(
addr,
@@ -2228,7 +2234,11 @@ impl<'db> Evaluator<'db> {
Ok(())
}
- fn size_align_of(&self, ty: Ty<'db>, locals: &Locals) -> Result<'db, Option<(usize, usize)>> {
+ fn size_align_of(
+ &self,
+ ty: Ty<'db>,
+ locals: &Locals<'a>,
+ ) -> Result<'db, Option<(usize, usize)>> {
if let Some(layout) = self.layout_cache.borrow().get(&ty) {
return Ok(layout
.is_sized()
@@ -2257,7 +2267,7 @@ impl<'db> Evaluator<'db> {
fn size_of_sized(
&self,
ty: Ty<'db>,
- locals: &Locals,
+ locals: &Locals<'a>,
what: &'static str,
) -> Result<'db, usize> {
match self.size_align_of(ty, locals)? {
@@ -2271,7 +2281,7 @@ impl<'db> Evaluator<'db> {
fn size_align_of_sized(
&self,
ty: Ty<'db>,
- locals: &Locals,
+ locals: &Locals<'a>,
what: &'static str,
) -> Result<'db, (usize, usize)> {
match self.size_align_of(ty, locals)? {
@@ -2312,13 +2322,13 @@ impl<'db> Evaluator<'db> {
&self,
bytes: &[u8],
ty: Ty<'db>,
- locals: &Locals,
+ locals: &Locals<'a>,
) -> Result<'db, ComplexMemoryMap<'db>> {
- fn rec<'db>(
- this: &Evaluator<'db>,
+ fn rec<'a, 'db: 'a>(
+ this: &Evaluator<'a, 'db>,
bytes: &[u8],
ty: Ty<'db>,
- locals: &Locals,
+ locals: &Locals<'a>,
mm: &mut ComplexMemoryMap<'db>,
stack_depth_limit: usize,
) -> Result<'db, ()> {
@@ -2436,7 +2446,7 @@ impl<'db> Evaluator<'db> {
if let Some((v, l)) = detect_variant_from_bytes(
&layout,
this.db,
- &this.target_data_layout,
+ this.target_data_layout,
bytes,
e,
) {
@@ -2487,7 +2497,7 @@ impl<'db> Evaluator<'db> {
ty_of_bytes: impl Fn(&[u8]) -> Result<'db, Ty<'db>> + Copy,
addr: Address,
ty: Ty<'db>,
- locals: &Locals,
+ locals: &Locals<'a>,
) -> Result<'db, ()> {
// FIXME: support indirect references
let layout = self.layout(ty)?;
@@ -2546,7 +2556,7 @@ impl<'db> Evaluator<'db> {
if let Some((ev, layout)) = detect_variant_from_bytes(
&layout,
self.db,
- &self.target_data_layout,
+ self.target_data_layout,
self.read_memory(addr, layout.size.bytes_usize())?,
e,
) {
@@ -2619,10 +2629,10 @@ impl<'db> Evaluator<'db> {
bytes: Interval,
destination: Interval,
args: &[IntervalAndTy<'db>],
- locals: &Locals,
+ locals: &Locals<'a>,
target_bb: Option<BasicBlockId>,
span: MirSpan,
- ) -> Result<'db, Option<StackFrame>> {
+ ) -> Result<'db, Option<StackFrame<'a>>> {
let id = from_bytes!(usize, bytes.get(self)?);
let next_ty = self.vtable_map.ty(id)?;
use rustc_type_ir::TyKind;
@@ -2650,9 +2660,9 @@ impl<'db> Evaluator<'db> {
generic_args: GenericArgs<'db>,
destination: Interval,
args: &[IntervalAndTy<'db>],
- locals: &Locals,
+ locals: &Locals<'a>,
span: MirSpan,
- ) -> Result<'db, Option<StackFrame>> {
+ ) -> Result<'db, Option<StackFrame<'a>>> {
let mir_body = self
.db
.monomorphized_mir_body_for_closure(
@@ -2688,10 +2698,10 @@ impl<'db> Evaluator<'db> {
generic_args: GenericArgs<'db>,
destination: Interval,
args: &[IntervalAndTy<'db>],
- locals: &Locals,
+ locals: &Locals<'a>,
target_bb: Option<BasicBlockId>,
span: MirSpan,
- ) -> Result<'db, Option<StackFrame>> {
+ ) -> Result<'db, Option<StackFrame<'a>>> {
match def {
CallableDefId::FunctionId(def) => {
if self.detect_fn_trait(def).is_some() {
@@ -2746,9 +2756,9 @@ impl<'db> Evaluator<'db> {
&self,
def: FunctionId,
generic_args: GenericArgs<'db>,
- locals: &Locals,
+ locals: &Locals<'a>,
span: MirSpan,
- ) -> Result<'db, MirOrDynIndex> {
+ ) -> Result<'db, MirOrDynIndex<'a>> {
let pair = (def, generic_args);
if let Some(r) = self.mir_or_dyn_index_cache.borrow().get(&pair) {
return Ok(r.clone());
@@ -2788,11 +2798,11 @@ impl<'db> Evaluator<'db> {
mut def: FunctionId,
args: &[IntervalAndTy<'db>],
generic_args: GenericArgs<'db>,
- locals: &Locals,
+ locals: &Locals<'a>,
destination: Interval,
target_bb: Option<BasicBlockId>,
span: MirSpan,
- ) -> Result<'db, Option<StackFrame>> {
+ ) -> Result<'db, Option<StackFrame<'a>>> {
if self.detect_and_exec_special_function(
def,
args,
@@ -2854,18 +2864,18 @@ impl<'db> Evaluator<'db> {
fn exec_looked_up_function(
&mut self,
- mir_body: Arc<MirBody>,
- locals: &Locals,
+ mir_body: &'a MirBody,
+ locals: &Locals<'a>,
def: FunctionId,
arg_bytes: impl Iterator<Item = IntervalOrOwned>,
span: MirSpan,
destination: Interval,
target_bb: Option<BasicBlockId>,
- ) -> Result<'db, Option<StackFrame>> {
+ ) -> Result<'db, Option<StackFrame<'a>>> {
Ok(if let Some(target_bb) = target_bb {
let (mut locals, prev_stack_ptr) =
- self.create_locals_for_body(&mir_body, Some(destination))?;
- self.fill_locals_for_body(&mir_body, &mut locals, arg_bytes.into_iter())?;
+ self.create_locals_for_body(mir_body, Some(destination))?;
+ self.fill_locals_for_body(mir_body, &mut locals, arg_bytes.into_iter())?;
let span = (span, locals.body.owner);
Some(StackFrame { locals, destination: Some(target_bb), prev_stack_ptr, span })
} else {
@@ -2885,11 +2895,11 @@ impl<'db> Evaluator<'db> {
def: FunctionId,
args: &[IntervalAndTy<'db>],
generic_args: GenericArgs<'db>,
- locals: &Locals,
+ locals: &Locals<'a>,
destination: Interval,
target_bb: Option<BasicBlockId>,
span: MirSpan,
- ) -> Result<'db, Option<StackFrame>> {
+ ) -> Result<'db, Option<StackFrame<'a>>> {
let func = args
.first()
.ok_or_else(|| MirEvalError::InternalError("fn trait with no arg".into()))?;
@@ -2954,7 +2964,7 @@ impl<'db> Evaluator<'db> {
}
}
- fn eval_static(&mut self, st: StaticId, locals: &Locals) -> Result<'db, Address> {
+ fn eval_static(&mut self, st: StaticId, locals: &Locals<'a>) -> Result<'db, Address> {
if let Some(o) = self.static_locations.get(&st) {
return Ok(*o);
};
@@ -3001,7 +3011,12 @@ impl<'db> Evaluator<'db> {
}
}
- fn drop_place(&mut self, place: &Place, locals: &mut Locals, span: MirSpan) -> Result<'db, ()> {
+ fn drop_place(
+ &mut self,
+ place: &Place,
+ locals: &mut Locals<'a>,
+ span: MirSpan,
+ ) -> Result<'db, ()> {
let (addr, ty, metadata) = self.place_addr_and_ty_and_metadata(place, locals)?;
if !locals.drop_flags.remove_place(place, &locals.body.projection_store) {
return Ok(());
@@ -3016,7 +3031,7 @@ impl<'db> Evaluator<'db> {
fn run_drop_glue_deep(
&mut self,
ty: Ty<'db>,
- locals: &Locals,
+ locals: &Locals<'a>,
addr: Address,
_metadata: &[u8],
span: MirSpan,
diff --git a/crates/hir-ty/src/mir/eval/shim.rs b/crates/hir-ty/src/mir/eval/shim.rs
index 4154760f6e..a0978bd6e8 100644
--- a/crates/hir-ty/src/mir/eval/shim.rs
+++ b/crates/hir-ty/src/mir/eval/shim.rs
@@ -29,13 +29,13 @@ enum EvalLangItem {
DropInPlace,
}
-impl<'db> Evaluator<'db> {
+impl<'a, 'db: 'a> Evaluator<'a, 'db> {
pub(super) fn detect_and_exec_special_function(
&mut self,
def: FunctionId,
args: &[IntervalAndTy<'db>],
generic_args: GenericArgs<'db>,
- locals: &Locals,
+ locals: &Locals<'a>,
destination: Interval,
span: MirSpan,
) -> Result<'db, bool> {
@@ -132,7 +132,7 @@ impl<'db> Evaluator<'db> {
def: FunctionId,
args: &[IntervalAndTy<'db>],
self_ty: Ty<'db>,
- locals: &Locals,
+ locals: &Locals<'a>,
destination: Interval,
span: MirSpan,
) -> Result<'db, ()> {
@@ -190,7 +190,7 @@ impl<'db> Evaluator<'db> {
layout: Arc<Layout>,
addr: Address,
def: FunctionId,
- locals: &Locals,
+ locals: &Locals<'a>,
destination: Interval,
span: MirSpan,
) -> Result<'db, ()> {
@@ -296,7 +296,7 @@ impl<'db> Evaluator<'db> {
it: EvalLangItem,
generic_args: GenericArgs<'db>,
args: &[IntervalAndTy<'db>],
- locals: &Locals,
+ locals: &Locals<'a>,
span: MirSpan,
) -> Result<'db, Vec<u8>> {
use EvalLangItem::*;
@@ -368,7 +368,7 @@ impl<'db> Evaluator<'db> {
id: i64,
args: &[IntervalAndTy<'db>],
destination: Interval,
- _locals: &Locals,
+ _locals: &Locals<'a>,
_span: MirSpan,
) -> Result<'db, ()> {
match id {
@@ -399,7 +399,7 @@ impl<'db> Evaluator<'db> {
args: &[IntervalAndTy<'db>],
_generic_args: GenericArgs<'db>,
destination: Interval,
- locals: &Locals,
+ locals: &Locals<'a>,
span: MirSpan,
) -> Result<'db, ()> {
match as_str {
@@ -563,7 +563,7 @@ impl<'db> Evaluator<'db> {
args: &[IntervalAndTy<'db>],
generic_args: GenericArgs<'db>,
destination: Interval,
- locals: &Locals,
+ locals: &Locals<'a>,
span: MirSpan,
needs_override: bool,
) -> Result<'db, bool> {
@@ -1345,7 +1345,7 @@ impl<'db> Evaluator<'db> {
&mut self,
ty: Ty<'db>,
metadata: Interval,
- locals: &Locals,
+ locals: &Locals<'a>,
) -> Result<'db, (usize, usize)> {
Ok(match ty.kind() {
TyKind::Str => (from_bytes!(usize, metadata.get(self)?), 1),
@@ -1404,7 +1404,7 @@ impl<'db> Evaluator<'db> {
args: &[IntervalAndTy<'db>],
generic_args: GenericArgs<'db>,
destination: Interval,
- locals: &Locals,
+ locals: &Locals<'a>,
_span: MirSpan,
) -> Result<'db, ()> {
// We are a single threaded runtime with no UB checking and no optimization, so
diff --git a/crates/hir-ty/src/mir/eval/shim/simd.rs b/crates/hir-ty/src/mir/eval/shim/simd.rs
index 6e20562b4e..2458597ff4 100644
--- a/crates/hir-ty/src/mir/eval/shim/simd.rs
+++ b/crates/hir-ty/src/mir/eval/shim/simd.rs
@@ -6,7 +6,7 @@ use crate::consteval::try_const_usize;
use super::*;
-impl<'db> Evaluator<'db> {
+impl<'a, 'db: 'a> Evaluator<'a, 'db> {
fn detect_simd_ty(&self, ty: Ty<'db>) -> Result<'db, (usize, Ty<'db>)> {
match ty.kind() {
TyKind::Adt(adt_def, subst) => {
@@ -53,7 +53,7 @@ impl<'db> Evaluator<'db> {
args: &[IntervalAndTy<'db>],
_generic_args: GenericArgs<'db>,
destination: Interval,
- _locals: &Locals,
+ _locals: &Locals<'a>,
_span: MirSpan,
) -> Result<'db, ()> {
match name {
diff --git a/crates/hir-ty/src/mir/lower.rs b/crates/hir-ty/src/mir/lower.rs
index 9c9cf0ac0b..b2a7eaa674 100644
--- a/crates/hir-ty/src/mir/lower.rs
+++ b/crates/hir-ty/src/mir/lower.rs
@@ -25,7 +25,6 @@ use rustc_hash::FxHashMap;
use rustc_type_ir::inherent::{Const as _, GenericArgs as _, IntoKind, Ty as _};
use span::{Edition, FileId};
use syntax::TextRange;
-use triomphe::Arc;
use crate::{
Adjust, Adjustment, AutoBorrow, CallableDefId, ParamEnvAndCrate,
@@ -2137,10 +2136,11 @@ fn cast_kind<'db>(
})
}
+#[salsa_macros::tracked(returns(ref), cycle_result = mir_body_for_closure_cycle_result)]
pub fn mir_body_for_closure_query<'db>(
db: &'db dyn HirDatabase,
closure: InternedClosureId,
-) -> Result<'db, Arc<MirBody>> {
+) -> Result<'db, MirBody> {
let InternedClosure { owner, expr, .. } = closure.loc(db);
let body_owner =
owner.as_def_with_body().expect("MIR lowering should only happen for body-owned closures");
@@ -2293,13 +2293,11 @@ pub fn mir_body_for_closure_query<'db>(
return Err(MirLowerError::UnresolvedUpvar(err));
}
ctx.result.shrink_to_fit();
- Ok(Arc::new(ctx.result))
+ Ok(ctx.result)
}
-pub fn mir_body_query<'db>(
- db: &'db dyn HirDatabase,
- def: DefWithBodyId,
-) -> Result<'db, Arc<MirBody>> {
+#[salsa_macros::tracked(returns(ref), cycle_result = mir_body_cycle_result)]
+pub fn mir_body_query<'db>(db: &'db dyn HirDatabase, def: DefWithBodyId) -> Result<'db, MirBody> {
let krate = def.krate(db);
let edition = krate.data(db).edition;
let detail = match def {
@@ -2328,14 +2326,22 @@ pub fn mir_body_query<'db>(
let infer = InferenceResult::of(db, def);
let mut result = lower_body_to_mir(db, def, body, infer, body.root_expr())?;
result.shrink_to_fit();
- Ok(Arc::new(result))
+ Ok(result)
}
-pub(crate) fn mir_body_cycle_result<'db>(
+fn mir_body_cycle_result<'db>(
_db: &'db dyn HirDatabase,
_: salsa::Id,
_def: DefWithBodyId,
-) -> Result<'db, Arc<MirBody>> {
+) -> Result<'db, MirBody> {
+ Err(MirLowerError::Loop)
+}
+
+fn mir_body_for_closure_cycle_result<'db>(
+ _db: &'db dyn HirDatabase,
+ _: salsa::Id,
+ _def: InternedClosureId,
+) -> Result<'db, MirBody> {
Err(MirLowerError::Loop)
}
diff --git a/crates/hir-ty/src/mir/monomorphization.rs b/crates/hir-ty/src/mir/monomorphization.rs
index dfce8ca2a5..b3529437c0 100644
--- a/crates/hir-ty/src/mir/monomorphization.rs
+++ b/crates/hir-ty/src/mir/monomorphization.rs
@@ -12,7 +12,6 @@ use rustc_type_ir::inherent::IntoKind;
use rustc_type_ir::{
FallibleTypeFolder, TypeFlags, TypeFoldable, TypeSuperFoldable, TypeVisitableExt,
};
-use triomphe::Arc;
use crate::{
ParamEnvAndCrate,
@@ -240,38 +239,50 @@ impl<'db> Filler<'db> {
}
}
+#[salsa_macros::tracked(returns(ref), cycle_result = monomorphized_mir_body_cycle_result)]
pub fn monomorphized_mir_body_query(
db: &dyn HirDatabase,
owner: DefWithBodyId,
subst: StoredGenericArgs,
trait_env: StoredParamEnvAndCrate,
-) -> Result<Arc<MirBody>, MirLowerError> {
+) -> Result<MirBody, MirLowerError> {
let mut filler = Filler::new(db, trait_env.as_ref(), subst.as_ref());
let body = db.mir_body(owner)?;
let mut body = (*body).clone();
filler.fill_body(&mut body)?;
- Ok(Arc::new(body))
+ Ok(body)
}
-pub(crate) fn monomorphized_mir_body_cycle_result(
+fn monomorphized_mir_body_cycle_result(
_db: &dyn HirDatabase,
_: salsa::Id,
_: DefWithBodyId,
_: StoredGenericArgs,
_: StoredParamEnvAndCrate,
-) -> Result<Arc<MirBody>, MirLowerError> {
+) -> Result<MirBody, MirLowerError> {
Err(MirLowerError::Loop)
}
+#[salsa_macros::tracked(returns(ref), cycle_result = monomorphized_mir_body_for_closure_cycle_result)]
pub fn monomorphized_mir_body_for_closure_query(
db: &dyn HirDatabase,
closure: InternedClosureId,
subst: StoredGenericArgs,
trait_env: StoredParamEnvAndCrate,
-) -> Result<Arc<MirBody>, MirLowerError> {
+) -> Result<MirBody, MirLowerError> {
let mut filler = Filler::new(db, trait_env.as_ref(), subst.as_ref());
let body = db.mir_body_for_closure(closure)?;
let mut body = (*body).clone();
filler.fill_body(&mut body)?;
- Ok(Arc::new(body))
+ Ok(body)
+}
+
+fn monomorphized_mir_body_for_closure_cycle_result(
+ _db: &dyn HirDatabase,
+ _: salsa::Id,
+ _: InternedClosureId,
+ _: StoredGenericArgs,
+ _: StoredParamEnvAndCrate,
+) -> Result<MirBody, MirLowerError> {
+ Err(MirLowerError::Loop)
}
diff --git a/crates/hir-ty/src/mir/pretty.rs b/crates/hir-ty/src/mir/pretty.rs
index de5ee223a1..c224f2054f 100644
--- a/crates/hir-ty/src/mir/pretty.rs
+++ b/crates/hir-ty/src/mir/pretty.rs
@@ -160,7 +160,7 @@ impl<'a, 'db> MirPrettyCtx<'a, 'db> {
let result = mem::take(&mut self.result);
let indent = mem::take(&mut self.indent);
let mut ctx = MirPrettyCtx {
- body: &body,
+ body,
local_to_binding: body.local_to_binding_map(),
result,
indent,
diff --git a/crates/hir/src/lib.rs b/crates/hir/src/lib.rs
index 6f5508691e..b74f594ebe 100644
--- a/crates/hir/src/lib.rs
+++ b/crates/hir/src/lib.rs
@@ -1120,7 +1120,7 @@ fn macro_call_diagnostics<'db>(
let Some(e) = db.parse_macro_expansion_error(macro_call_id) else {
return;
};
- let ValueResult { value: parse_errors, err } = &*e;
+ let ValueResult { value: parse_errors, err } = e;
if let Some(err) = err {
let loc = db.lookup_intern_macro_call(macro_call_id);
let file_id = loc.kind.file_id();
@@ -1436,7 +1436,7 @@ impl Field {
Type::new(db, var_id, ty)
}
- pub fn layout(&self, db: &dyn HirDatabase) -> Result<Layout, LayoutError> {
+ pub fn layout<'db>(&self, db: &'db dyn HirDatabase) -> Result<Layout<'db>, LayoutError> {
db.layout_of_ty(
self.ty(db).ty.store(),
param_env_from_has_crate(
@@ -1696,7 +1696,7 @@ impl Enum {
self.variants(db).iter().any(|v| !matches!(v.kind(db), StructKind::Unit))
}
- pub fn layout(self, db: &dyn HirDatabase) -> Result<Layout, LayoutError> {
+ pub fn layout<'db>(self, db: &'db dyn HirDatabase) -> Result<Layout<'db>, LayoutError> {
Adt::from(self).layout(db)
}
@@ -1783,7 +1783,7 @@ impl EnumVariant {
db.const_eval_discriminant(self.into())
}
- pub fn layout(&self, db: &dyn HirDatabase) -> Result<Layout, LayoutError> {
+ pub fn layout<'db>(&self, db: &'db dyn HirDatabase) -> Result<Layout<'db>, LayoutError> {
let parent_enum = self.parent_enum(db);
let parent_layout = parent_enum.layout(db)?;
Ok(match &parent_layout.0.variants {
@@ -1866,7 +1866,7 @@ impl Adt {
has_non_default_type_params(db, self.into())
}
- pub fn layout(self, db: &dyn HirDatabase) -> Result<Layout, LayoutError> {
+ pub fn layout<'db>(self, db: &'db dyn HirDatabase) -> Result<Layout<'db>, LayoutError> {
let interner = DbInterner::new_no_crate(db);
let adt_id = AdtId::from(self);
let args = GenericArgs::for_item_with_defaults(interner, adt_id.into(), |_, id, _| {
@@ -2211,7 +2211,7 @@ impl DefWithBody {
if let Ok(borrowck_results) = db.borrowck(id) {
for borrowck_result in borrowck_results.iter() {
- let mir_body = &borrowck_result.mir_body;
+ let mir_body = borrowck_result.mir_body(db);
for moof in &borrowck_result.moved_out_of_ref {
let span: InFile<SyntaxNodePtr> = match moof.span {
mir::MirSpan::ExprId(e) => match source_map.expr_syntax(e) {
@@ -6530,7 +6530,7 @@ impl<'db> Type<'db> {
.collect()
}
- pub fn layout(&self, db: &'db dyn HirDatabase) -> Result<Layout, LayoutError> {
+ pub fn layout(&self, db: &'db dyn HirDatabase) -> Result<Layout<'db>, LayoutError> {
db.layout_of_ty(self.ty.store(), self.env.store())
.map(|layout| Layout(layout, db.target_data_layout(self.env.krate).unwrap()))
}
@@ -6702,9 +6702,9 @@ impl<'db> Callable<'db> {
}
#[derive(Clone, Debug, Eq, PartialEq)]
-pub struct Layout(Arc<TyLayout>, Arc<TargetDataLayout>);
+pub struct Layout<'db>(Arc<TyLayout>, &'db TargetDataLayout);
-impl Layout {
+impl<'db> Layout<'db> {
pub fn size(&self) -> u64 {
self.0.size.bytes()
}
@@ -6714,7 +6714,7 @@ impl Layout {
}
pub fn niches(&self) -> Option<u128> {
- Some(self.0.largest_niche?.available(&*self.1))
+ Some(self.0.largest_niche?.available(self.1))
}
pub fn field_offset(&self, field: Field) -> Option<u64> {
@@ -6803,7 +6803,7 @@ impl Layout {
let tag_size =
if let layout::Variants::Multiple { tag, tag_encoding, .. } = &self.0.variants {
match tag_encoding {
- TagEncoding::Direct => tag.size(&*self.1).bytes_usize(),
+ TagEncoding::Direct => tag.size(self.1).bytes_usize(),
TagEncoding::Niche { .. } => 0,
}
} else {
diff --git a/crates/hir/src/term_search/tactics.rs b/crates/hir/src/term_search/tactics.rs
index b11f7a1723..99ad1e0739 100644
--- a/crates/hir/src/term_search/tactics.rs
+++ b/crates/hir/src/term_search/tactics.rs
@@ -56,11 +56,12 @@ pub(super) fn trivial<'a, 'lt, 'db, DB: HirDatabase>(
let borrowck = db.borrowck(it.parent.as_def_with_body()?).ok()?;
let invalid = borrowck.iter().any(|b| {
+ let mir_body = b.mir_body(ctx.sema.db);
b.partially_moved.iter().any(|moved| {
- Some(&moved.local) == b.mir_body.binding_locals.get(it.binding_id)
+ Some(&moved.local) == mir_body.binding_locals.get(it.binding_id)
}) || b.borrow_regions.iter().any(|region| {
// Shared borrows are fine
- Some(&region.local) == b.mir_body.binding_locals.get(it.binding_id)
+ Some(&region.local) == mir_body.binding_locals.get(it.binding_id)
&& region.kind != BorrowKind::Shared
})
});
diff --git a/crates/ide/src/hover/render.rs b/crates/ide/src/hover/render.rs
index 4f60321e32..e08bbc5c21 100644
--- a/crates/ide/src/hover/render.rs
+++ b/crates/ide/src/hover/render.rs
@@ -1136,12 +1136,12 @@ fn markup(
}
}
-fn render_memory_layout(
+fn render_memory_layout<'db>(
config: Option<MemoryLayoutHoverConfig>,
- layout: impl FnOnce() -> Result<Layout, LayoutError>,
- offset: impl FnOnce(&Layout) -> Option<u64>,
- padding: impl FnOnce(&Layout) -> Option<(&str, u64)>,
- tag: impl FnOnce(&Layout) -> Option<usize>,
+ layout: impl FnOnce() -> Result<Layout<'db>, LayoutError>,
+ offset: impl FnOnce(&Layout<'db>) -> Option<u64>,
+ padding: impl for<'a> FnOnce(&'a Layout<'db>) -> Option<(&'a str, u64)>,
+ tag: impl FnOnce(&Layout<'db>) -> Option<usize>,
) -> Option<String> {
let config = config?;
let layout = layout().ok()?;
diff --git a/crates/ide/src/view_memory_layout.rs b/crates/ide/src/view_memory_layout.rs
index 47ca616f31..1b9df9722b 100644
--- a/crates/ide/src/view_memory_layout.rs
+++ b/crates/ide/src/view_memory_layout.rs
@@ -108,7 +108,7 @@ pub(crate) fn view_memory_layout(
nodes: &mut Vec<MemoryLayoutNode>,
db: &RootDatabase,
ty: &Type<'_>,
- layout: &Layout,
+ layout: &Layout<'_>,
parent_idx: usize,
display_target: DisplayTarget,
) {