feat(storage-server): add StorageServer<F: FileSystem> with BlockDevice trait, mock adapters, and tests

This commit is contained in:
2026-10-18 03:37:40 +02:00
parent b7bc223a79
commit 7a4600b3a2
13 changed files with 591 additions and 12 deletions

View File

@@ -0,0 +1,88 @@
use server_framework::{Decode, Encode};
use crate::filesystem::FileHandle;
#[derive(Debug, PartialEq)]
pub enum StorageRequest {
Open { path_word0: usize, path_word1: usize },
Read { handle: FileHandle, max_bytes: usize },
Write { handle: FileHandle, data_word: usize },
Close { handle: FileHandle },
ListDir { path_word0: usize, path_word1: usize },
Create { path_word0: usize, path_word1: usize },
Delete { path_word0: usize, path_word1: usize },
FileSize { handle: FileHandle },
}
#[derive(Debug, PartialEq)]
pub enum StorageResponse {
Handle(FileHandle),
Data { bytes_read: usize },
Written { bytes_written: usize },
Ok,
DirEntries { count: usize },
Size(usize),
NotFound,
Error,
}
impl Encode for StorageRequest {
fn encode(&self) -> [usize; 4] {
match self {
StorageRequest::Open { path_word0, path_word1 } => [0, *path_word0, *path_word1, 0],
StorageRequest::Read { handle, max_bytes } => [1, handle.raw() as usize, *max_bytes, 0],
StorageRequest::Write { handle, data_word } => [2, handle.raw() as usize, *data_word, 0],
StorageRequest::Close { handle } => [3, handle.raw() as usize, 0, 0],
StorageRequest::ListDir { path_word0, path_word1 } => [4, *path_word0, *path_word1, 0],
StorageRequest::Create { path_word0, path_word1 } => [5, *path_word0, *path_word1, 0],
StorageRequest::Delete { path_word0, path_word1 } => [6, *path_word0, *path_word1, 0],
StorageRequest::FileSize { handle } => [7, handle.raw() as usize, 0, 0],
}
}
}
impl Decode for StorageRequest {
fn decode(words: [usize; 4]) -> Option<Self> {
match words[0] {
0 => Some(StorageRequest::Open { path_word0: words[1], path_word1: words[2] }),
1 => Some(StorageRequest::Read { handle: FileHandle::new(words[1] as u16), max_bytes: words[2] }),
2 => Some(StorageRequest::Write { handle: FileHandle::new(words[1] as u16), data_word: words[2] }),
3 => Some(StorageRequest::Close { handle: FileHandle::new(words[1] as u16) }),
4 => Some(StorageRequest::ListDir { path_word0: words[1], path_word1: words[2] }),
5 => Some(StorageRequest::Create { path_word0: words[1], path_word1: words[2] }),
6 => Some(StorageRequest::Delete { path_word0: words[1], path_word1: words[2] }),
7 => Some(StorageRequest::FileSize { handle: FileHandle::new(words[1] as u16) }),
_ => None,
}
}
}
impl Encode for StorageResponse {
fn encode(&self) -> [usize; 4] {
match self {
StorageResponse::Handle(h) => [0, h.raw() as usize, 0, 0],
StorageResponse::Data { bytes_read } => [1, *bytes_read, 0, 0],
StorageResponse::Written { bytes_written } => [2, *bytes_written, 0, 0],
StorageResponse::Ok => [3, 0, 0, 0],
StorageResponse::DirEntries { count } => [4, *count, 0, 0],
StorageResponse::Size(s) => [5, *s, 0, 0],
StorageResponse::NotFound => [6, 0, 0, 0],
StorageResponse::Error => [7, 0, 0, 0],
}
}
}
impl Decode for StorageResponse {
fn decode(words: [usize; 4]) -> Option<Self> {
match words[0] {
0 => Some(StorageResponse::Handle(FileHandle::new(words[1] as u16))),
1 => Some(StorageResponse::Data { bytes_read: words[1] }),
2 => Some(StorageResponse::Written { bytes_written: words[1] }),
3 => Some(StorageResponse::Ok),
4 => Some(StorageResponse::DirEntries { count: words[1] }),
5 => Some(StorageResponse::Size(words[1])),
6 => Some(StorageResponse::NotFound),
7 => Some(StorageResponse::Error),
_ => None,
}
}
}