tokio_core/io/mod.rs
1//! I/O conveniences when working with primitives in `tokio-core`
2//!
3//! Contains various combinators to work with I/O objects and type definitions
4//! as well.
5//!
6//! A description of the high-level I/O combinators can be [found online] in
7//! addition to a description of the [low level details].
8//!
9//! [found online]: https://tokio.rs/docs/getting-started/core/
10//! [low level details]: https://tokio.rs/docs/going-deeper-tokio/core-low-level/
11
12#![deprecated(note = "moved to the `tokio-io` crate")]
13#![allow(deprecated)]
14
15use std::io;
16
17use futures::{Async, Poll};
18use futures::future::BoxFuture;
19use futures::stream::BoxStream;
20use iovec::IoVec;
21
22/// A convenience typedef around a `Future` whose error component is `io::Error`
23pub type IoFuture<T> = BoxFuture<T, io::Error>;
24
25/// A convenience typedef around a `Stream` whose error component is `io::Error`
26pub type IoStream<T> = BoxStream<T, io::Error>;
27
28/// A convenience macro for working with `io::Result<T>` from the `Read` and
29/// `Write` traits.
30///
31/// This macro takes `io::Result<T>` as input, and returns `T` as the output. If
32/// the input type is of the `Err` variant, then `Poll::NotReady` is returned if
33/// it indicates `WouldBlock` or otherwise `Err` is returned.
34#[macro_export]
35macro_rules! try_nb {
36 ($e:expr) => (match $e {
37 Ok(t) => t,
38 Err(ref e) if e.kind() == ::std::io::ErrorKind::WouldBlock => {
39 return Ok(::futures::Async::NotReady)
40 }
41 Err(e) => return Err(e.into()),
42 })
43}
44
45mod copy;
46mod frame;
47mod flush;
48mod read_exact;
49mod read_to_end;
50mod read;
51mod read_until;
52mod split;
53mod window;
54mod write_all;
55pub use self::copy::{copy, Copy};
56pub use self::frame::{EasyBuf, EasyBufMut, Framed, Codec};
57pub use self::flush::{flush, Flush};
58pub use self::read_exact::{read_exact, ReadExact};
59pub use self::read_to_end::{read_to_end, ReadToEnd};
60pub use self::read::{read, Read};
61pub use self::read_until::{read_until, ReadUntil};
62pub use self::split::{ReadHalf, WriteHalf};
63pub use self::window::Window;
64pub use self::write_all::{write_all, WriteAll};
65
66/// A trait for read/write I/O objects
67///
68/// This trait represents I/O objects which are readable and writable.
69/// Additionally, they're associated with the ability to test whether they're
70/// readable or writable.
71///
72/// Importantly, the methods of this trait are intended to be used in conjunction
73/// with the current task of a future. Namely whenever any of them return a
74/// value that indicates "would block" the current future's task is arranged to
75/// receive a notification when the method would otherwise not indicate that it
76/// would block.
77pub trait Io: io::Read + io::Write {
78 /// Tests to see if this I/O object may be readable.
79 ///
80 /// This method returns an `Async<()>` indicating whether the object
81 /// **might** be readable. It is possible that even if this method returns
82 /// `Async::Ready` that a call to `read` would return a `WouldBlock` error.
83 ///
84 /// There is a default implementation for this function which always
85 /// indicates that an I/O object is readable, but objects which can
86 /// implement a finer grained version of this are recommended to do so.
87 ///
88 /// If this function returns `Async::NotReady` then the current future's
89 /// task is arranged to receive a notification when it might not return
90 /// `NotReady`.
91 ///
92 /// # Panics
93 ///
94 /// This method is likely to panic if called from outside the context of a
95 /// future's task.
96 fn poll_read(&mut self) -> Async<()> {
97 Async::Ready(())
98 }
99
100 /// Tests to see if this I/O object may be writable.
101 ///
102 /// This method returns an `Async<()>` indicating whether the object
103 /// **might** be writable. It is possible that even if this method returns
104 /// `Async::Ready` that a call to `write` would return a `WouldBlock` error.
105 ///
106 /// There is a default implementation for this function which always
107 /// indicates that an I/O object is writable, but objects which can
108 /// implement a finer grained version of this are recommended to do so.
109 ///
110 /// If this function returns `Async::NotReady` then the current future's
111 /// task is arranged to receive a notification when it might not return
112 /// `NotReady`.
113 ///
114 /// # Panics
115 ///
116 /// This method is likely to panic if called from outside the context of a
117 /// future's task.
118 fn poll_write(&mut self) -> Async<()> {
119 Async::Ready(())
120 }
121
122 /// Read in a list of buffers all at once.
123 ///
124 /// This operation will attempt to read bytes from this socket and place
125 /// them into the list of buffers provided. Note that each buffer is an
126 /// `IoVec` which can be created from a byte slice.
127 ///
128 /// The buffers provided will be filled in sequentially. A buffer will be
129 /// entirely filled up before the next is written to.
130 ///
131 /// The number of bytes read is returned, if successful, or an error is
132 /// returned otherwise. If no bytes are available to be read yet then
133 /// a "would block" error is returned. This operation should not block.
134 ///
135 /// There is a default implementation for this function which treats this
136 /// as a single read using the first buffer in the list, but objects which
137 /// can implement this as an atomic read using all the buffers are
138 /// recommended to do so. For example, `TcpStream` can implement this
139 /// using the `readv` syscall.
140 fn read_vec(&mut self, bufs: &mut [&mut IoVec]) -> io::Result<usize> {
141 if bufs.is_empty() {
142 Ok(0)
143 } else {
144 self.read(&mut bufs[0])
145 }
146 }
147
148 /// Write a list of buffers all at once.
149 ///
150 /// This operation will attempt to write a list of byte buffers to this
151 /// socket. Note that each buffer is an `IoVec` which can be created from a
152 /// byte slice.
153 ///
154 /// The buffers provided will be written sequentially. A buffer will be
155 /// entirely written before the next is written.
156 ///
157 /// The number of bytes written is returned, if successful, or an error is
158 /// returned otherwise. If the socket is not currently writable then a
159 /// "would block" error is returned. This operation should not block.
160 ///
161 /// There is a default implementation for this function which writes the
162 /// first buffer only, but objects which can implement this as an atomic
163 /// write using all the buffers are recommended to do so. For example,
164 /// `TcpStream` can implement this using the `writev` syscall.
165 fn write_vec(&mut self, bufs: &[&IoVec]) -> io::Result<usize> {
166 if bufs.is_empty() {
167 Ok(0)
168 } else {
169 self.write(&bufs[0])
170 }
171 }
172
173 /// Provides a `Stream` and `Sink` interface for reading and writing to this
174 /// `Io` object, using `Decode` and `Encode` to read and write the raw data.
175 ///
176 /// Raw I/O objects work with byte sequences, but higher-level code usually
177 /// wants to batch these into meaningful chunks, called "frames". This
178 /// method layers framing on top of an I/O object, by using the `Codec`
179 /// traits to handle encoding and decoding of messages frames. Note that
180 /// the incoming and outgoing frame types may be distinct.
181 ///
182 /// This function returns a *single* object that is both `Stream` and
183 /// `Sink`; grouping this into a single object is often useful for layering
184 /// things like gzip or TLS, which require both read and write access to the
185 /// underlying object.
186 ///
187 /// If you want to work more directly with the streams and sink, consider
188 /// calling `split` on the `Framed` returned by this method, which will
189 /// break them into separate objects, allowing them to interact more easily.
190 fn framed<C: Codec>(self, codec: C) -> Framed<Self, C>
191 where Self: Sized,
192 {
193 frame::framed(self, codec)
194 }
195
196 /// Helper method for splitting this read/write object into two halves.
197 ///
198 /// The two halves returned implement the `Read` and `Write` traits,
199 /// respectively.
200 fn split(self) -> (ReadHalf<Self>, WriteHalf<Self>)
201 where Self: Sized
202 {
203 split::split(self)
204 }
205}
206
207/// A trait for framed reading and writing.
208///
209/// Most implementations of `FramedIo` are for doing protocol level
210/// serialization and deserialization.
211///
212/// Importantly, the methods of this trait are intended to be used in conjunction
213/// with the current task of a future. Namely whenever any of them return a
214/// value that indicates "would block" the current future's task is arranged to
215/// receive a notification when the method would otherwise not indicate that it
216/// would block.
217//
218/// For a sample implementation of `FramedIo` you can take a look at the
219/// `Framed` type in the `frame` module of this crate.
220#[doc(hidden)]
221#[deprecated(since = "0.1.1", note = "replaced by Sink + Stream")]
222pub trait FramedIo {
223 /// Messages written
224 type In;
225
226 /// Messages read
227 type Out;
228
229 /// Tests to see if this `FramedIo` may be readable.
230 fn poll_read(&mut self) -> Async<()>;
231
232 /// Read a message frame from the `FramedIo`
233 fn read(&mut self) -> Poll<Self::Out, io::Error>;
234
235 /// Tests to see if this `FramedIo` may be writable.
236 ///
237 /// Unlike most other calls to poll readiness, it is important that when
238 /// `FramedIo::poll_write` returns `Async::Ready` that a write will
239 /// succeed.
240 fn poll_write(&mut self) -> Async<()>;
241
242 /// Write a message frame to the `FramedIo`
243 fn write(&mut self, req: Self::In) -> Poll<(), io::Error>;
244
245 /// Flush pending writes or do any other work not driven by reading /
246 /// writing.
247 ///
248 /// Since the backing source is non-blocking, there is no guarantee that a
249 /// call to `FramedIo::write` is able to write the full message to the
250 /// backing source immediately. In this case, the `FramedIo` will need to
251 /// buffer the remaining data to write. Calls to `FramedIo:flush` attempt
252 /// to write any remaining data in the write buffer to the underlying
253 /// source.
254 fn flush(&mut self) -> Poll<(), io::Error>;
255}