1use core::{cell::UnsafeCell, marker::PhantomData};
2
3use bitmaps::{Bits, BitsImpl};
4
5use crate::{
6 persist::PersistTrigger,
7 policy::{AccessPolicy, PersistPolicy},
8 shadow::{HostShadow, KernelShadow},
9 table::ShadowTable,
10 types::StagingBuffer,
11};
12
13pub struct NoStage;
14
15pub struct WithStage<SB: StagingBuffer> {
16 pub(crate) sb: SB,
17}
18
19pub struct ShadowStorageBase<const TS: usize, const BS: usize, const BC: usize, AP, PP, PT, PK, SS>
20where
21 AP: AccessPolicy,
22 PP: PersistPolicy<PK>,
23 PT: PersistTrigger<PK>,
24 BitsImpl<BC>: Bits,
25{
26 pub(crate) table: UnsafeCell<ShadowTable<TS, BS, BC>>,
27 pub(crate) access_policy: AP,
28 pub(crate) persist_policy: PP,
29 pub(crate) persist_trigger: UnsafeCell<PT>,
30 pub(crate) stage_state: UnsafeCell<SS>,
31 _phantom: PhantomData<PK>,
32}
33
34pub type ShadowStorage<const TS: usize, const BS: usize, const BC: usize, AP, PP, PT, PK> =
35 ShadowStorageBase<TS, BS, BC, AP, PP, PT, PK, NoStage>;
36
37impl<const TS: usize, const BS: usize, const BC: usize, AP, PP, PT, PK>
38 ShadowStorageBase<TS, BS, BC, AP, PP, PT, PK, NoStage>
39where
40 AP: AccessPolicy,
41 PP: PersistPolicy<PK>,
42 PT: PersistTrigger<PK>,
43 BitsImpl<BC>: Bits,
44{
45 pub fn new(policy: AP, persist: PP, trigger: PT) -> Self {
46 Self {
47 table: UnsafeCell::new(ShadowTable::new()),
48 access_policy: policy,
49 persist_policy: persist,
50 persist_trigger: UnsafeCell::new(trigger),
51 stage_state: UnsafeCell::new(NoStage),
52 _phantom: PhantomData,
53 }
54 }
55
56 pub fn with_staging<SB: StagingBuffer>(
58 self,
59 sb: SB,
60 ) -> ShadowStorageBase<TS, BS, BC, AP, PP, PT, PK, WithStage<SB>> {
61 ShadowStorageBase {
62 table: self.table,
63 access_policy: self.access_policy,
64 persist_policy: self.persist_policy,
65 persist_trigger: self.persist_trigger,
66 stage_state: UnsafeCell::new(WithStage { sb }),
67 _phantom: PhantomData,
68 }
69 }
70}
71
72impl<const TS: usize, const BS: usize, const BC: usize, AP, PP, PT, PK, SS>
73 ShadowStorageBase<TS, BS, BC, AP, PP, PT, PK, SS>
74where
75 AP: AccessPolicy,
76 PP: PersistPolicy<PK>,
77 PT: PersistTrigger<PK>,
78 BitsImpl<BC>: Bits,
79{
80 pub fn host_shadow(&self) -> HostShadow<'_, TS, BS, BC, AP, PP, PT, PK, SS> {
81 HostShadow::new(self)
82 }
83
84 pub fn kernel_shadow(&self) -> KernelShadow<'_, TS, BS, BC, AP, PP, PT, PK, SS> {
85 KernelShadow::new(self)
86 }
87}