Skip to content

Commit 230a022

Browse files
committed
Push the KV buffer into DataModelState
1 parent 3b5a27d commit 230a022

20 files changed

Lines changed: 396 additions & 217 deletions

bloat-check/src/bin/bloat-check.rs

Lines changed: 13 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,9 @@
4141
#![recursion_limit = "256"]
4242

4343
use core::future::Future;
44-
use core::mem::{size_of_val, MaybeUninit};
44+
use core::mem::size_of_val;
45+
#[cfg(target_os = "none")]
46+
use core::mem::MaybeUninit;
4547

4648
// Logging - `defmt` for embedded targets, `log` for others
4749
#[cfg(target_os = "none")]
@@ -69,20 +71,18 @@ use rs_matter::dm::clusters::wifi_diag::{
6971
use rs_matter::dm::devices::test::{DAC_PRIVKEY, TEST_DEV_ATT, TEST_DEV_COMM, TEST_DEV_DET};
7072
use rs_matter::dm::devices::DEV_TYPE_ON_OFF_LIGHT;
7173
use rs_matter::dm::endpoints::WifiSysHandler;
72-
use rs_matter::dm::events::DEFAULT_MAX_EVENTS_BUF_SIZE;
7374
use rs_matter::dm::networks::wireless::{
7475
NetCtlState, NetCtlStateMutex, NetCtlWithStatusImpl, WifiNetworks,
7576
};
7677
use rs_matter::dm::networks::NetChangeNotif;
77-
use rs_matter::dm::subscriptions::DEFAULT_MAX_SUBSCRIPTIONS;
7878
use rs_matter::dm::{endpoints, IMBuffer};
7979
use rs_matter::dm::{
8080
Async, DataModel, Dataver, Endpoint, EpClMatcher, Node, WirelessDataModelState,
8181
};
8282
use rs_matter::error::Error;
8383
use rs_matter::pairing::qr::QrTextType;
8484
use rs_matter::pairing::DiscoveryCapabilities;
85-
use rs_matter::persist::{DummyKvBlobStore, SharedKvBlobStore};
85+
use rs_matter::persist::{DummyKvBlobStore, SharedKvBlobStore, DEFAULT_KV_BUF_SIZE};
8686
use rs_matter::respond::DefaultResponder;
8787
use rs_matter::sc::pase::MAX_COMM_WINDOW_TIMEOUT_SECS;
8888
use rs_matter::tlv::Nullable;
@@ -162,8 +162,6 @@ struct MatterStack<'a> {
162162
state: WirelessDataModelState<WifiNetworks<3>>,
163163
net_ctl_state: NetCtlStateMutex,
164164
btp: Btp,
165-
// We don't run a persistence task, but emulate its typical memory consumnption
166-
psm_buffer: MaybeUninit<[u8; 4096]>,
167165
}
168166

169167
impl<'a> MatterStack<'a> {
@@ -180,7 +178,6 @@ impl<'a> MatterStack<'a> {
180178
state <- WirelessDataModelState::init(WifiNetworks::init()),
181179
net_ctl_state <- NetCtlState::init_with_mutex(),
182180
btp <- Btp::init(),
183-
psm_buffer: MaybeUninit::zeroed(),
184181
})
185182
}
186183
}
@@ -198,24 +195,20 @@ type AppDmHandler<'a> = handler_chain_type!(
198195
type AppCrypto = RustCrypto<'static, WeakTestOnlyRand>;
199196
type AppDataModel<'a> = DataModel<
200197
'a,
201-
DEFAULT_MAX_SUBSCRIPTIONS,
202-
DEFAULT_MAX_EVENTS_BUF_SIZE,
203198
&'a AppCrypto,
204199
PooledBuffers<10, IMBuffer>,
205200
(Node<'a>, &'a AppDmHandler<'a>),
206-
SharedKvBlobStore<DummyKvBlobStore, &'static mut [u8]>,
201+
DummyKvBlobStore,
207202
WifiNetworks<3>,
208203
&'a AppNetCtl<'a>,
209204
>;
210205
type AppResponder<'d, 'a> = DefaultResponder<
211206
'd,
212207
'a,
213-
DEFAULT_MAX_SUBSCRIPTIONS,
214-
DEFAULT_MAX_EVENTS_BUF_SIZE,
215208
&'a AppCrypto,
216209
PooledBuffers<10, IMBuffer>,
217210
(Node<'a>, &'a AppDmHandler<'a>),
218-
SharedKvBlobStore<DummyKvBlobStore, &'static mut [u8]>,
211+
DummyKvBlobStore,
219212
WifiNetworks<3>,
220213
&'a AppNetCtl<'a>,
221214
>;
@@ -289,11 +282,10 @@ fn main() -> ! {
289282
&mut stack_total,
290283
);
291284
report_size("BTP", size_of_val(&stack.btp), &mut stack_total);
292-
report_size(
293-
"Persister buffer",
294-
size_of_val(&stack.psm_buffer),
295-
&mut stack_total,
296-
);
285+
// The KV/persister scratch buffer now lives inside `DataModelState` (behind a
286+
// blocking mutex) rather than in the `SharedKvBlobStore`. It is not visible
287+
// through the per-component accessors above, so account for it explicitly.
288+
report_size("KV scratch buffer", DEFAULT_KV_BUF_SIZE, &mut stack_total);
297289

298290
report_subtotal_size("TOTAL MATTER STACK ", stack_total);
299291

@@ -322,8 +314,9 @@ fn main() -> ! {
322314

323315
let mut rand = unwrap!(crypto.weak_rand());
324316

325-
let kv_buf = unsafe { stack.psm_buffer.assume_init_mut() }.as_mut_slice();
326-
let kv = SharedKvBlobStore::new(DummyKvBlobStore, kv_buf);
317+
// The KV scratch buffer now lives inside `DataModelState` (see the "KV scratch
318+
// buffer" line in the memory report); the store itself is buffer-less.
319+
let kv = SharedKvBlobStore::new(DummyKvBlobStore);
327320

328321
// A Wireless handler with a sample app cluster (on-off)
329322
let handler = mk_static!(

examples/src/bin/bridge.rs

Lines changed: 9 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -69,17 +69,20 @@ fn main() -> Result<(), Error> {
6969
let mut matter = Matter::new(&TEST_DEV_DET, TEST_DEV_COMM, &TEST_DEV_ATT, MATTER_PORT);
7070

7171
// Persistence
72-
let mut kv_buf = [0; 4096];
7372
let mut kv = DirKvBlobStore::new_default();
74-
futures_lite::future::block_on(matter.load_persist(&mut kv, &mut kv_buf))?;
7573

7674
// Create the transport buffers
7775
let buffers = PooledBuffers::<10, _>::new(0);
7876

79-
// Create the data model state (subscriptions, events, network store) and load
80-
// the persisted event counter.
77+
// Create the data model state (subscriptions, events, network store). It owns
78+
// the KV scratch buffer, which the startup loads below reuse rather than
79+
// allocating a separate one.
8180
let mut state: EthDataModelState = EthDataModelState::new(EthNetwork::new_default());
82-
futures_lite::future::block_on(state.load_persist(&mut kv, &mut kv_buf))?;
81+
82+
// Re-hydrate the `Matter` instance and the data model state (event-number
83+
// epoch) using the state's own scratch buffer.
84+
futures_lite::future::block_on(matter.load_persist(&mut kv, state.kv_buf_mut()))?;
85+
futures_lite::future::block_on(state.load_persist(&mut kv))?;
8386

8487
// Create the crypto instance
8588
let crypto = default_crypto(rand::thread_rng(), DAC_PRIVKEY);
@@ -104,7 +107,7 @@ fn main() -> Result<(), Error> {
104107
&crypto,
105108
&buffers,
106109
dm_handler(rand, &on_off_handler_ep2, &on_off_handler_ep3),
107-
SharedKvBlobStore::new(kv, kv_buf.as_mut_slice()),
110+
SharedKvBlobStore::new(kv),
108111
&state,
109112
);
110113

examples/src/bin/camera_tests.rs

Lines changed: 9 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -371,7 +371,6 @@ type WebRtc = WebRtcProvHandler<StubWebRtcHooks, N_SESSIONS, SDP_LEN, OUT_LEN, C
371371

372372
static MATTER: StaticCell<Matter> = StaticCell::new();
373373
static BUFFERS: StaticCell<PooledBuffers<10, rs_matter::dm::IMBuffer>> = StaticCell::new();
374-
static KV_BUF: StaticCell<[u8; 4096]> = StaticCell::new();
375374
static WEBRTC: StaticCell<WebRtc> = StaticCell::new();
376375
static CAM_AV: StaticCell<CamAv> = StaticCell::new();
377376
static CAM_AV_SETTINGS: StaticCell<
@@ -405,16 +404,19 @@ fn main() -> Result<(), Error> {
405404
args::port_override(),
406405
));
407406

408-
let kv_buf = KV_BUF.uninit().init_zeroed().as_mut_slice();
409407
let mut kv = args::file_kv_store();
410-
futures_lite::future::block_on(matter.load_persist(&mut kv, kv_buf))?;
411408

412409
let buffers = BUFFERS.uninit().init_with(PooledBuffers::init(0));
413410

414-
// Create the data model state (subscriptions, events, network store) and load
415-
// the persisted event counter.
411+
// Create the data model state (subscriptions, events, network store). It owns
412+
// the KV scratch buffer, which the startup loads below reuse rather than
413+
// allocating a separate one.
416414
let mut state: EthDataModelState = EthDataModelState::new(EthNetwork::new_default());
417-
futures_lite::future::block_on(state.load_persist(&mut kv, kv_buf))?;
415+
416+
// Re-hydrate the `Matter` instance and the data model state (event-number
417+
// epoch) using the state's own scratch buffer.
418+
futures_lite::future::block_on(matter.load_persist(&mut kv, state.kv_buf_mut()))?;
419+
futures_lite::future::block_on(state.load_persist(&mut kv))?;
418420

419421
let crypto = default_crypto(rand::thread_rng(), DAC_PRIVKEY);
420422
let mut rand = crypto.rand()?;
@@ -572,7 +574,7 @@ fn main() -> Result<(), Error> {
572574
push_av,
573575
chime,
574576
),
575-
SharedKvBlobStore::new(kv, kv_buf),
577+
SharedKvBlobStore::new(kv),
576578
&state,
577579
);
578580

examples/src/bin/dimmable_light.rs

Lines changed: 9 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -76,17 +76,20 @@ fn main() -> Result<(), Error> {
7676
let mut matter = Matter::new(&TEST_DEV_DET, TEST_DEV_COMM, &TEST_DEV_ATT, MATTER_PORT);
7777

7878
// Persistence
79-
let mut kv_buf = [0u8; 4096];
8079
let mut kv = rs_matter::persist::DirKvBlobStore::new_default();
81-
futures_lite::future::block_on(matter.load_persist(&mut kv, &mut kv_buf))?;
8280

8381
// Create the transport buffers
8482
let buffers = PooledBuffers::<10, IMBuffer>::new(0);
8583

86-
// Create the data model state (subscriptions, events, network store) and load
87-
// the persisted event counter.
84+
// Create the data model state (subscriptions, events, network store). It owns
85+
// the KV scratch buffer, which the startup loads below reuse rather than
86+
// allocating a separate one.
8887
let mut state: EthDataModelState = EthDataModelState::new(EthNetwork::new_default());
89-
futures_lite::future::block_on(state.load_persist(&mut kv, &mut kv_buf))?;
88+
89+
// Re-hydrate the `Matter` instance and the data model state (event-number
90+
// epoch) using the state's own scratch buffer.
91+
futures_lite::future::block_on(matter.load_persist(&mut kv, state.kv_buf_mut()))?;
92+
futures_lite::future::block_on(state.load_persist(&mut kv))?;
9093

9194
// Create the crypto instance
9295
let crypto = default_crypto(rand::thread_rng(), DAC_PRIVKEY);
@@ -119,7 +122,7 @@ fn main() -> Result<(), Error> {
119122
&crypto,
120123
&buffers,
121124
dm_handler(rand, &on_off_handler, &level_control_handler),
122-
SharedKvBlobStore::new(kv, kv_buf),
125+
SharedKvBlobStore::new(kv),
123126
&state,
124127
);
125128

examples/src/bin/light_tests.rs

Lines changed: 9 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,6 @@ mod args;
7979
static MATTER: StaticCell<Matter> = StaticCell::new();
8080
static BUFFERS: StaticCell<PooledBuffers<10, IMBuffer>> = StaticCell::new();
8181
static STATE: StaticCell<EthDataModelState> = StaticCell::new();
82-
static KV_BUF: StaticCell<[u8; 4096]> = StaticCell::new();
8382

8483
fn main() -> Result<(), Error> {
8584
let thread = std::thread::Builder::new()
@@ -106,16 +105,19 @@ fn run() -> Result<(), Error> {
106105
args::port_override(),
107106
));
108107

109-
let kv_buf = KV_BUF.uninit().init_zeroed().as_mut_slice();
110108
let mut kv = args::file_kv_store();
111-
futures_lite::future::block_on(matter.load_persist(&mut kv, kv_buf))?;
112109

113110
let buffers = BUFFERS.uninit().init_with(PooledBuffers::init(0));
114111

115-
// Create the data model state (subscriptions, events, network store) and load
116-
// the persisted event counter.
112+
// Create the data model state (subscriptions, events, network store). It owns
113+
// the KV scratch buffer, which the startup loads below reuse rather than
114+
// allocating a separate one.
117115
let state = STATE.init(EthDataModelState::new(EthNetwork::new_default()));
118-
futures_lite::future::block_on(state.load_persist(&mut kv, kv_buf))?;
116+
117+
// Re-hydrate the `Matter` instance and the data model state (event-number
118+
// epoch) using the state's own scratch buffer.
119+
futures_lite::future::block_on(matter.load_persist(&mut kv, state.kv_buf_mut()))?;
120+
futures_lite::future::block_on(state.load_persist(&mut kv))?;
119121

120122
let crypto = default_crypto(rand::thread_rng(), DAC_PRIVKEY);
121123
let mut rand = crypto.rand()?;
@@ -160,7 +162,7 @@ fn run() -> Result<(), Error> {
160162
&level_control_handler,
161163
&color_control_handler,
162164
),
163-
SharedKvBlobStore::new(kv, kv_buf),
165+
SharedKvBlobStore::new(kv),
164166
state,
165167
);
166168

examples/src/bin/media_player.rs

Lines changed: 9 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -85,17 +85,20 @@ fn main() -> Result<(), Error> {
8585
let mut matter = Matter::new(&TEST_DEV_DET, TEST_DEV_COMM, &TEST_DEV_ATT, MATTER_PORT);
8686

8787
// Persistence
88-
let mut kv_buf = [0; 4096];
8988
let mut kv = DirKvBlobStore::new_default();
90-
futures_lite::future::block_on(matter.load_persist(&mut kv, &mut kv_buf))?;
9189

9290
// Create the transport buffers
9391
let buffers = PooledBuffers::<10, _>::new(0);
9492

95-
// Create the data model state (subscriptions, events, network store) and load
96-
// the persisted event counter.
93+
// Create the data model state (subscriptions, events, network store). It owns
94+
// the KV scratch buffer, which the startup loads below reuse rather than
95+
// allocating a separate one.
9796
let mut state: EthDataModelState = EthDataModelState::new(EthNetwork::new_default());
98-
futures_lite::future::block_on(state.load_persist(&mut kv, &mut kv_buf))?;
97+
98+
// Re-hydrate the `Matter` instance and the data model state (event-number
99+
// epoch) using the state's own scratch buffer.
100+
futures_lite::future::block_on(matter.load_persist(&mut kv, state.kv_buf_mut()))?;
101+
futures_lite::future::block_on(state.load_persist(&mut kv))?;
99102

100103
// Create the crypto instance
101104
let crypto = default_crypto(rand::thread_rng(), DAC_PRIVKEY);
@@ -115,7 +118,7 @@ fn main() -> Result<(), Error> {
115118
&crypto,
116119
&buffers,
117120
dm_handler(rand, &on_off_handler),
118-
SharedKvBlobStore::new(kv, kv_buf.as_mut_slice()),
121+
SharedKvBlobStore::new(kv),
119122
&state,
120123
);
121124

examples/src/bin/onoff_light.rs

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -61,15 +61,19 @@ fn main() -> Result<(), Error> {
6161
let mut matter = Matter::new(&TEST_DEV_DET, TEST_DEV_COMM, &TEST_DEV_ATT, MATTER_PORT);
6262

6363
// Persistence
64-
let mut kv_buf = [0u8; 4096];
6564
let mut kv = DirKvBlobStore::new_default();
66-
futures_lite::future::block_on(matter.load_persist(&mut kv, &mut kv_buf))?;
6765

6866
// Create the transport buffers
6967
let buffers = PooledBuffers::<10, IMBuffer>::new(0);
7068

71-
// Create the data model state (subscriptions table, events queue, network store)
72-
let state: EthDataModelState = EthDataModelState::new(EthNetwork::new_default());
69+
// Create the data model state (subscriptions table, events queue, network
70+
// store). It owns the KV scratch buffer, which we reuse for the startup load
71+
// below rather than allocating a separate one.
72+
let mut state: EthDataModelState = EthDataModelState::new(EthNetwork::new_default());
73+
74+
// Re-hydrate the `Matter` instance (fabrics, ACLs, basic info) using the
75+
// state's own scratch buffer.
76+
futures_lite::future::block_on(matter.load_persist(&mut kv, state.kv_buf_mut()))?;
7377

7478
// Create the crypto instance
7579
let crypto = default_crypto(rand::thread_rng(), DAC_PRIVKEY);
@@ -89,7 +93,7 @@ fn main() -> Result<(), Error> {
8993
&crypto,
9094
&buffers,
9195
dm_handler(rand, &on_off_handler),
92-
SharedKvBlobStore::new(kv, kv_buf),
96+
SharedKvBlobStore::new(kv),
9397
&state,
9498
);
9599

examples/src/bin/onoff_light_bt.rs

Lines changed: 11 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -126,23 +126,22 @@ fn run<N: NetCtl + WifiDiag + NetChangeNotif>(
126126
// Create the Matter object
127127
let mut matter = Matter::new(&TEST_DEV_DET, TEST_DEV_COMM, &TEST_DEV_ATT, MATTER_PORT);
128128

129-
// A storage for the Wifi networks, re-hydrated from persistence.
130-
let mut networks = WifiNetworks::<3>::new();
131-
132129
// Persistence
133-
let mut kv_buf = [0; 4096];
134130
let mut kv = DirKvBlobStore::new_default();
135-
futures_lite::future::block_on(matter.load_persist(&mut kv, &mut kv_buf))?;
136-
futures_lite::future::block_on(networks.load_persist(&mut kv, &mut kv_buf))?;
137131

138132
// Create the transport buffers
139133
let buffers = PooledBuffers::<10, _>::new(0);
140134

141-
// Create the data model state (subscriptions, events, the Wifi network store)
142-
// and load the persisted event counter. The (raw) network store was loaded
143-
// above, before being moved into the state.
144-
let mut state: WirelessDataModelState<WifiNetworks<3>> = WirelessDataModelState::new(networks);
145-
futures_lite::future::block_on(state.load_persist(&mut kv, &mut kv_buf))?;
135+
// Create the data model state (subscriptions, events, the Wifi network store).
136+
// It owns the KV scratch buffer, so the one-time startup loads below reuse it
137+
// (`state.kv_buf_mut()`) rather than allocating a separate buffer.
138+
let mut state: WirelessDataModelState<WifiNetworks<3>> =
139+
WirelessDataModelState::new(WifiNetworks::new());
140+
141+
// Re-hydrate persisted state: the `Matter` instance (fabrics, ACLs, basic
142+
// info) and the data model state itself (event-number epoch + Wifi networks).
143+
futures_lite::future::block_on(matter.load_persist(&mut kv, state.kv_buf_mut()))?;
144+
futures_lite::future::block_on(state.load_persist(&mut kv))?;
146145

147146
// Create the crypto instance
148147
let crypto = default_crypto(rand::thread_rng(), DAC_PRIVKEY);
@@ -169,7 +168,7 @@ fn run<N: NetCtl + WifiDiag + NetChangeNotif>(
169168
&crypto,
170169
&buffers,
171170
dm_handler(rand, &on_off_handler, &net_ctl, &net_ctl),
172-
SharedKvBlobStore::new(kv, kv_buf.as_mut_slice()),
171+
SharedKvBlobStore::new(kv),
173172
&net_ctl,
174173
&state,
175174
);

0 commit comments

Comments
 (0)