1
0

More stuff

This commit is contained in:
Erik Johnston
2022-09-06 22:43:51 +01:00
parent 53e83c76b2
commit f3b7940e14
3 changed files with 37 additions and 33 deletions

View File

@@ -3,3 +3,7 @@
[workspace]
members = ["rust"]
[profile.release]
debug = true

View File

@@ -48,7 +48,7 @@ struct LruCacheNodeInner {
per_cache_list: Arc<Mutex<LinkedList<LruCacheNodeAdapterPerCache>>>,
cache: Mutex<Option<PyObject>>,
key: PyObject,
value: PyObject,
value: Arc<Mutex<PyObject>>,
callbacks: Py<PySet>,
memory: usize,
}
@@ -73,7 +73,7 @@ impl LruCacheNode {
per_cache_list: cache_list.0,
cache: Mutex::new(Some(cache)),
key,
value,
value: Arc::new(Mutex::new(value)),
callbacks,
memory,
});
@@ -91,35 +91,34 @@ impl LruCacheNode {
LruCacheNode(node)
}
fn add_callbacks(&self, py: Python<'_>, callbacks: Py<PySet>) -> PyResult<()> {
let new_callbacks = callbacks.as_ref(py);
fn add_callbacks(&self, py: Python<'_>, new_callbacks: &PyAny) -> PyResult<()> {
if new_callbacks.len()? == 0 {
return Ok(());
}
let current_callbacks = self.0.callbacks.as_ref(py);
for cb in new_callbacks {
current_callbacks.add(cb)?;
for cb in new_callbacks.iter()? {
current_callbacks.add(cb?)?;
}
Ok(())
}
fn run_and_clear_callbacks(&self, py: Python<'_>) {
let current_callbacks = self.0.callbacks.as_ref(py);
let callbacks = self.0.callbacks.as_ref(py);
if current_callbacks.len() == 0 {
if callbacks.is_empty() {
return;
}
// Swap out the stored callbacks with an empty list
let callbacks = std::mem::replace(&mut *callback_guard, Vec::new());
// Drop the lock
std::mem::drop(callback_guard);
for callback in callbacks {
if let Err(err) = callback.call0(py) {
if let Err(err) = callback.call0() {
error!("LruCacheNode callback errored: {err}");
}
}
callbacks.clear();
}
fn drop_from_cache(&self) -> PyResult<()> {
@@ -195,8 +194,13 @@ impl LruCacheNode {
}
#[getter]
fn value(&self) -> &PyObject {
&self.0.value
fn value(&self) -> PyObject {
self.0.value.lock().expect("poisoned").clone()
}
#[setter]
fn set_value(&self, value: PyObject) {
*self.0.value.lock().expect("poisoned") = value
}
#[getter]

View File

@@ -44,6 +44,7 @@ from twisted.internet.interfaces import IReactorTime
from synapse.config import cache as cache_config
from synapse.metrics.background_process_metrics import wrap_as_background_process
from synapse.metrics.jemalloc import get_jemalloc_stats
from synapse.synapse_rust.lru_cache import LruCacheNode, PerCacheLinkedList
from synapse.util import Clock, caches
from synapse.util.caches import CacheMetric, EvictionReason, register_cache
from synapse.util.caches.treecache import (
@@ -456,25 +457,21 @@ class LruCache(Generic[KT, VT]):
list_root = ListNode[_Node[KT, VT]].create_root_node()
rust_linked_list = PerCacheLinkedList()
lock = threading.Lock()
def evict() -> None:
while cache_len() > self.max_size:
# Get the last node in the list (i.e. the oldest node).
todelete = list_root.prev_node
todelete = rust_linked_list.get_back()
# The list root should always have a valid `prev_node` if the
# cache is not empty.
assert todelete is not None
# The node should always have a reference to a cache entry, as
# we only drop the cache entry when we remove the node from the
# list.
node = todelete.get_cache_entry()
assert node is not None
evicted_len = delete_node(node)
cache.pop(node.key, None)
evicted_len = delete_node(todelete)
cache.pop(todelete.key, None)
if metrics:
metrics.inc_evictions(EvictionReason.size, evicted_len)
@@ -502,14 +499,13 @@ class LruCache(Generic[KT, VT]):
def add_node(
key: KT, value: VT, callbacks: Collection[Callable[[], None]] = ()
) -> None:
node: _Node[KT, VT] = _Node(
list_root,
node: _Node[KT, VT] = LruCacheNode(
self,
rust_linked_list,
key,
value,
weak_ref_to_self,
real_clock,
callbacks,
prune_unread_entries,
set(callbacks),
0,
)
cache[key] = node
@@ -520,7 +516,7 @@ class LruCache(Generic[KT, VT]):
metrics.inc_memory_usage(node.memory)
def move_node_to_front(node: _Node[KT, VT]) -> None:
node.move_to_front(real_clock, list_root)
node.move_to_front()
def delete_node(node: _Node[KT, VT]) -> int:
node.drop_from_lists()