1use crate::{
21 StorageKey, StorageValue, OverlayedChanges,
22 backend::Backend, overlayed_changes::OverlayedExtensions,
23};
24use tetsy_hash_db::Hasher;
25use tet_core::{
26 storage::{well_known_keys::is_child_storage_key, ChildInfo, TrackedStorageKey},
27 hexdisplay::HexDisplay,
28};
29use tp_trie::{trie_types::Layout, empty_child_trie_root};
30use externalities::{
31 Externalities, Extensions, Extension, ExtensionStore,
32};
33use codec::{Decode, Encode, EncodeAppend};
34
35use tetcore_std::{fmt, any::{Any, TypeId}, vec::Vec, vec, boxed::Box};
36use crate::{warn, trace, log_error};
37#[cfg(feature = "std")]
38use crate::changes_trie::State as ChangesTrieState;
39use crate::StorageTransactionCache;
40#[cfg(feature = "std")]
41use std::error;
42
43const EXT_NOT_ALLOWED_TO_FAIL: &str = "Externalities not allowed to fail within runtime";
44const BENCHMARKING_FN: &str = "\
45 This is a special fn only for benchmarking where a database commit happens from the runtime.
46 For that reason client started transactions before calling into runtime are not allowed.
47 Without client transactions the loop condition garantuees the success of the tx close.";
48
49
50#[cfg(feature = "std")]
51fn guard() -> panic_handler::AbortGuard {
52 panic_handler::AbortGuard::force_abort()
53}
54
55#[cfg(not(feature = "std"))]
56fn guard() -> () {
57 ()
58}
59
60#[cfg(feature = "std")]
62#[derive(Debug, Copy, Clone)]
63pub enum Error<B, E> {
64 #[allow(unused)]
66 Backend(B),
67 #[allow(unused)]
69 Executor(E),
70}
71
72#[cfg(feature = "std")]
73impl<B: fmt::Display, E: fmt::Display> fmt::Display for Error<B, E> {
74 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
75 match *self {
76 Error::Backend(ref e) => write!(f, "Storage backend error: {}", e),
77 Error::Executor(ref e) => write!(f, "Sub-call execution error: {}", e),
78 }
79 }
80}
81
82#[cfg(feature = "std")]
83impl<B: error::Error, E: error::Error> error::Error for Error<B, E> {
84 fn description(&self) -> &str {
85 match *self {
86 Error::Backend(..) => "backend error",
87 Error::Executor(..) => "executor error",
88 }
89 }
90}
91
92pub struct Ext<'a, H, N, B>
94 where
95 H: Hasher,
96 B: 'a + Backend<H>,
97 N: crate::changes_trie::BlockNumber,
98{
99 overlay: &'a mut OverlayedChanges,
101 backend: &'a B,
103 storage_transaction_cache: &'a mut StorageTransactionCache<B::Transaction, H, N>,
105 #[cfg(feature = "std")]
107 changes_trie_state: Option<ChangesTrieState<'a, H, N>>,
108 pub id: u16,
110 _phantom: tetcore_std::marker::PhantomData<N>,
112 #[cfg(feature = "std")]
114 extensions: Option<OverlayedExtensions<'a>>,
115}
116
117
118impl<'a, H, N, B> Ext<'a, H, N, B>
119 where
120 H: Hasher,
121 B: Backend<H>,
122 N: crate::changes_trie::BlockNumber,
123{
124 #[cfg(not(feature = "std"))]
126 pub fn new(
127 overlay: &'a mut OverlayedChanges,
128 storage_transaction_cache: &'a mut StorageTransactionCache<B::Transaction, H, N>,
129 backend: &'a B,
130 ) -> Self {
131 Ext {
132 overlay,
133 backend,
134 id: 0,
135 storage_transaction_cache,
136 _phantom: Default::default(),
137 }
138 }
139
140 #[cfg(feature = "std")]
142 pub fn new(
143 overlay: &'a mut OverlayedChanges,
144 storage_transaction_cache: &'a mut StorageTransactionCache<B::Transaction, H, N>,
145 backend: &'a B,
146 changes_trie_state: Option<ChangesTrieState<'a, H, N>>,
147 extensions: Option<&'a mut Extensions>,
148 ) -> Self {
149 Self {
150 overlay,
151 backend,
152 changes_trie_state,
153 storage_transaction_cache,
154 id: rand::random(),
155 _phantom: Default::default(),
156 extensions: extensions.map(OverlayedExtensions::new),
157 }
158 }
159
160 fn mark_dirty(&mut self) {
164 self.storage_transaction_cache.reset();
165 }
166}
167
168#[cfg(test)]
169impl<'a, H, N, B> Ext<'a, H, N, B>
170where
171 H: Hasher,
172 H::Out: Ord + 'static,
173 B: 'a + Backend<H>,
174 N: crate::changes_trie::BlockNumber,
175{
176 pub fn storage_pairs(&self) -> Vec<(StorageKey, StorageValue)> {
177 use std::collections::HashMap;
178
179 self.backend.pairs().iter()
180 .map(|&(ref k, ref v)| (k.to_vec(), Some(v.to_vec())))
181 .chain(self.overlay.changes().map(|(k, v)| (k.clone(), v.value().cloned())))
182 .collect::<HashMap<_, _>>()
183 .into_iter()
184 .filter_map(|(k, maybe_val)| maybe_val.map(|val| (k, val)))
185 .collect()
186 }
187}
188
189impl<'a, H, N, B> Externalities for Ext<'a, H, N, B>
190where
191 H: Hasher,
192 H::Out: Ord + 'static + codec::Codec,
193 B: Backend<H>,
194 N: crate::changes_trie::BlockNumber,
195{
196 fn set_offchain_storage(&mut self, key: &[u8], value: Option<&[u8]>) {
197 self.overlay.set_offchain_storage(key, value)
198 }
199
200 fn storage(&self, key: &[u8]) -> Option<StorageValue> {
201 let _guard = guard();
202 let result = self.overlay.storage(key).map(|x| x.map(|x| x.to_vec())).unwrap_or_else(||
203 self.backend.storage(key).expect(EXT_NOT_ALLOWED_TO_FAIL));
204 trace!(target: "state", "{:04x}: Get {}={:?}",
205 self.id,
206 HexDisplay::from(&key),
207 result.as_ref().map(HexDisplay::from)
208 );
209 result
210 }
211
212 fn storage_hash(&self, key: &[u8]) -> Option<Vec<u8>> {
213 let _guard = guard();
214 let result = self.overlay
215 .storage(key)
216 .map(|x| x.map(|x| H::hash(x)))
217 .unwrap_or_else(|| self.backend.storage_hash(key).expect(EXT_NOT_ALLOWED_TO_FAIL));
218
219 trace!(target: "state", "{:04x}: Hash {}={:?}",
220 self.id,
221 HexDisplay::from(&key),
222 result,
223 );
224 result.map(|r| r.encode())
225 }
226
227 fn child_storage(
228 &self,
229 child_info: &ChildInfo,
230 key: &[u8],
231 ) -> Option<StorageValue> {
232 let _guard = guard();
233 let result = self.overlay
234 .child_storage(child_info, key)
235 .map(|x| x.map(|x| x.to_vec()))
236 .unwrap_or_else(||
237 self.backend.child_storage(child_info, key)
238 .expect(EXT_NOT_ALLOWED_TO_FAIL)
239 );
240
241 trace!(target: "state", "{:04x}: GetChild({}) {}={:?}",
242 self.id,
243 HexDisplay::from(&child_info.storage_key()),
244 HexDisplay::from(&key),
245 result.as_ref().map(HexDisplay::from)
246 );
247
248 result
249 }
250
251 fn child_storage_hash(
252 &self,
253 child_info: &ChildInfo,
254 key: &[u8],
255 ) -> Option<Vec<u8>> {
256 let _guard = guard();
257 let result = self.overlay
258 .child_storage(child_info, key)
259 .map(|x| x.map(|x| H::hash(x)))
260 .unwrap_or_else(||
261 self.backend.child_storage_hash(child_info, key)
262 .expect(EXT_NOT_ALLOWED_TO_FAIL)
263 );
264
265 trace!(target: "state", "{:04x}: ChildHash({}) {}={:?}",
266 self.id,
267 HexDisplay::from(&child_info.storage_key()),
268 HexDisplay::from(&key),
269 result,
270 );
271
272 result.map(|r| r.encode())
273 }
274
275 fn exists_storage(&self, key: &[u8]) -> bool {
276 let _guard = guard();
277 let result = match self.overlay.storage(key) {
278 Some(x) => x.is_some(),
279 _ => self.backend.exists_storage(key).expect(EXT_NOT_ALLOWED_TO_FAIL),
280 };
281
282 trace!(target: "state", "{:04x}: Exists {}={:?}",
283 self.id,
284 HexDisplay::from(&key),
285 result,
286 );
287
288 result
289 }
290
291 fn exists_child_storage(
292 &self,
293 child_info: &ChildInfo,
294 key: &[u8],
295 ) -> bool {
296 let _guard = guard();
297
298 let result = match self.overlay.child_storage(child_info, key) {
299 Some(x) => x.is_some(),
300 _ => self.backend
301 .exists_child_storage(child_info, key)
302 .expect(EXT_NOT_ALLOWED_TO_FAIL),
303 };
304
305 trace!(target: "state", "{:04x}: ChildExists({}) {}={:?}",
306 self.id,
307 HexDisplay::from(&child_info.storage_key()),
308 HexDisplay::from(&key),
309 result,
310 );
311 result
312 }
313
314 fn next_storage_key(&self, key: &[u8]) -> Option<StorageKey> {
315 let next_backend_key = self.backend.next_storage_key(key).expect(EXT_NOT_ALLOWED_TO_FAIL);
316 let next_overlay_key_change = self.overlay.next_storage_key_change(key);
317
318 match (next_backend_key, next_overlay_key_change) {
319 (Some(backend_key), Some(overlay_key)) if &backend_key[..] < overlay_key.0 => Some(backend_key),
320 (backend_key, None) => backend_key,
321 (_, Some(overlay_key)) => if overlay_key.1.value().is_some() {
322 Some(overlay_key.0.to_vec())
323 } else {
324 self.next_storage_key(&overlay_key.0[..])
325 },
326 }
327 }
328
329 fn next_child_storage_key(
330 &self,
331 child_info: &ChildInfo,
332 key: &[u8],
333 ) -> Option<StorageKey> {
334 let next_backend_key = self.backend
335 .next_child_storage_key(child_info, key)
336 .expect(EXT_NOT_ALLOWED_TO_FAIL);
337 let next_overlay_key_change = self.overlay.next_child_storage_key_change(
338 child_info.storage_key(),
339 key
340 );
341
342 match (next_backend_key, next_overlay_key_change) {
343 (Some(backend_key), Some(overlay_key)) if &backend_key[..] < overlay_key.0 => Some(backend_key),
344 (backend_key, None) => backend_key,
345 (_, Some(overlay_key)) => if overlay_key.1.value().is_some() {
346 Some(overlay_key.0.to_vec())
347 } else {
348 self.next_child_storage_key(
349 child_info,
350 &overlay_key.0[..],
351 )
352 },
353 }
354 }
355
356 fn place_storage(&mut self, key: StorageKey, value: Option<StorageValue>) {
357 trace!(target: "state", "{:04x}: Put {}={:?}",
358 self.id,
359 HexDisplay::from(&key),
360 value.as_ref().map(HexDisplay::from)
361 );
362 let _guard = guard();
363 if is_child_storage_key(&key) {
364 warn!(target: "trie", "Refuse to directly set child storage key");
365 return;
366 }
367
368 self.mark_dirty();
369 self.overlay.set_storage(key, value);
370 }
371
372 fn place_child_storage(
373 &mut self,
374 child_info: &ChildInfo,
375 key: StorageKey,
376 value: Option<StorageValue>,
377 ) {
378 trace!(target: "state", "{:04x}: PutChild({}) {}={:?}",
379 self.id,
380 HexDisplay::from(&child_info.storage_key()),
381 HexDisplay::from(&key),
382 value.as_ref().map(HexDisplay::from)
383 );
384 let _guard = guard();
385
386 self.mark_dirty();
387 self.overlay.set_child_storage(child_info, key, value);
388 }
389
390 fn kill_child_storage(
391 &mut self,
392 child_info: &ChildInfo,
393 limit: Option<u32>,
394 ) -> bool {
395 trace!(target: "state", "{:04x}: KillChild({})",
396 self.id,
397 HexDisplay::from(&child_info.storage_key()),
398 );
399 let _guard = guard();
400 self.mark_dirty();
401 self.overlay.clear_child_storage(child_info);
402
403 if let Some(limit) = limit {
404 let mut num_deleted: u32 = 0;
405 let mut all_deleted = true;
406 self.backend.apply_to_child_keys_while(child_info, |key| {
407 if num_deleted == limit {
408 all_deleted = false;
409 return false;
410 }
411 if let Some(num) = num_deleted.checked_add(1) {
412 num_deleted = num;
413 } else {
414 all_deleted = false;
415 return false;
416 }
417 self.overlay.set_child_storage(child_info, key.to_vec(), None);
418 true
419 });
420 all_deleted
421 } else {
422 self.backend.apply_to_child_keys_while(child_info, |key| {
423 self.overlay.set_child_storage(child_info, key.to_vec(), None);
424 true
425 });
426 true
427 }
428 }
429
430 fn clear_prefix(&mut self, prefix: &[u8]) {
431 trace!(target: "state", "{:04x}: ClearPrefix {}",
432 self.id,
433 HexDisplay::from(&prefix),
434 );
435 let _guard = guard();
436
437 if tet_core::storage::well_known_keys::starts_with_child_storage_key(prefix) {
438 warn!(target: "trie", "Refuse to directly clear prefix that is part or contains of child storage key");
439 return;
440 }
441
442 self.mark_dirty();
443 self.overlay.clear_prefix(prefix);
444 self.backend.for_keys_with_prefix(prefix, |key| {
445 self.overlay.set_storage(key.to_vec(), None);
446 });
447 }
448
449 fn clear_child_prefix(
450 &mut self,
451 child_info: &ChildInfo,
452 prefix: &[u8],
453 ) {
454 trace!(target: "state", "{:04x}: ClearChildPrefix({}) {}",
455 self.id,
456 HexDisplay::from(&child_info.storage_key()),
457 HexDisplay::from(&prefix),
458 );
459 let _guard = guard();
460
461 self.mark_dirty();
462 self.overlay.clear_child_prefix(child_info, prefix);
463 self.backend.for_child_keys_with_prefix(child_info, prefix, |key| {
464 self.overlay.set_child_storage(child_info, key.to_vec(), None);
465 });
466 }
467
468 fn storage_append(
469 &mut self,
470 key: Vec<u8>,
471 value: Vec<u8>,
472 ) {
473 trace!(target: "state", "{:04x}: Append {}={}",
474 self.id,
475 HexDisplay::from(&key),
476 HexDisplay::from(&value),
477 );
478
479 let _guard = guard();
480 self.mark_dirty();
481
482 let backend = &mut self.backend;
483 let current_value = self.overlay.value_mut_or_insert_with(
484 &key,
485 || backend.storage(&key).expect(EXT_NOT_ALLOWED_TO_FAIL).unwrap_or_default()
486 );
487 StorageAppend::new(current_value).append(value);
488 }
489
490 fn storage_root(&mut self) -> Vec<u8> {
491 let _guard = guard();
492 if let Some(ref root) = self.storage_transaction_cache.transaction_storage_root {
493 trace!(target: "state", "{:04x}: Root(cached) {}",
494 self.id,
495 HexDisplay::from(&root.as_ref()),
496 );
497 return root.encode();
498 }
499
500 let root = self.overlay.storage_root(self.backend, self.storage_transaction_cache);
501 trace!(target: "state", "{:04x}: Root {}", self.id, HexDisplay::from(&root.as_ref()));
502 root.encode()
503 }
504
505 fn child_storage_root(
506 &mut self,
507 child_info: &ChildInfo,
508 ) -> Vec<u8> {
509 let _guard = guard();
510 let storage_key = child_info.storage_key();
511 let prefixed_storage_key = child_info.prefixed_storage_key();
512 if self.storage_transaction_cache.transaction_storage_root.is_some() {
513 let root = self
514 .storage(prefixed_storage_key.as_slice())
515 .and_then(|k| Decode::decode(&mut &k[..]).ok())
516 .unwrap_or_else(
517 || empty_child_trie_root::<Layout<H>>()
518 );
519 trace!(target: "state", "{:04x}: ChildRoot({})(cached) {}",
520 self.id,
521 HexDisplay::from(&storage_key),
522 HexDisplay::from(&root.as_ref()),
523 );
524 root.encode()
525 } else {
526 let root = if let Some((changes, info)) = self.overlay.child_changes(storage_key) {
527 let delta = changes.map(|(k, v)| (k.as_ref(), v.value().map(AsRef::as_ref)));
528 Some(self.backend.child_storage_root(info, delta))
529 } else {
530 None
531 };
532
533 if let Some((root, is_empty, _)) = root {
534 let root = root.encode();
535 if is_empty {
541 self.overlay.set_storage(prefixed_storage_key.into_inner(), None);
542 } else {
543 self.overlay.set_storage(prefixed_storage_key.into_inner(), Some(root.clone()));
544 }
545
546 trace!(target: "state", "{:04x}: ChildRoot({}) {}",
547 self.id,
548 HexDisplay::from(&storage_key.as_ref()),
549 HexDisplay::from(&root.as_ref()),
550 );
551 root
552 } else {
553 let root = self
555 .storage(prefixed_storage_key.as_slice())
556 .and_then(|k| Decode::decode(&mut &k[..]).ok())
557 .unwrap_or_else(
558 || empty_child_trie_root::<Layout<H>>()
559 );
560 trace!(target: "state", "{:04x}: ChildRoot({})(no_change) {}",
561 self.id,
562 HexDisplay::from(&storage_key.as_ref()),
563 HexDisplay::from(&root.as_ref()),
564 );
565 root.encode()
566 }
567 }
568 }
569
570 #[cfg(not(feature = "std"))]
571 fn storage_changes_root(&mut self, _parent_hash: &[u8]) -> Result<Option<Vec<u8>>, ()> {
572 Ok(None)
573 }
574
575 #[cfg(feature = "std")]
576 fn storage_changes_root(&mut self, parent_hash: &[u8]) -> Result<Option<Vec<u8>>, ()> {
577 let _guard = guard();
578 let root = self.overlay.changes_trie_root(
579 self.backend,
580 self.changes_trie_state.as_ref(),
581 Decode::decode(&mut &parent_hash[..]).map_err(|e|
582 trace!(
583 target: "state",
584 "Failed to decode changes root parent hash: {}",
585 e,
586 )
587 )?,
588 true,
589 self.storage_transaction_cache,
590 );
591
592 trace!(target: "state", "{:04x}: ChangesRoot({}) {:?}",
593 self.id,
594 HexDisplay::from(&parent_hash),
595 root,
596 );
597
598 root.map(|r| r.map(|o| o.encode()))
599 }
600
601 fn storage_start_transaction(&mut self) {
602 self.overlay.start_transaction()
603 }
604
605 fn storage_rollback_transaction(&mut self) -> Result<(), ()> {
606 self.mark_dirty();
607 self.overlay.rollback_transaction().map_err(|_| ())
608 }
609
610 fn storage_commit_transaction(&mut self) -> Result<(), ()> {
611 self.overlay.commit_transaction().map_err(|_| ())
612 }
613
614 fn wipe(&mut self) {
615 for _ in 0..self.overlay.transaction_depth() {
616 self.overlay.rollback_transaction().expect(BENCHMARKING_FN);
617 }
618 self.overlay.drain_storage_changes(
619 &self.backend,
620 #[cfg(feature = "std")]
621 None,
622 Default::default(),
623 self.storage_transaction_cache,
624 ).expect(EXT_NOT_ALLOWED_TO_FAIL);
625 self.backend.wipe().expect(EXT_NOT_ALLOWED_TO_FAIL);
626 self.mark_dirty();
627 self.overlay
628 .enter_runtime()
629 .expect("We have reset the overlay above, so we can not be in the runtime; qed");
630 }
631
632 fn commit(&mut self) {
633 for _ in 0..self.overlay.transaction_depth() {
634 self.overlay.commit_transaction().expect(BENCHMARKING_FN);
635 }
636 let changes = self.overlay.drain_storage_changes(
637 &self.backend,
638 #[cfg(feature = "std")]
639 None,
640 Default::default(),
641 self.storage_transaction_cache,
642 ).expect(EXT_NOT_ALLOWED_TO_FAIL);
643 self.backend.commit(
644 changes.transaction_storage_root,
645 changes.transaction,
646 changes.main_storage_changes,
647 changes.child_storage_changes,
648 ).expect(EXT_NOT_ALLOWED_TO_FAIL);
649 self.mark_dirty();
650 self.overlay
651 .enter_runtime()
652 .expect("We have reset the overlay above, so we can not be in the runtime; qed");
653 }
654
655 fn read_write_count(&self) -> (u32, u32, u32, u32) {
656 self.backend.read_write_count()
657 }
658
659 fn reset_read_write_count(&mut self) {
660 self.backend.reset_read_write_count()
661 }
662
663 fn get_whitelist(&self) -> Vec<TrackedStorageKey> {
664 self.backend.get_whitelist()
665 }
666
667 fn set_whitelist(&mut self, new: Vec<TrackedStorageKey>) {
668 self.backend.set_whitelist(new)
669 }
670}
671
672struct EncodeOpaqueValue(Vec<u8>);
674
675impl Encode for EncodeOpaqueValue {
676 fn using_encoded<R, F: FnOnce(&[u8]) -> R>(&self, f: F) -> R {
677 f(&self.0)
678 }
679}
680
681pub(crate) struct StorageAppend<'a>(&'a mut Vec<u8>);
683
684impl<'a> StorageAppend<'a> {
685 pub fn new(storage: &'a mut Vec<u8>) -> Self {
687 Self(storage)
688 }
689
690 pub fn append(&mut self, value: Vec<u8>) {
694 let value = vec![EncodeOpaqueValue(value)];
695
696 let item = tetcore_std::mem::take(self.0);
697
698 *self.0 = match Vec::<EncodeOpaqueValue>::append_or_new(item, &value) {
699 Ok(item) => item,
700 Err(_) => {
701 log_error!(
702 target: "runtime",
703 "Failed to append value, resetting storage item to `[value]`.",
704 );
705 value.encode()
706 }
707 };
708 }
709}
710
711#[cfg(not(feature = "std"))]
712impl<'a, H, N, B> ExtensionStore for Ext<'a, H, N, B>
713where
714 H: Hasher,
715 H::Out: Ord + 'static + codec::Codec,
716 B: Backend<H>,
717 N: crate::changes_trie::BlockNumber,
718{
719 fn extension_by_type_id(&mut self, _type_id: TypeId) -> Option<&mut dyn Any> {
720 None
721 }
722
723 fn register_extension_with_type_id(
724 &mut self,
725 _type_id: TypeId,
726 _extension: Box<dyn Extension>,
727 ) -> Result<(), externalities::Error> {
728 Err(externalities::Error::ExtensionsAreNotSupported)
729 }
730
731 fn deregister_extension_by_type_id(
732 &mut self,
733 _type_id: TypeId,
734 ) -> Result<(), externalities::Error> {
735 Err(externalities::Error::ExtensionsAreNotSupported)
736 }
737}
738
739#[cfg(feature = "std")]
740impl<'a, H, N, B> ExtensionStore for Ext<'a, H, N, B>
741where
742 H: Hasher,
743 B: 'a + Backend<H>,
744 N: crate::changes_trie::BlockNumber,
745{
746 fn extension_by_type_id(&mut self, type_id: TypeId) -> Option<&mut dyn Any> {
747 self.extensions.as_mut().and_then(|exts| exts.get_mut(type_id))
748 }
749
750 fn register_extension_with_type_id(
751 &mut self,
752 type_id: TypeId,
753 extension: Box<dyn Extension>,
754 ) -> Result<(), externalities::Error> {
755 if let Some(ref mut extensions) = self.extensions {
756 extensions.register(type_id, extension)
757 } else {
758 Err(externalities::Error::ExtensionsAreNotSupported)
759 }
760 }
761
762 fn deregister_extension_by_type_id(&mut self, type_id: TypeId) -> Result<(), externalities::Error> {
763 if let Some(ref mut extensions) = self.extensions {
764 if extensions.deregister(type_id) {
765 Ok(())
766 } else {
767 Err(externalities::Error::ExtensionIsNotRegistered(type_id))
768 }
769 } else {
770 Err(externalities::Error::ExtensionsAreNotSupported)
771 }
772 }
773}
774
775#[cfg(test)]
776mod tests {
777 use super::*;
778 use hex_literal::hex;
779 use num_traits::Zero;
780 use codec::Encode;
781 use tet_core::{
782 H256,
783 Blake2Hasher,
784 map,
785 storage::{
786 Storage,
787 StorageChild,
788 well_known_keys::EXTRINSIC_INDEX,
789 },
790 };
791 use crate::{
792 changes_trie::{
793 Configuration as ChangesTrieConfiguration,
794 InMemoryStorage as TestChangesTrieStorage,
795 }, InMemoryBackend,
796 };
797
798 type TestBackend = InMemoryBackend<Blake2Hasher>;
799 type TestExt<'a> = Ext<'a, Blake2Hasher, u64, TestBackend>;
800
801 fn prepare_overlay_with_changes() -> OverlayedChanges {
802 let mut changes = OverlayedChanges::default();
803 changes.set_collect_extrinsics(true);
804 changes.set_extrinsic_index(1);
805 changes.set_storage(vec![1], Some(vec![100]));
806 changes.set_storage(EXTRINSIC_INDEX.to_vec(), Some(3u32.encode()));
807 changes.set_offchain_storage(b"k1", Some(b"v1"));
808 changes.set_offchain_storage(b"k2", Some(b"v2"));
809 changes
810 }
811
812 fn changes_trie_config() -> ChangesTrieConfiguration {
813 ChangesTrieConfiguration {
814 digest_interval: 0,
815 digest_levels: 0,
816 }
817 }
818
819 #[test]
820 fn storage_changes_root_is_none_when_storage_is_not_provided() {
821 let mut overlay = prepare_overlay_with_changes();
822 let mut cache = StorageTransactionCache::default();
823 let backend = TestBackend::default();
824 let mut ext = TestExt::new(&mut overlay, &mut cache, &backend, None, None);
825 assert_eq!(ext.storage_changes_root(&H256::default().encode()).unwrap(), None);
826 }
827
828 #[test]
829 fn storage_changes_root_is_none_when_state_is_not_provided() {
830 let mut overlay = prepare_overlay_with_changes();
831 let mut cache = StorageTransactionCache::default();
832 let backend = TestBackend::default();
833 let mut ext = TestExt::new(&mut overlay, &mut cache, &backend, None, None);
834 assert_eq!(ext.storage_changes_root(&H256::default().encode()).unwrap(), None);
835 }
836
837 #[test]
838 fn storage_changes_root_is_some_when_extrinsic_changes_are_non_empty() {
839 let mut overlay = prepare_overlay_with_changes();
840 let mut cache = StorageTransactionCache::default();
841 let storage = TestChangesTrieStorage::with_blocks(vec![(99, Default::default())]);
842 let state = Some(ChangesTrieState::new(changes_trie_config(), Zero::zero(), &storage));
843 let backend = TestBackend::default();
844 let mut ext = TestExt::new(&mut overlay, &mut cache, &backend, state, None);
845 assert_eq!(
846 ext.storage_changes_root(&H256::default().encode()).unwrap(),
847 Some(hex!("bb0c2ef6e1d36d5490f9766cfcc7dfe2a6ca804504c3bb206053890d6dd02376").to_vec()),
848 );
849 }
850
851 #[test]
852 fn storage_changes_root_is_some_when_extrinsic_changes_are_empty() {
853 let mut overlay = prepare_overlay_with_changes();
854 let mut cache = StorageTransactionCache::default();
855 overlay.set_collect_extrinsics(false);
856 overlay.set_storage(vec![1], None);
857 let storage = TestChangesTrieStorage::with_blocks(vec![(99, Default::default())]);
858 let state = Some(ChangesTrieState::new(changes_trie_config(), Zero::zero(), &storage));
859 let backend = TestBackend::default();
860 let mut ext = TestExt::new(&mut overlay, &mut cache, &backend, state, None);
861 assert_eq!(
862 ext.storage_changes_root(&H256::default().encode()).unwrap(),
863 Some(hex!("96f5aae4690e7302737b6f9b7f8567d5bbb9eac1c315f80101235a92d9ec27f4").to_vec()),
864 );
865 }
866
867 #[test]
868 fn next_storage_key_works() {
869 let mut cache = StorageTransactionCache::default();
870 let mut overlay = OverlayedChanges::default();
871 overlay.set_storage(vec![20], None);
872 overlay.set_storage(vec![30], Some(vec![31]));
873 let backend = Storage {
874 top: map![
875 vec![10] => vec![10],
876 vec![20] => vec![20],
877 vec![40] => vec![40]
878 ],
879 children_default: map![]
880 }.into();
881
882 let ext = TestExt::new(&mut overlay, &mut cache, &backend, None, None);
883
884 assert_eq!(ext.next_storage_key(&[5]), Some(vec![10]));
886
887 assert_eq!(ext.next_storage_key(&[10]), Some(vec![30]));
889
890 assert_eq!(ext.next_storage_key(&[20]), Some(vec![30]));
892
893 assert_eq!(ext.next_storage_key(&[30]), Some(vec![40]));
895
896 drop(ext);
897 overlay.set_storage(vec![50], Some(vec![50]));
898 let ext = TestExt::new(&mut overlay, &mut cache, &backend, None, None);
899
900 assert_eq!(ext.next_storage_key(&[40]), Some(vec![50]));
902 }
903
904 #[test]
905 fn next_child_storage_key_works() {
906 let child_info = ChildInfo::new_default(b"Child1");
907 let child_info = &child_info;
908
909 let mut cache = StorageTransactionCache::default();
910 let mut overlay = OverlayedChanges::default();
911 overlay.set_child_storage(child_info, vec![20], None);
912 overlay.set_child_storage(child_info, vec![30], Some(vec![31]));
913 let backend = Storage {
914 top: map![],
915 children_default: map![
916 child_info.storage_key().to_vec() => StorageChild {
917 data: map![
918 vec![10] => vec![10],
919 vec![20] => vec![20],
920 vec![40] => vec![40]
921 ],
922 child_info: child_info.to_owned(),
923 }
924 ],
925 }.into();
926
927 let ext = TestExt::new(&mut overlay, &mut cache, &backend, None, None);
928
929 assert_eq!(ext.next_child_storage_key(child_info, &[5]), Some(vec![10]));
931
932 assert_eq!(ext.next_child_storage_key(child_info, &[10]), Some(vec![30]));
934
935 assert_eq!(ext.next_child_storage_key(child_info, &[20]), Some(vec![30]));
937
938 assert_eq!(ext.next_child_storage_key(child_info, &[30]), Some(vec![40]));
940
941 drop(ext);
942 overlay.set_child_storage(child_info, vec![50], Some(vec![50]));
943 let ext = TestExt::new(&mut overlay, &mut cache, &backend, None, None);
944
945 assert_eq!(ext.next_child_storage_key(child_info, &[40]), Some(vec![50]));
947 }
948
949 #[test]
950 fn child_storage_works() {
951 let child_info = ChildInfo::new_default(b"Child1");
952 let child_info = &child_info;
953 let mut cache = StorageTransactionCache::default();
954 let mut overlay = OverlayedChanges::default();
955 overlay.set_child_storage(child_info, vec![20], None);
956 overlay.set_child_storage(child_info, vec![30], Some(vec![31]));
957 let backend = Storage {
958 top: map![],
959 children_default: map![
960 child_info.storage_key().to_vec() => StorageChild {
961 data: map![
962 vec![10] => vec![10],
963 vec![20] => vec![20],
964 vec![30] => vec![40]
965 ],
966 child_info: child_info.to_owned(),
967 }
968 ],
969 }.into();
970
971 let ext = TestExt::new(&mut overlay, &mut cache, &backend, None, None);
972
973 assert_eq!(ext.child_storage(child_info, &[10]), Some(vec![10]));
974 assert_eq!(
975 ext.child_storage_hash(child_info, &[10]),
976 Some(Blake2Hasher::hash(&[10]).as_ref().to_vec()),
977 );
978
979 assert_eq!(ext.child_storage(child_info, &[20]), None);
980 assert_eq!(
981 ext.child_storage_hash(child_info, &[20]),
982 None,
983 );
984
985 assert_eq!(ext.child_storage(child_info, &[30]), Some(vec![31]));
986 assert_eq!(
987 ext.child_storage_hash(child_info, &[30]),
988 Some(Blake2Hasher::hash(&[31]).as_ref().to_vec()),
989 );
990 }
991
992 #[test]
993 fn clear_prefix_cannot_delete_a_child_root() {
994 let child_info = ChildInfo::new_default(b"Child1");
995 let child_info = &child_info;
996 let mut cache = StorageTransactionCache::default();
997 let mut overlay = OverlayedChanges::default();
998 let backend = Storage {
999 top: map![],
1000 children_default: map![
1001 child_info.storage_key().to_vec() => StorageChild {
1002 data: map![
1003 vec![30] => vec![40]
1004 ],
1005 child_info: child_info.to_owned(),
1006 }
1007 ],
1008 }.into();
1009
1010 let ext = TestExt::new(&mut overlay, &mut cache, &backend, None, None);
1011
1012 use tet_core::storage::well_known_keys;
1013 let mut ext = ext;
1014 let mut not_under_prefix = well_known_keys::CHILD_STORAGE_KEY_PREFIX.to_vec();
1015 not_under_prefix[4] = 88;
1016 not_under_prefix.extend(b"path");
1017 ext.set_storage(not_under_prefix.clone(), vec![10]);
1018
1019 ext.clear_prefix(&[]);
1020 ext.clear_prefix(&well_known_keys::CHILD_STORAGE_KEY_PREFIX[..4]);
1021 let mut under_prefix = well_known_keys::CHILD_STORAGE_KEY_PREFIX.to_vec();
1022 under_prefix.extend(b"path");
1023 ext.clear_prefix(&well_known_keys::CHILD_STORAGE_KEY_PREFIX[..4]);
1024 assert_eq!(ext.child_storage(child_info, &[30]), Some(vec![40]));
1025 assert_eq!(ext.storage(not_under_prefix.as_slice()), Some(vec![10]));
1026 ext.clear_prefix(¬_under_prefix[..5]);
1027 assert_eq!(ext.storage(not_under_prefix.as_slice()), None);
1028 }
1029
1030 #[test]
1031 fn storage_append_works() {
1032 let mut data = Vec::new();
1033 let mut append = StorageAppend::new(&mut data);
1034 append.append(1u32.encode());
1035 append.append(2u32.encode());
1036 drop(append);
1037
1038 assert_eq!(Vec::<u32>::decode(&mut &data[..]).unwrap(), vec![1, 2]);
1039
1040 let mut data = vec![1];
1042 let mut append = StorageAppend::new(&mut data);
1043 append.append(1u32.encode());
1044 append.append(2u32.encode());
1045 drop(append);
1046
1047 assert_eq!(Vec::<u32>::decode(&mut &data[..]).unwrap(), vec![1, 2]);
1048 }
1049}