1use axdriver::prelude::*;
2
3const BLOCK_SIZE: usize = 512;
4
5pub struct Disk {
7 block_id: u64,
8 offset: usize,
9 dev: AxBlockDevice,
10}
11
12impl Disk {
13 pub fn new(dev: AxBlockDevice) -> Self {
15 assert_eq!(BLOCK_SIZE, dev.block_size());
16 Self {
17 block_id: 0,
18 offset: 0,
19 dev,
20 }
21 }
22
23 pub fn size(&self) -> u64 {
25 self.dev.num_blocks() * BLOCK_SIZE as u64
26 }
27
28 pub fn position(&self) -> u64 {
30 self.block_id * BLOCK_SIZE as u64 + self.offset as u64
31 }
32
33 pub fn set_position(&mut self, pos: u64) {
35 self.block_id = pos / BLOCK_SIZE as u64;
36 self.offset = pos as usize % BLOCK_SIZE;
37 }
38
39 pub fn read_one(&mut self, buf: &mut [u8]) -> DevResult<usize> {
41 let read_size = if self.offset == 0 && buf.len() >= BLOCK_SIZE {
42 let mut data = [0u8; BLOCK_SIZE];
44 self.dev.read_block(self.block_id, &mut data)?;
45 buf[0..BLOCK_SIZE].copy_from_slice(&data);
46 self.block_id += 1;
49 BLOCK_SIZE
50 } else {
51 let mut data = [0u8; BLOCK_SIZE];
53 let start = self.offset;
54 let count = buf.len().min(BLOCK_SIZE - self.offset);
55
56 self.dev.read_block(self.block_id, &mut data)?;
57 buf[..count].copy_from_slice(&data[start..start + count]);
58
59 self.offset += count;
60 if self.offset >= BLOCK_SIZE {
61 self.block_id += 1;
62 self.offset -= BLOCK_SIZE;
63 }
64 count
65 };
66 Ok(read_size)
67 }
68
69 pub fn write_one(&mut self, buf: &[u8]) -> DevResult<usize> {
71 let write_size = if self.offset == 0 && buf.len() >= BLOCK_SIZE {
72 let data = buf[0..BLOCK_SIZE].to_vec();
77 self.dev.write_block(self.block_id, &data)?;
78 self.block_id += 1;
79 BLOCK_SIZE
80 } else {
81 let mut data = [0u8; BLOCK_SIZE];
83 let start = self.offset;
84 let count = buf.len().min(BLOCK_SIZE - self.offset);
85
86 self.dev.read_block(self.block_id, &mut data)?;
87 data[start..start + count].copy_from_slice(&buf[..count]);
88 self.dev.write_block(self.block_id, &data)?;
89
90 self.offset += count;
91 if self.offset >= BLOCK_SIZE {
92 self.block_id += 1;
93 self.offset -= BLOCK_SIZE;
94 }
95 count
96 };
97 Ok(write_size)
98 }
99
100 #[allow(unused)]
102 pub fn read_offset(&mut self, offset: usize) -> [u8; BLOCK_SIZE] {
103 let block_id = offset / BLOCK_SIZE;
104 let mut block_data = [0u8; BLOCK_SIZE];
105 self.dev
106 .read_block(block_id as u64, &mut block_data)
107 .unwrap();
108 block_data
109 }
110
111 #[allow(unused)]
113 pub fn write_offset(&mut self, offset: usize, buf: &[u8]) -> DevResult<usize> {
114 assert!(
115 buf.len() == BLOCK_SIZE,
116 "Buffer length must be equal to BLOCK_SIZE"
117 );
118 assert!(offset % BLOCK_SIZE == 0);
119 let block_id = offset / BLOCK_SIZE;
120 self.dev.write_block(block_id as u64, buf).unwrap();
121 Ok(buf.len())
122 }
123}