1use super::{write_into, WriteInto};
2use std::io;
3use std::mem::size_of;
4use std::slice::from_raw_parts;
5
6pub struct Plain<T>(pub T);
50
51impl<T> WriteInto for Plain<&T> {
53 type Output = ();
54
55 fn write_into(self, sink: &mut impl io::Write) -> io::Result<Self::Output> {
56 let bytes = unsafe {
60 let data = self.0 as *const T as *const u8;
61 from_raw_parts(data, size_of::<T>())
62 };
63
64 sink.write_all(&bytes)?;
65 Ok(())
66 }
67}
68
69impl<T> WriteInto for &Plain<&T> {
70 type Output = ();
71
72 fn write_into(self, sink: &mut impl io::Write) -> io::Result<Self::Output> {
73 write_into(sink, Plain(self.0))
74 }
75}
76
77impl<T> WriteInto for Plain<&[T]> {
79 type Output = ();
80
81 fn write_into(self, sink: &mut impl io::Write) -> io::Result<Self::Output> {
82 let bytes = unsafe {
86 let data = self.0 as *const [T] as *const u8;
87 from_raw_parts(data, self.0.len() * size_of::<T>())
88 };
89
90 sink.write_all(&bytes)?;
91 Ok(())
92 }
93}
94
95impl<T> WriteInto for &Plain<&[T]> {
96 type Output = ();
97
98 fn write_into(self, sink: &mut impl io::Write) -> io::Result<Self::Output> {
99 write_into(sink, Plain(self.0))
100 }
101}
102
103impl WriteInto for Plain<&str> {
104 type Output = ();
105
106 fn write_into(self, sink: &mut impl io::Write) -> io::Result<Self::Output> {
107 sink.write_all(self.0.as_bytes())?;
108 Ok(())
109 }
110}
111
112impl WriteInto for &Plain<&str> {
113 type Output = ();
114
115 fn write_into(self, sink: &mut impl io::Write) -> io::Result<Self::Output> {
116 write_into(sink, Plain(self.0))
117 }
118}
119
120macro_rules! impl_write_into {
121 ($($primitive:ty)*) => {
122 $(
123 impl WriteInto for Plain<$primitive> {
124 type Output = ();
125
126 fn write_into(self, sink: &mut impl io::Write) -> io::Result<Self::Output> {
127 write_into(sink, Plain(&self.0))
128 }
129 }
130
131 impl WriteInto for &Plain<$primitive> {
132 type Output = ();
133
134 fn write_into(self, sink: &mut impl io::Write) -> io::Result<Self::Output> {
135 write_into(sink, Plain(&self.0))
136 }
137 }
138 )*
139 };
140}
141
142impl_write_into! {
143 i8 i16 i32 i64 i128 isize
144 u8 u16 u32 u64 u128 usize
145 bool char f32 f64
146}
147
148#[cfg(test)]
149mod tests {
150 use super::super::*;
151 use super::*;
152
153 #[test]
154 fn write_u8() {
155 let mut buffer = Vec::new();
156 write_into(&mut buffer, Plain(&0x7Fu8)).unwrap();
157 assert_eq!(&buffer, &[0x7F]);
158 }
159
160 #[test]
161 fn write_str() {
162 let bytes = "([Ljava/lang/String;)V";
163 let mut buffer = Vec::new();
164 write_into(&mut buffer, Plain(bytes)).unwrap();
165 assert_eq!(&buffer, b"([Ljava/lang/String;)V");
166 }
167
168 #[test]
169 fn write_slice_of_arrays() {
170 let bytes: &[[u8; 2]] = &[[0x01, 0x02], [0x03, 0x04]];
171 let mut buffer = Vec::new();
172 write_into(&mut buffer, Plain(bytes)).unwrap();
173 assert_eq!(&buffer, &[0x01, 0x02, 0x03, 0x04]);
174 }
175}