1use inherit_methods_macro::inherit_methods;
6use ostd_pod::Pod;
7
8use super::{
9 FallibleVmRead, FallibleVmWrite, Infallible, PodOnce, VmIo, VmIoFill, VmIoOnce, VmReader,
10 VmWriter,
11};
12use crate::{Error, prelude::*};
13
14pub trait HasVmReaderWriter {
20 type Types: VmReaderWriterTypes;
29
30 fn reader(&self) -> <Self::Types as VmReaderWriterTypes>::Reader<'_>;
32 fn writer(&self) -> <Self::Types as VmReaderWriterTypes>::Writer<'_>;
34}
35
36pub trait VmReaderWriterTypes {
38 type Reader<'a>;
40 type Writer<'a>;
42
43 fn to_reader_result(reader: Self::Reader<'_>) -> Result<VmReader<'_, Infallible>>;
45 fn to_writer_result(writer: Self::Writer<'_>) -> Result<VmWriter<'_, Infallible>>;
47}
48
49pub enum VmReaderWriterIdentity {}
51impl VmReaderWriterTypes for VmReaderWriterIdentity {
52 type Reader<'a> = VmReader<'a, Infallible>;
53 type Writer<'a> = VmWriter<'a, Infallible>;
54 fn to_reader_result(reader: Self::Reader<'_>) -> Result<VmReader<'_, Infallible>> {
55 Ok(reader)
56 }
57 fn to_writer_result(writer: Self::Writer<'_>) -> Result<VmWriter<'_, Infallible>> {
58 Ok(writer)
59 }
60}
61
62pub enum VmReaderWriterResult {}
64impl VmReaderWriterTypes for VmReaderWriterResult {
65 type Reader<'a> = Result<VmReader<'a, Infallible>>;
66 type Writer<'a> = Result<VmWriter<'a, Infallible>>;
67 fn to_reader_result(reader: Self::Reader<'_>) -> Result<VmReader<'_, Infallible>> {
68 reader
69 }
70 fn to_writer_result(writer: Self::Writer<'_>) -> Result<VmWriter<'_, Infallible>> {
71 writer
72 }
73}
74
75impl<S: HasVmReaderWriter + Send + Sync> VmIo for S {
76 fn read(&self, offset: usize, writer: &mut VmWriter) -> Result<()> {
77 let mut reader = <Self as HasVmReaderWriter>::Types::to_reader_result(self.reader())?;
78
79 let limit = offset.checked_add(writer.avail()).ok_or(Error::Overflow)?;
80 if limit > reader.remain() {
81 return Err(Error::InvalidArgs);
82 }
83
84 reader.skip(offset);
85 let _len = reader
86 .to_fallible()
87 .read_fallible(writer)
88 .map_err(|(err, _)| err)?;
89 debug_assert!(!writer.has_avail());
90 Ok(())
91 }
92
93 fn read_bytes(&self, offset: usize, buf: &mut [u8]) -> Result<()> {
94 let mut reader = <Self as HasVmReaderWriter>::Types::to_reader_result(self.reader())?;
95
96 let limit = offset.checked_add(buf.len()).ok_or(Error::Overflow)?;
97 if limit > reader.remain() {
98 return Err(Error::InvalidArgs);
99 }
100
101 let len = reader.skip(offset).read(&mut VmWriter::from(&mut *buf));
102 debug_assert_eq!(len, buf.len());
103 Ok(())
104 }
105
106 fn read_val<T: Pod>(&self, offset: usize) -> Result<T> {
110 let mut reader = <Self as HasVmReaderWriter>::Types::to_reader_result(self.reader())?;
111
112 if offset > reader.remain() {
113 return Err(Error::InvalidArgs);
114 }
115
116 reader.skip(offset).read_val()
117 }
118
119 fn write(&self, offset: usize, reader: &mut VmReader) -> Result<()> {
120 let mut writer = <Self as HasVmReaderWriter>::Types::to_writer_result(self.writer())?;
121
122 let limit = offset.checked_add(reader.remain()).ok_or(Error::Overflow)?;
123 if limit > writer.avail() {
124 return Err(Error::InvalidArgs);
125 }
126
127 writer.skip(offset);
128 let _len = writer
129 .to_fallible()
130 .write_fallible(reader)
131 .map_err(|(err, _)| err)?;
132 debug_assert!(!reader.has_remain());
133 Ok(())
134 }
135
136 fn write_bytes(&self, offset: usize, buf: &[u8]) -> Result<()> {
137 let mut writer = <Self as HasVmReaderWriter>::Types::to_writer_result(self.writer())?;
138
139 let limit = offset.checked_add(buf.len()).ok_or(Error::Overflow)?;
140 if limit > writer.avail() {
141 return Err(Error::InvalidArgs);
142 }
143
144 let len = writer.skip(offset).write(&mut VmReader::from(buf));
145 debug_assert_eq!(len, buf.len());
146 Ok(())
147 }
148
149 fn write_val<T: Pod>(&self, offset: usize, new_val: &T) -> Result<()> {
153 let mut writer = <Self as HasVmReaderWriter>::Types::to_writer_result(self.writer())?;
154
155 if offset > writer.avail() {
156 return Err(Error::InvalidArgs);
157 }
158
159 writer.skip(offset).write_val(new_val)
160 }
161}
162
163impl<S: HasVmReaderWriter> VmIoFill for S {
164 fn fill_zeros(&self, offset: usize, len: usize) -> core::result::Result<(), (Error, usize)> {
165 let mut writer = <Self as HasVmReaderWriter>::Types::to_writer_result(self.writer())
166 .map_err(|err| (err, 0))?;
167
168 if offset > writer.avail() {
169 return Err((Error::InvalidArgs, 0));
170 }
171
172 let filled_len = writer.skip(offset).fill_zeros(len);
173 if filled_len == len {
174 Ok(())
175 } else {
176 Err((Error::InvalidArgs, filled_len))
177 }
178 }
179}
180
181impl<S: HasVmReaderWriter> VmIoOnce for S {
182 fn read_once<T: PodOnce>(&self, offset: usize) -> Result<T> {
183 let mut reader = <Self as HasVmReaderWriter>::Types::to_reader_result(self.reader())?;
184 reader.skip(offset).read_once()
185 }
186
187 fn write_once<T: PodOnce>(&self, offset: usize, new_val: &T) -> Result<()> {
188 let mut writer = <Self as HasVmReaderWriter>::Types::to_writer_result(self.writer())?;
189 writer.skip(offset).write_once(new_val)
190 }
191}
192
193macro_rules! impl_vm_io_pointer {
200 ($typ:ty,$from:tt) => {
201 #[inherit_methods(from = $from)]
202 impl<T: HasVmReaderWriter> HasVmReaderWriter for $typ {
203 type Types = T::Types;
204 fn reader(&self) -> <Self::Types as VmReaderWriterTypes>::Reader<'_>;
205 fn writer(&self) -> <Self::Types as VmReaderWriterTypes>::Writer<'_>;
206 }
207 };
208}
209
210impl_vm_io_pointer!(&T, "(**self)");
211impl_vm_io_pointer!(&mut T, "(**self)");
212impl_vm_io_pointer!(Box<T>, "(**self)");
213impl_vm_io_pointer!(Arc<T>, "(**self)");