Skip to content

Commit b5580ad

Browse files
committed
Force invalidation on cache eviction
1 parent 00dbf01 commit b5580ad

File tree

11 files changed

+106
-2
lines changed

11 files changed

+106
-2
lines changed

components/salsa-macro-rules/src/setup_tracked_fn.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,8 @@ macro_rules! setup_tracked_fn {
6060

6161
assert_return_type_is_update: {$($assert_return_type_is_update:tt)*},
6262

63+
force_invalidation_on_cache_eviction: $force_invalidation_on_cache_eviction:literal,
64+
6365
// Annoyingly macro-rules hygiene does not extend to items defined in the macro.
6466
// We have the procedural macro generate names for those items that are
6567
// not used elsewhere in the user's code.
@@ -192,6 +194,7 @@ macro_rules! setup_tracked_fn {
192194
line: line!(),
193195
};
194196
const DEBUG_NAME: &'static str = stringify!($fn_name);
197+
const FORCE_INVALIDATION_ON_CACHE_EVICTION: bool = $force_invalidation_on_cache_eviction;
195198

196199
type DbView = dyn $Db;
197200

components/salsa-macros/src/accumulator.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@ impl AllowedOptions for Accumulator {
4444
const LRU: bool = false;
4545
const CONSTRUCTOR_NAME: bool = false;
4646
const ID: bool = false;
47+
const FORCE_INVALIDATION_ON_CACHE_EVICTION: bool = false;
4748
}
4849

4950
struct StructMacro {

components/salsa-macros/src/input.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,8 @@ impl crate::options::AllowedOptions for InputStruct {
6262
const CONSTRUCTOR_NAME: bool = true;
6363

6464
const ID: bool = false;
65+
66+
const FORCE_INVALIDATION_ON_CACHE_EVICTION: bool = false;
6567
}
6668

6769
impl SalsaStructAllowedOptions for InputStruct {

components/salsa-macros/src/interned.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,8 @@ impl crate::options::AllowedOptions for InternedStruct {
6262
const CONSTRUCTOR_NAME: bool = true;
6363

6464
const ID: bool = true;
65+
66+
const FORCE_INVALIDATION_ON_CACHE_EVICTION: bool = false;
6567
}
6668

6769
impl SalsaStructAllowedOptions for InternedStruct {

components/salsa-macros/src/options.rs

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -89,6 +89,8 @@ pub(crate) struct Options<A: AllowedOptions> {
8989
/// If this is `Some`, the value is the `<ident>`.
9090
pub id: Option<syn::Path>,
9191

92+
pub force_invalidation_on_cache_eviction: Option<syn::Ident>,
93+
9294
/// Remember the `A` parameter, which plays no role after parsing.
9395
phantom: PhantomData<A>,
9496
}
@@ -112,6 +114,7 @@ impl<A: AllowedOptions> Default for Options<A> {
112114
lru: Default::default(),
113115
singleton: Default::default(),
114116
id: Default::default(),
117+
force_invalidation_on_cache_eviction: Default::default(),
115118
}
116119
}
117120
}
@@ -133,6 +136,7 @@ pub(crate) trait AllowedOptions {
133136
const LRU: bool;
134137
const CONSTRUCTOR_NAME: bool;
135138
const ID: bool;
139+
const FORCE_INVALIDATION_ON_CACHE_EVICTION: bool;
136140
}
137141

138142
type Equals = syn::Token![=];
@@ -351,6 +355,20 @@ impl<A: AllowedOptions> syn::parse::Parse for Options<A> {
351355
"`id` option not allowed here",
352356
));
353357
}
358+
} else if ident == "force_invalidation_on_cache_eviction" {
359+
if A::FORCE_INVALIDATION_ON_CACHE_EVICTION {
360+
if let Some(old) = options.force_invalidation_on_cache_eviction.replace(ident) {
361+
return Err(syn::Error::new(
362+
old.span(),
363+
"option `force_invalidation_on_cache_eviction` provided twice",
364+
));
365+
}
366+
} else {
367+
return Err(syn::Error::new(
368+
ident.span(),
369+
"`force_invalidation_on_cache_eviction` option not allowed here",
370+
));
371+
}
354372
} else {
355373
return Err(syn::Error::new(
356374
ident.span(),

components/salsa-macros/src/tracked_fn.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,8 @@ impl crate::options::AllowedOptions for TrackedFn {
5555
const CONSTRUCTOR_NAME: bool = false;
5656

5757
const ID: bool = false;
58+
59+
const FORCE_INVALIDATION_ON_CACHE_EVICTION: bool = true;
5860
}
5961

6062
struct Macro {
@@ -147,6 +149,8 @@ impl Macro {
147149
let lru = Literal::usize_unsuffixed(self.args.lru.unwrap_or(0));
148150

149151
let return_ref: bool = self.args.return_ref.is_some();
152+
let force_invalidation_on_cache_eviction: bool =
153+
self.args.force_invalidation_on_cache_eviction.is_some();
150154

151155
// The path expression is responsible for emitting the primary span in the diagnostic we
152156
// want, so by uniformly using `output_ty.span()` we ensure that the diagnostic is emitted
@@ -185,6 +189,7 @@ impl Macro {
185189
lru: #lru,
186190
return_ref: #return_ref,
187191
assert_return_type_is_update: { #assert_return_type_is_update },
192+
force_invalidation_on_cache_eviction: #force_invalidation_on_cache_eviction,
188193
unused_names: [
189194
#zalsa,
190195
#Configuration,

components/salsa-macros/src/tracked_struct.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,8 @@ impl crate::options::AllowedOptions for TrackedStruct {
5757
const CONSTRUCTOR_NAME: bool = true;
5858

5959
const ID: bool = false;
60+
61+
const FORCE_INVALIDATION_ON_CACHE_EVICTION: bool = false;
6062
}
6163

6264
impl SalsaStructAllowedOptions for TrackedStruct {

src/function.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@ pub type Memo<C> = memo::Memo<<C as Configuration>::Output<'static>>;
3838
pub trait Configuration: Any {
3939
const DEBUG_NAME: &'static str;
4040
const LOCATION: crate::ingredient::Location;
41+
const FORCE_INVALIDATION_ON_CACHE_EVICTION: bool;
4142

4243
/// The database that this function is associated with.
4344
type DbView: ?Sized + crate::Database;

src/function/execute.rs

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ use crate::function::{Configuration, IngredientImpl};
44
use crate::loom::sync::atomic::{AtomicBool, Ordering};
55
use crate::zalsa::{MemoIngredientIndex, Zalsa, ZalsaDatabase};
66
use crate::zalsa_local::{ActiveQueryGuard, QueryRevisions};
7-
use crate::{Event, EventKind, Id, Revision};
7+
use crate::{Durability, Event, EventKind, Id, Revision};
88

99
impl<C> IngredientImpl<C>
1010
where
@@ -269,7 +269,12 @@ where
269269
// Query was not previously executed, or value is potentially
270270
// stale, or value is absent. Let's execute!
271271
let new_value = C::execute(db, C::id_to_input(db, id));
272+
let mut revisions = active_query.pop();
272273

273-
(new_value, active_query.pop())
274+
if C::FORCE_INVALIDATION_ON_CACHE_EVICTION {
275+
revisions.durability = Durability::MIN;
276+
}
277+
278+
(new_value, revisions)
274279
}
275280
}

src/function/maybe_changed_after.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -70,6 +70,10 @@ where
7070
return VerifyResult::Changed;
7171
};
7272

73+
if C::FORCE_INVALIDATION_ON_CACHE_EVICTION && memo.value.is_none() {
74+
return VerifyResult::Changed;
75+
}
76+
7377
let can_shallow_update = self.shallow_verify_memo(zalsa, database_key_index, memo);
7478
if can_shallow_update.yes() && !memo.may_be_provisional() {
7579
self.update_shallow(zalsa, database_key_index, memo, can_shallow_update);

0 commit comments

Comments
 (0)