1#![allow(unsafe_code)]
2
3use crate::{
4 AccessPolicy, HostView, PersistTrigger,
5 policy::PersistPolicy,
6 storage::{NoStage, ShadowStorageBase, WithStage},
7 types::StagingBuffer,
8 view::HostViewStaged,
9};
10
11pub struct HostShadow<'a, const TS: usize, const BS: usize, const BC: usize, AP, PP, PT, PK, SS>
12where
13 AP: AccessPolicy,
14 PP: PersistPolicy<PK>,
15 PT: PersistTrigger<PK>,
16 bitmaps::BitsImpl<BC>: bitmaps::Bits,
17{
18 storage: &'a ShadowStorageBase<TS, BS, BC, AP, PP, PT, PK, SS>,
19}
20
21impl<'a, const TS: usize, const BS: usize, const BC: usize, AP, PP, PT, PK, SS>
22 HostShadow<'a, TS, BS, BC, AP, PP, PT, PK, SS>
23where
24 AP: AccessPolicy,
25 PP: PersistPolicy<PK>,
26 PT: PersistTrigger<PK>,
27 bitmaps::BitsImpl<BC>: bitmaps::Bits,
28{
29 pub(crate) fn new(storage: &'a ShadowStorageBase<TS, BS, BC, AP, PP, PT, PK, SS>) -> Self {
30 Self { storage }
31 }
32}
33
34impl<'a, const TS: usize, const BS: usize, const BC: usize, AP, PP, PT, PK>
35 HostShadow<'a, TS, BS, BC, AP, PP, PT, PK, NoStage>
36where
37 AP: AccessPolicy,
38 PP: PersistPolicy<PK>,
39 PT: PersistTrigger<PK>,
40 bitmaps::BitsImpl<BC>: bitmaps::Bits,
41{
42 pub fn with_view<R>(
43 &self,
44 f: impl FnOnce(&mut HostView<TS, BS, BC, AP, PP, PT, PK>) -> R,
45 ) -> R {
46 critical_section::with(|_| unsafe { self.with_view_unchecked(f) })
47 }
48
49 pub unsafe fn with_view_unchecked<R>(
54 &self,
55 f: impl FnOnce(&mut HostView<TS, BS, BC, AP, PP, PT, PK>) -> R,
56 ) -> R {
57 let table = unsafe { &mut *self.storage.table.get() };
58 let persist_trigger = unsafe { &mut *self.storage.persist_trigger.get() };
59 let access_policy = &self.storage.access_policy;
60 let persist_policy = &self.storage.persist_policy;
61 let mut view = HostView::new(table, access_policy, persist_policy, persist_trigger);
62 f(&mut view)
63 }
64}
65
66impl<'a, const TS: usize, const BS: usize, const BC: usize, AP, PP, PT, PK, SB>
67 HostShadow<'a, TS, BS, BC, AP, PP, PT, PK, WithStage<SB>>
68where
69 AP: AccessPolicy,
70 PP: PersistPolicy<PK>,
71 PT: PersistTrigger<PK>,
72 bitmaps::BitsImpl<BC>: bitmaps::Bits,
73 SB: StagingBuffer,
74{
75 pub fn with_view<R>(
76 &self,
77 f: impl FnOnce(&mut HostViewStaged<TS, BS, BC, AP, PP, PT, PK, SB>) -> R,
78 ) -> R {
79 critical_section::with(|_| unsafe { self.with_view_unchecked(f) })
80 }
81
82 pub unsafe fn with_view_unchecked<R>(
87 &self,
88 f: impl FnOnce(&mut HostViewStaged<TS, BS, BC, AP, PP, PT, PK, SB>) -> R,
89 ) -> R {
90 let table = unsafe { &mut *self.storage.table.get() };
91 let stage = unsafe { &mut *self.storage.stage_state.get() };
92 let persist_trigger = unsafe { &mut *self.storage.persist_trigger.get() };
93 let access_policy = &self.storage.access_policy;
94 let persist_policy = &self.storage.persist_policy;
95 let base = HostView::new(table, access_policy, persist_policy, persist_trigger);
96 let mut view = HostViewStaged::new(base, &mut stage.sb);
97 f(&mut view)
98 }
99}