cache_srv/
lib.rs

1#![feature(naked_functions)]
2
3use std::{collections::BTreeMap, sync::Mutex, time::Instant};
4
5use twizzler_abi::{
6    object::ObjID,
7    syscall::{sys_object_ctrl, ObjectControlCmd},
8};
9use twizzler_rt_abi::{
10    object::{MapFlags, ObjectHandle},
11    Result,
12};
13
14#[derive(Debug, Clone, Copy)]
15#[repr(C)]
16pub struct CachedStats {
17    pub id: ObjID,
18    pub start: Instant,
19    pub flags: MapFlags,
20    pub addr: u64,
21}
22
23type Key = (ObjID, MapFlags);
24
25struct HeldObject {
26    start: Instant,
27    handle: ObjectHandle,
28}
29
30impl HeldObject {
31    fn new(handle: ObjectHandle) -> Self {
32        Self {
33            start: Instant::now(),
34            handle,
35        }
36    }
37}
38
39struct CacheState {
40    map: BTreeMap<Key, HeldObject>,
41}
42
43impl CacheState {
44    const fn new() -> Self {
45        Self {
46            map: BTreeMap::new(),
47        }
48    }
49}
50
51static STATE: Mutex<CacheState> = Mutex::new(CacheState::new());
52
53#[secgate::secure_gate]
54pub fn hold(id: ObjID, flags: MapFlags) -> Result<bool> {
55    let handle = twizzler_rt_abi::object::twz_rt_map_object(id, flags)?;
56    let mut state = STATE.lock().unwrap();
57    Ok(state
58        .map
59        .insert((id, flags), HeldObject::new(handle))
60        .is_some())
61}
62
63#[secgate::secure_gate]
64pub fn drop(id: ObjID, flags: MapFlags) -> Result<bool> {
65    let mut state = STATE.lock().unwrap();
66    Ok(state.map.remove(&(id, flags)).is_some())
67}
68
69#[secgate::secure_gate]
70pub fn preload(id: ObjID) -> Result<()> {
71    sys_object_ctrl(id, ObjectControlCmd::Preload)
72}
73
74#[secgate::secure_gate]
75pub fn stat(_id: ObjID) -> Result<()> {
76    Ok(())
77}
78
79#[secgate::secure_gate]
80pub fn list_nth(nth: u64) -> Result<Option<CachedStats>> {
81    let state = STATE.lock().unwrap();
82    if let Some(v) = state.map.values().nth(nth as usize) {
83        Ok(Some(CachedStats {
84            id: v.handle.id(),
85            flags: v.handle.map_flags(),
86            start: v.start,
87            addr: v.handle.start().addr() as u64,
88        }))
89    } else {
90        Ok(None)
91    }
92}