1#![cfg_attr(not(feature = "std"), no_std)]
18
19#[cfg(not(feature = "std"))]
20extern crate alloc;
21
22use hash_db::{
23 AsHashDB, AsPlainDB, HashDB, HashDBRef, Hasher as KeyHasher, MaybeDebug, PlainDB, PlainDBRef,
24 Prefix,
25};
26#[cfg(feature = "std")]
27use std::{
28 borrow::Borrow, cmp::Eq, collections::hash_map::Entry, collections::HashMap as Map, hash,
29 marker::PhantomData, mem,
30};
31
32#[cfg(not(feature = "std"))]
33use alloc::collections::btree_map::{BTreeMap as Map, Entry};
34
35#[cfg(not(feature = "std"))]
36use core::{borrow::Borrow, cmp::Eq, hash, marker::PhantomData, mem};
37
38#[cfg(not(feature = "std"))]
39use alloc::vec::Vec;
40
41pub struct MemoryDB<H, KF, T>
84where
85 H: KeyHasher,
86 KF: KeyFunction<H>,
87{
88 data: Map<KF::Key, (T, i32)>,
89 hashed_null_node: H::Out,
90 null_node_data: T,
91 _kf: PhantomData<KF>,
92}
93
94impl<H, KF, T> Clone for MemoryDB<H, KF, T>
95where
96 H: KeyHasher,
97 KF: KeyFunction<H>,
98 T: Clone,
99{
100 fn clone(&self) -> Self {
101 Self {
102 data: self.data.clone(),
103 hashed_null_node: self.hashed_null_node,
104 null_node_data: self.null_node_data.clone(),
105 _kf: Default::default(),
106 }
107 }
108}
109
110impl<H, KF, T> PartialEq<MemoryDB<H, KF, T>> for MemoryDB<H, KF, T>
111where
112 H: KeyHasher,
113 KF: KeyFunction<H>,
114 T: Eq + MaybeDebug,
115{
116 fn eq(&self, other: &MemoryDB<H, KF, T>) -> bool {
117 for a in self.data.iter() {
118 match other.data.get(a.0) {
119 Some(v) if v != a.1 => return false,
120 None => return false,
121 _ => (),
122 }
123 }
124 true
125 }
126}
127
128impl<H, KF, T> Eq for MemoryDB<H, KF, T>
129where
130 H: KeyHasher,
131 KF: KeyFunction<H>,
132 T: Eq + MaybeDebug,
133{
134}
135
136pub trait KeyFunction<H: KeyHasher> {
137 type Key: Send + Sync + Clone + hash::Hash + Eq + MaybeDebug + core::cmp::Ord;
138
139 fn key(hash: &H::Out, prefix: Prefix) -> Self::Key;
140}
141
142pub struct HashKey<H>(PhantomData<H>);
144
145impl<H> Clone for HashKey<H> {
146 fn clone(&self) -> Self {
147 Self(Default::default())
148 }
149}
150
151impl<H> core::fmt::Debug for HashKey<H> {
152 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
153 core::write!(f, "HashKey")
154 }
155}
156
157impl<H: KeyHasher> KeyFunction<H> for HashKey<H> {
158 type Key = H::Out;
159
160 fn key(hash: &H::Out, prefix: Prefix) -> H::Out {
161 hash_key::<H>(hash, prefix)
162 }
163}
164
165pub fn hash_key<H: KeyHasher>(key: &H::Out, _prefix: Prefix) -> H::Out {
167 *key
168}
169
170pub struct PrefixedKey<H>(PhantomData<H>);
172
173impl<H> Clone for PrefixedKey<H> {
174 fn clone(&self) -> Self {
175 Self(Default::default())
176 }
177}
178
179impl<H> core::fmt::Debug for PrefixedKey<H> {
180 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
181 core::write!(f, "PrefixedKey")
182 }
183}
184
185impl<H: KeyHasher> KeyFunction<H> for PrefixedKey<H> {
186 type Key = Vec<u8>;
187
188 fn key(hash: &H::Out, prefix: Prefix) -> Vec<u8> {
189 prefixed_key::<H>(hash, prefix)
190 }
191}
192
193pub fn prefixed_key<H: KeyHasher>(key: &H::Out, prefix: Prefix) -> Vec<u8> {
195 let mut prefixed_key = Vec::with_capacity(key.as_ref().len() + prefix.0.len() + 1);
196 prefixed_key.extend_from_slice(prefix.0);
197 if let Some(last) = prefix.1 {
198 prefixed_key.push(last);
199 }
200 prefixed_key.extend_from_slice(key.as_ref());
201 prefixed_key
202}
203
204#[derive(Clone, Debug)]
209#[deprecated(since = "0.22.0")]
210pub struct LegacyPrefixedKey<H: KeyHasher>(PhantomData<H>);
211
212#[allow(deprecated)]
213impl<H: KeyHasher> KeyFunction<H> for LegacyPrefixedKey<H> {
214 type Key = Vec<u8>;
215
216 fn key(hash: &H::Out, prefix: Prefix) -> Vec<u8> {
217 legacy_prefixed_key::<H>(hash, prefix)
218 }
219}
220
221#[deprecated(since = "0.22.0")]
224pub fn legacy_prefixed_key<H: KeyHasher>(key: &H::Out, prefix: Prefix) -> Vec<u8> {
225 let mut prefixed_key = Vec::with_capacity(key.as_ref().len() + prefix.0.len() + 1);
226 if let Some(last) = prefix.1 {
227 let mut prev = 0x01u8;
228 for i in prefix.0.iter() {
229 prefixed_key.push((prev << 4) + (*i >> 4));
230 prev = *i;
231 }
232 prefixed_key.push((prev << 4) + (last >> 4));
233 } else {
234 prefixed_key.push(0);
235 prefixed_key.extend_from_slice(prefix.0);
236 }
237 prefixed_key.extend_from_slice(key.as_ref());
238 prefixed_key
239}
240
241impl<H, KF, T> Default for MemoryDB<H, KF, T>
242where
243 H: KeyHasher,
244 T: for<'a> From<&'a [u8]>,
245 KF: KeyFunction<H>,
246{
247 fn default() -> Self {
248 Self::from_null_node(&[0u8][..], [0u8][..].into())
249 }
250}
251
252impl<H, KF, T> MemoryDB<H, KF, T>
254where
255 H: KeyHasher,
256 T: Default,
257 KF: KeyFunction<H>,
258{
259 pub fn remove_and_purge(&mut self, key: &<H as KeyHasher>::Out, prefix: Prefix) -> Option<T> {
262 if key == &self.hashed_null_node {
263 return None
264 }
265 let key = KF::key(key, prefix);
266 match self.data.entry(key) {
267 Entry::Occupied(mut entry) =>
268 if entry.get().1 == 1 {
269 let (value, _) = entry.remove();
270 Some(value)
271 } else {
272 entry.get_mut().1 -= 1;
273 None
274 },
275 Entry::Vacant(entry) => {
276 let value = T::default();
277 entry.insert((value, -1));
278 None
279 },
280 }
281 }
282
283 #[inline]
287 pub fn shrink_to_fit(&mut self) {
288 #[cfg(feature = "std")]
289 self.data.shrink_to_fit();
290 }
291}
292
293impl<H, KF, T> MemoryDB<H, KF, T>
294where
295 H: KeyHasher,
296 T: for<'a> From<&'a [u8]>,
297 KF: KeyFunction<H>,
298{
299 pub fn from_null_node(null_key: &[u8], null_node_data: T) -> Self {
301 MemoryDB {
302 data: Map::default(),
303 hashed_null_node: H::hash(null_key),
304 null_node_data,
305 _kf: Default::default(),
306 }
307 }
308
309 pub fn new(data: &[u8]) -> Self {
311 Self::from_null_node(data, data.into())
312 }
313
314 pub fn default_with_root() -> (Self, H::Out) {
316 let db = Self::default();
317 let root = db.hashed_null_node;
318
319 (db, root)
320 }
321
322 pub fn clear(&mut self) {
344 self.data.clear();
345 }
346
347 pub fn purge(&mut self) {
349 self.data.retain(|_, (_, rc)| {
350 let keep = *rc != 0;
351 keep
352 });
353 }
354
355 pub fn drain(&mut self) -> Map<KF::Key, (T, i32)> {
357 mem::take(&mut self.data)
358 }
359
360 pub fn raw(&self, key: &<H as KeyHasher>::Out, prefix: Prefix) -> Option<(&T, i32)> {
366 if key == &self.hashed_null_node {
367 return Some((&self.null_node_data, 1))
368 }
369 self.data.get(&KF::key(key, prefix)).map(|(value, count)| (value, *count))
370 }
371
372 pub fn consolidate(&mut self, mut other: Self) {
374 for (key, (value, rc)) in other.drain() {
375 match self.data.entry(key) {
376 Entry::Occupied(mut entry) => {
377 if entry.get().1 < 0 {
378 entry.get_mut().0 = value;
379 }
380
381 entry.get_mut().1 += rc;
382 },
383 Entry::Vacant(entry) => {
384 entry.insert((value, rc));
385 },
386 }
387 }
388 }
389
390 pub fn keys(&self) -> Map<KF::Key, i32> {
392 self.data
393 .iter()
394 .filter_map(|(k, v)| if v.1 != 0 { Some((k.clone(), v.1)) } else { None })
395 .collect()
396 }
397}
398
399impl<H, KF, T> PlainDB<H::Out, T> for MemoryDB<H, KF, T>
400where
401 H: KeyHasher,
402 T: Default + PartialEq<T> + for<'a> From<&'a [u8]> + Clone + Send + Sync,
403 KF: Send + Sync + KeyFunction<H>,
404 KF::Key: Borrow<[u8]> + for<'a> From<&'a [u8]>,
405{
406 fn get(&self, key: &H::Out) -> Option<T> {
407 match self.data.get(key.as_ref()) {
408 Some(&(ref d, rc)) if rc > 0 => Some(d.clone()),
409 _ => None,
410 }
411 }
412
413 fn contains(&self, key: &H::Out) -> bool {
414 match self.data.get(key.as_ref()) {
415 Some(&(_, x)) if x > 0 => true,
416 _ => false,
417 }
418 }
419
420 fn emplace(&mut self, key: H::Out, value: T) {
421 match self.data.entry(key.as_ref().into()) {
422 Entry::Occupied(mut entry) => {
423 let &mut (ref mut old_value, ref mut rc) = entry.get_mut();
424 if *rc <= 0 {
425 *old_value = value;
426 }
427 *rc += 1;
428 },
429 Entry::Vacant(entry) => {
430 entry.insert((value, 1));
431 },
432 }
433 }
434
435 fn remove(&mut self, key: &H::Out) {
436 match self.data.entry(key.as_ref().into()) {
437 Entry::Occupied(mut entry) => {
438 let &mut (_, ref mut rc) = entry.get_mut();
439 *rc -= 1;
440 },
441 Entry::Vacant(entry) => {
442 let value = T::default();
443 entry.insert((value, -1));
444 },
445 }
446 }
447}
448
449impl<H, KF, T> PlainDBRef<H::Out, T> for MemoryDB<H, KF, T>
450where
451 H: KeyHasher,
452 T: Default + PartialEq<T> + for<'a> From<&'a [u8]> + Clone + Send + Sync,
453 KF: Send + Sync + KeyFunction<H>,
454 KF::Key: Borrow<[u8]> + for<'a> From<&'a [u8]>,
455{
456 fn get(&self, key: &H::Out) -> Option<T> {
457 PlainDB::get(self, key)
458 }
459 fn contains(&self, key: &H::Out) -> bool {
460 PlainDB::contains(self, key)
461 }
462}
463
464impl<H, KF, T> HashDB<H, T> for MemoryDB<H, KF, T>
465where
466 H: KeyHasher,
467 T: Default + PartialEq<T> + AsRef<[u8]> + for<'a> From<&'a [u8]> + Clone + Send + Sync,
468 KF: KeyFunction<H> + Send + Sync,
469{
470 fn get(&self, key: &H::Out, prefix: Prefix) -> Option<T> {
471 if key == &self.hashed_null_node {
472 return Some(self.null_node_data.clone())
473 }
474
475 let key = KF::key(key, prefix);
476 match self.data.get(&key) {
477 Some(&(ref d, rc)) if rc > 0 => Some(d.clone()),
478 _ => None,
479 }
480 }
481
482 fn contains(&self, key: &H::Out, prefix: Prefix) -> bool {
483 if key == &self.hashed_null_node {
484 return true
485 }
486
487 let key = KF::key(key, prefix);
488 match self.data.get(&key) {
489 Some(&(_, x)) if x > 0 => true,
490 _ => false,
491 }
492 }
493
494 fn emplace(&mut self, key: H::Out, prefix: Prefix, value: T) {
495 if value == self.null_node_data {
496 return
497 }
498
499 let key = KF::key(&key, prefix);
500 match self.data.entry(key) {
501 Entry::Occupied(mut entry) => {
502 let &mut (ref mut old_value, ref mut rc) = entry.get_mut();
503 if *rc <= 0 {
504 *old_value = value;
505 }
506 *rc += 1;
507 },
508 Entry::Vacant(entry) => {
509 entry.insert((value, 1));
510 },
511 }
512 }
513
514 fn insert(&mut self, prefix: Prefix, value: &[u8]) -> H::Out {
515 if T::from(value) == self.null_node_data {
516 return self.hashed_null_node
517 }
518
519 let key = H::hash(value);
520 HashDB::emplace(self, key, prefix, value.into());
521 key
522 }
523
524 fn remove(&mut self, key: &H::Out, prefix: Prefix) {
525 if key == &self.hashed_null_node {
526 return
527 }
528
529 let key = KF::key(key, prefix);
530 match self.data.entry(key) {
531 Entry::Occupied(mut entry) => {
532 let &mut (_, ref mut rc) = entry.get_mut();
533 *rc -= 1;
534 },
535 Entry::Vacant(entry) => {
536 let value = T::default();
537 entry.insert((value, -1));
538 },
539 }
540 }
541}
542
543impl<H, KF, T> HashDBRef<H, T> for MemoryDB<H, KF, T>
544where
545 H: KeyHasher,
546 T: Default + PartialEq<T> + AsRef<[u8]> + for<'a> From<&'a [u8]> + Clone + Send + Sync,
547 KF: KeyFunction<H> + Send + Sync,
548{
549 fn get(&self, key: &H::Out, prefix: Prefix) -> Option<T> {
550 HashDB::get(self, key, prefix)
551 }
552 fn contains(&self, key: &H::Out, prefix: Prefix) -> bool {
553 HashDB::contains(self, key, prefix)
554 }
555}
556
557impl<H, KF, T> AsPlainDB<H::Out, T> for MemoryDB<H, KF, T>
558where
559 H: KeyHasher,
560 T: Default + PartialEq<T> + for<'a> From<&'a [u8]> + Clone + Send + Sync,
561 KF: KeyFunction<H> + Send + Sync,
562 KF::Key: Borrow<[u8]> + for<'a> From<&'a [u8]>,
563{
564 fn as_plain_db(&self) -> &dyn PlainDB<H::Out, T> {
565 self
566 }
567 fn as_plain_db_mut(&mut self) -> &mut dyn PlainDB<H::Out, T> {
568 self
569 }
570}
571
572impl<H, KF, T> AsHashDB<H, T> for MemoryDB<H, KF, T>
573where
574 H: KeyHasher,
575 T: Default + PartialEq<T> + AsRef<[u8]> + for<'a> From<&'a [u8]> + Clone + Send + Sync,
576 KF: KeyFunction<H> + Send + Sync,
577{
578 fn as_hash_db(&self) -> &dyn HashDB<H, T> {
579 self
580 }
581 fn as_hash_db_mut(&mut self) -> &mut dyn HashDB<H, T> {
582 self
583 }
584}
585
586#[cfg(test)]
587mod tests {
588 use super::{HashDB, HashKey, KeyHasher, MemoryDB};
589 use hash_db::EMPTY_PREFIX;
590 use keccak_hasher::KeccakHasher;
591
592 #[test]
593 fn memorydb_remove_and_purge() {
594 let hello_bytes = b"Hello world!";
595 let hello_key = KeccakHasher::hash(hello_bytes);
596
597 let mut m = MemoryDB::<KeccakHasher, HashKey<_>, Vec<u8>>::default();
598 m.remove(&hello_key, EMPTY_PREFIX);
599 assert_eq!(m.raw(&hello_key, EMPTY_PREFIX).unwrap().1, -1);
600 m.purge();
601 assert_eq!(m.raw(&hello_key, EMPTY_PREFIX).unwrap().1, -1);
602 m.insert(EMPTY_PREFIX, hello_bytes);
603 assert_eq!(m.raw(&hello_key, EMPTY_PREFIX).unwrap().1, 0);
604 m.purge();
605 assert_eq!(m.raw(&hello_key, EMPTY_PREFIX), None);
606
607 let mut m = MemoryDB::<KeccakHasher, HashKey<_>, Vec<u8>>::default();
608 assert!(m.remove_and_purge(&hello_key, EMPTY_PREFIX).is_none());
609 assert_eq!(m.raw(&hello_key, EMPTY_PREFIX).unwrap().1, -1);
610 m.insert(EMPTY_PREFIX, hello_bytes);
611 m.insert(EMPTY_PREFIX, hello_bytes);
612 assert_eq!(m.raw(&hello_key, EMPTY_PREFIX).unwrap().1, 1);
613 assert_eq!(&*m.remove_and_purge(&hello_key, EMPTY_PREFIX).unwrap(), hello_bytes);
614 assert_eq!(m.raw(&hello_key, EMPTY_PREFIX), None);
615 assert!(m.remove_and_purge(&hello_key, EMPTY_PREFIX).is_none());
616 }
617
618 #[test]
619 fn consolidate() {
620 let mut main = MemoryDB::<KeccakHasher, HashKey<_>, Vec<u8>>::default();
621 let mut other = MemoryDB::<KeccakHasher, HashKey<_>, Vec<u8>>::default();
622 let remove_key = other.insert(EMPTY_PREFIX, b"doggo");
623 main.remove(&remove_key, EMPTY_PREFIX);
624
625 let insert_key = other.insert(EMPTY_PREFIX, b"arf");
626 main.emplace(insert_key, EMPTY_PREFIX, "arf".as_bytes().to_vec());
627
628 let negative_remove_key = other.insert(EMPTY_PREFIX, b"negative");
629 other.remove(&negative_remove_key, EMPTY_PREFIX); other.remove(&negative_remove_key, EMPTY_PREFIX); main.remove(&negative_remove_key, EMPTY_PREFIX); main.consolidate(other);
634
635 assert_eq!(main.raw(&remove_key, EMPTY_PREFIX).unwrap(), (&"doggo".as_bytes().to_vec(), 0));
636 assert_eq!(main.raw(&insert_key, EMPTY_PREFIX).unwrap(), (&"arf".as_bytes().to_vec(), 2));
637 assert_eq!(
638 main.raw(&negative_remove_key, EMPTY_PREFIX).unwrap(),
639 (&"negative".as_bytes().to_vec(), -2),
640 );
641 }
642
643 #[test]
644 fn default_works() {
645 let mut db = MemoryDB::<KeccakHasher, HashKey<_>, Vec<u8>>::default();
646 let hashed_null_node = KeccakHasher::hash(&[0u8][..]);
647 assert_eq!(db.insert(EMPTY_PREFIX, &[0u8][..]), hashed_null_node);
648
649 let (db2, root) = MemoryDB::<KeccakHasher, HashKey<_>, Vec<u8>>::default_with_root();
650 assert!(db2.contains(&root, EMPTY_PREFIX));
651 assert!(db.contains(&root, EMPTY_PREFIX));
652 }
653}