1#[cfg(feature = "allocator_api")]
2use std::alloc::Allocator;
3
4use compio_buf::{BufResult, IoBuf, IoBufMut, IoVectoredBuf, IoVectoredBufMut, t_alloc};
5use futures_util::Stream;
6use rustix::net::ReturnFlags;
7
8use crate::{AsyncReadManaged, IoResult};
9
10pub trait AsyncReadAncillary {
14 async fn read_with_ancillary<T: IoBufMut, C: IoBufMut>(
17 &mut self,
18 buffer: T,
19 control: C,
20 ) -> BufResult<(usize, usize, ReturnFlags), (T, C)>;
21
22 async fn read_vectored_with_ancillary<T: IoVectoredBufMut, C: IoBufMut>(
25 &mut self,
26 buffer: T,
27 control: C,
28 ) -> BufResult<(usize, usize, ReturnFlags), (T, C)>;
29}
30
31impl<A: AsyncReadAncillary + ?Sized> AsyncReadAncillary for &mut A {
32 #[inline]
33 async fn read_with_ancillary<T: IoBufMut, C: IoBufMut>(
34 &mut self,
35 buffer: T,
36 control: C,
37 ) -> BufResult<(usize, usize, ReturnFlags), (T, C)> {
38 (**self).read_with_ancillary(buffer, control).await
39 }
40
41 #[inline]
42 async fn read_vectored_with_ancillary<T: IoVectoredBufMut, C: IoBufMut>(
43 &mut self,
44 buffer: T,
45 control: C,
46 ) -> BufResult<(usize, usize, ReturnFlags), (T, C)> {
47 (**self).read_vectored_with_ancillary(buffer, control).await
48 }
49}
50
51impl<A: AsyncReadAncillary + ?Sized, #[cfg(feature = "allocator_api")] Alloc: Allocator>
52 AsyncReadAncillary for t_alloc!(Box, A, Alloc)
53{
54 #[inline]
55 async fn read_with_ancillary<T: IoBufMut, C: IoBufMut>(
56 &mut self,
57 buffer: T,
58 control: C,
59 ) -> BufResult<(usize, usize, ReturnFlags), (T, C)> {
60 (**self).read_with_ancillary(buffer, control).await
61 }
62
63 #[inline]
64 async fn read_vectored_with_ancillary<T: IoVectoredBufMut, C: IoBufMut>(
65 &mut self,
66 buffer: T,
67 control: C,
68 ) -> BufResult<(usize, usize, ReturnFlags), (T, C)> {
69 (**self).read_vectored_with_ancillary(buffer, control).await
70 }
71}
72
73pub trait AsyncWriteAncillary {
77 async fn write_with_ancillary<T: IoBuf, C: IoBuf>(
79 &mut self,
80 buffer: T,
81 control: C,
82 ) -> BufResult<usize, (T, C)>;
83
84 async fn write_vectored_with_ancillary<T: IoVectoredBuf, C: IoBuf>(
86 &mut self,
87 buffer: T,
88 control: C,
89 ) -> BufResult<usize, (T, C)>;
90}
91
92impl<A: AsyncWriteAncillary + ?Sized> AsyncWriteAncillary for &mut A {
93 #[inline]
94 async fn write_with_ancillary<T: IoBuf, C: IoBuf>(
95 &mut self,
96 buffer: T,
97 control: C,
98 ) -> BufResult<usize, (T, C)> {
99 (**self).write_with_ancillary(buffer, control).await
100 }
101
102 #[inline]
103 async fn write_vectored_with_ancillary<T: IoVectoredBuf, C: IoBuf>(
104 &mut self,
105 buffer: T,
106 control: C,
107 ) -> BufResult<usize, (T, C)> {
108 (**self)
109 .write_vectored_with_ancillary(buffer, control)
110 .await
111 }
112}
113
114impl<A: AsyncWriteAncillary + ?Sized, #[cfg(feature = "allocator_api")] Alloc: Allocator>
115 AsyncWriteAncillary for t_alloc!(Box, A, Alloc)
116{
117 #[inline]
118 async fn write_with_ancillary<T: IoBuf, C: IoBuf>(
119 &mut self,
120 buffer: T,
121 control: C,
122 ) -> BufResult<usize, (T, C)> {
123 (**self).write_with_ancillary(buffer, control).await
124 }
125
126 #[inline]
127 async fn write_vectored_with_ancillary<T: IoVectoredBuf, C: IoBuf>(
128 &mut self,
129 buffer: T,
130 control: C,
131 ) -> BufResult<usize, (T, C)> {
132 (**self)
133 .write_vectored_with_ancillary(buffer, control)
134 .await
135 }
136}
137
138pub trait AsyncWriteAncillaryZerocopy {
142 type BufferReadyFuture<T: IoBuf, C: IoBuf>: Future<Output = (T, C)>;
144 type VectoredBufferReadyFuture<T: IoVectoredBuf, C: IoBuf>: Future<Output = (T, C)>;
147
148 fn write_zerocopy_with_ancillary<T: IoBuf, C: IoBuf>(
153 &mut self,
154 buf: T,
155 control: C,
156 ) -> impl Future<Output = BufResult<usize, Self::BufferReadyFuture<T, C>>>;
157
158 fn write_zerocopy_vectored_with_ancillary<T: IoVectoredBuf, C: IoBuf>(
161 &mut self,
162 buf: T,
163 control: C,
164 ) -> impl Future<Output = BufResult<usize, Self::VectoredBufferReadyFuture<T, C>>>;
165}
166
167impl<A: AsyncWriteAncillaryZerocopy + ?Sized> AsyncWriteAncillaryZerocopy for &mut A {
168 type BufferReadyFuture<T: IoBuf, C: IoBuf> = A::BufferReadyFuture<T, C>;
169 type VectoredBufferReadyFuture<T: IoVectoredBuf, C: IoBuf> = A::VectoredBufferReadyFuture<T, C>;
170
171 #[inline]
172 fn write_zerocopy_with_ancillary<T: IoBuf, C: IoBuf>(
173 &mut self,
174 buf: T,
175 control: C,
176 ) -> impl Future<Output = BufResult<usize, Self::BufferReadyFuture<T, C>>> {
177 (**self).write_zerocopy_with_ancillary(buf, control)
178 }
179
180 #[inline]
181 fn write_zerocopy_vectored_with_ancillary<T: IoVectoredBuf, C: IoBuf>(
182 &mut self,
183 buf: T,
184 control: C,
185 ) -> impl Future<Output = BufResult<usize, Self::VectoredBufferReadyFuture<T, C>>> {
186 (**self).write_zerocopy_vectored_with_ancillary(buf, control)
187 }
188}
189
190impl<A: AsyncWriteAncillaryZerocopy + ?Sized, #[cfg(feature = "allocator_api")] Alloc: Allocator>
191 AsyncWriteAncillaryZerocopy for t_alloc!(Box, A, Alloc)
192{
193 type BufferReadyFuture<T: IoBuf, C: IoBuf> = A::BufferReadyFuture<T, C>;
194 type VectoredBufferReadyFuture<T: IoVectoredBuf, C: IoBuf> = A::VectoredBufferReadyFuture<T, C>;
195
196 fn write_zerocopy_with_ancillary<T: IoBuf, C: IoBuf>(
197 &mut self,
198 buf: T,
199 control: C,
200 ) -> impl Future<Output = BufResult<usize, Self::BufferReadyFuture<T, C>>> {
201 (**self).write_zerocopy_with_ancillary(buf, control)
202 }
203
204 fn write_zerocopy_vectored_with_ancillary<T: IoVectoredBuf, C: IoBuf>(
205 &mut self,
206 buf: T,
207 control: C,
208 ) -> impl Future<Output = BufResult<usize, Self::VectoredBufferReadyFuture<T, C>>> {
209 (**self).write_zerocopy_vectored_with_ancillary(buf, control)
210 }
211}
212
213pub trait AsyncReadAncillaryManaged: AsyncReadManaged {
217 async fn read_managed_with_ancillary<C: IoBufMut>(
225 &mut self,
226 len: usize,
227 control: C,
228 ) -> IoResult<Option<(Self::Buffer, C, ReturnFlags)>>;
229}
230
231pub trait AsyncReadAncillaryMulti {
235 type Return;
237
238 fn read_multi_with_ancillary(
240 &mut self,
241 control_len: usize,
242 ) -> impl Stream<Item = IoResult<Self::Return>>;
243}