1 use std::error;
2 use std::fmt;
3 
4 /// An error returned from the [`send`] method.
5 ///
6 /// The message could not be sent because the channel is disconnected.
7 ///
8 /// The error contains the message so it can be recovered.
9 ///
10 /// [`send`]: struct.Sender.html#method.send
11 #[derive(PartialEq, Eq, Clone, Copy)]
12 pub struct SendError<T>(pub T);
13 
14 /// An error returned from the [`try_send`] method.
15 ///
16 /// The error contains the message being sent so it can be recovered.
17 ///
18 /// [`try_send`]: struct.Sender.html#method.try_send
19 #[derive(PartialEq, Eq, Clone, Copy)]
20 pub enum TrySendError<T> {
21     /// The message could not be sent because the channel is full.
22     ///
23     /// If this is a zero-capacity channel, then the error indicates that there was no receiver
24     /// available to receive the message at the time.
25     Full(T),
26 
27     /// The message could not be sent because the channel is disconnected.
28     Disconnected(T),
29 }
30 
31 /// An error returned from the [`send_timeout`] method.
32 ///
33 /// The error contains the message being sent so it can be recovered.
34 ///
35 /// [`send_timeout`]: struct.Sender.html#method.send_timeout
36 #[derive(PartialEq, Eq, Clone, Copy)]
37 pub enum SendTimeoutError<T> {
38     /// The message could not be sent because the channel is full and the operation timed out.
39     ///
40     /// If this is a zero-capacity channel, then the error indicates that there was no receiver
41     /// available to receive the message and the operation timed out.
42     Timeout(T),
43 
44     /// The message could not be sent because the channel is disconnected.
45     Disconnected(T),
46 }
47 
48 /// An error returned from the [`recv`] method.
49 ///
50 /// A message could not be received because the channel is empty and disconnected.
51 ///
52 /// [`recv`]: struct.Receiver.html#method.recv
53 #[derive(PartialEq, Eq, Clone, Copy, Debug)]
54 pub struct RecvError;
55 
56 /// An error returned from the [`try_recv`] method.
57 ///
58 /// [`try_recv`]: struct.Receiver.html#method.recv
59 #[derive(PartialEq, Eq, Clone, Copy, Debug)]
60 pub enum TryRecvError {
61     /// A message could not be received because the channel is empty.
62     ///
63     /// If this is a zero-capacity channel, then the error indicates that there was no sender
64     /// available to send a message at the time.
65     Empty,
66 
67     /// The message could not be received because the channel is empty and disconnected.
68     Disconnected,
69 }
70 
71 /// An error returned from the [`recv_timeout`] method.
72 ///
73 /// [`recv_timeout`]: struct.Receiver.html#method.recv_timeout
74 #[derive(PartialEq, Eq, Clone, Copy, Debug)]
75 pub enum RecvTimeoutError {
76     /// A message could not be received because the channel is empty and the operation timed out.
77     ///
78     /// If this is a zero-capacity channel, then the error indicates that there was no sender
79     /// available to send a message and the operation timed out.
80     Timeout,
81 
82     /// The message could not be received because the channel is empty and disconnected.
83     Disconnected,
84 }
85 
86 /// An error returned from the [`try_select`] method.
87 ///
88 /// Failed because none of the channel operations were ready.
89 ///
90 /// [`try_select`]: struct.Select.html#method.try_select
91 #[derive(PartialEq, Eq, Clone, Copy, Debug)]
92 pub struct TrySelectError;
93 
94 /// An error returned from the [`select_timeout`] method.
95 ///
96 /// Failed because none of the channel operations became ready before the timeout.
97 ///
98 /// [`select_timeout`]: struct.Select.html#method.select_timeout
99 #[derive(PartialEq, Eq, Clone, Copy, Debug)]
100 pub struct SelectTimeoutError;
101 
102 /// An error returned from the [`try_ready`] method.
103 ///
104 /// Failed because none of the channel operations were ready.
105 ///
106 /// [`try_ready`]: struct.Select.html#method.try_ready
107 #[derive(PartialEq, Eq, Clone, Copy, Debug)]
108 pub struct TryReadyError;
109 
110 /// An error returned from the [`ready_timeout`] method.
111 ///
112 /// Failed because none of the channel operations became ready before the timeout.
113 ///
114 /// [`ready_timeout`]: struct.Select.html#method.ready_timeout
115 #[derive(PartialEq, Eq, Clone, Copy, Debug)]
116 pub struct ReadyTimeoutError;
117 
118 impl<T> fmt::Debug for SendError<T> {
fmt(&self, f: &mut fmt::Formatter) -> fmt::Result119     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
120         "SendError(..)".fmt(f)
121     }
122 }
123 
124 impl<T> fmt::Display for SendError<T> {
fmt(&self, f: &mut fmt::Formatter) -> fmt::Result125     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
126         "sending on a disconnected channel".fmt(f)
127     }
128 }
129 
130 impl<T: Send> error::Error for SendError<T> {
description(&self) -> &str131     fn description(&self) -> &str {
132         "sending on a disconnected channel"
133     }
134 
cause(&self) -> Option<&error::Error>135     fn cause(&self) -> Option<&error::Error> {
136         None
137     }
138 }
139 
140 impl<T> SendError<T> {
141     /// Unwraps the message.
142     ///
143     /// # Examples
144     ///
145     /// ```
146     /// use crossbeam_channel::unbounded;
147     ///
148     /// let (s, r) = unbounded();
149     /// drop(r);
150     ///
151     /// if let Err(err) = s.send("foo") {
152     ///     assert_eq!(err.into_inner(), "foo");
153     /// }
154     /// ```
into_inner(self) -> T155     pub fn into_inner(self) -> T {
156         self.0
157     }
158 }
159 
160 impl<T> fmt::Debug for TrySendError<T> {
fmt(&self, f: &mut fmt::Formatter) -> fmt::Result161     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
162         match *self {
163             TrySendError::Full(..) => "Full(..)".fmt(f),
164             TrySendError::Disconnected(..) => "Disconnected(..)".fmt(f),
165         }
166     }
167 }
168 
169 impl<T> fmt::Display for TrySendError<T> {
fmt(&self, f: &mut fmt::Formatter) -> fmt::Result170     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
171         match *self {
172             TrySendError::Full(..) => "sending on a full channel".fmt(f),
173             TrySendError::Disconnected(..) => "sending on a disconnected channel".fmt(f),
174         }
175     }
176 }
177 
178 impl<T: Send> error::Error for TrySendError<T> {
description(&self) -> &str179     fn description(&self) -> &str {
180         match *self {
181             TrySendError::Full(..) => "sending on a full channel",
182             TrySendError::Disconnected(..) => "sending on a disconnected channel",
183         }
184     }
185 
cause(&self) -> Option<&error::Error>186     fn cause(&self) -> Option<&error::Error> {
187         None
188     }
189 }
190 
191 impl<T> From<SendError<T>> for TrySendError<T> {
from(err: SendError<T>) -> TrySendError<T>192     fn from(err: SendError<T>) -> TrySendError<T> {
193         match err {
194             SendError(t) => TrySendError::Disconnected(t),
195         }
196     }
197 }
198 
199 impl<T> TrySendError<T> {
200     /// Unwraps the message.
201     ///
202     /// # Examples
203     ///
204     /// ```
205     /// use crossbeam_channel::bounded;
206     ///
207     /// let (s, r) = bounded(0);
208     ///
209     /// if let Err(err) = s.try_send("foo") {
210     ///     assert_eq!(err.into_inner(), "foo");
211     /// }
212     /// ```
into_inner(self) -> T213     pub fn into_inner(self) -> T {
214         match self {
215             TrySendError::Full(v) => v,
216             TrySendError::Disconnected(v) => v,
217         }
218     }
219 
220     /// Returns `true` if the send operation failed because the channel is full.
is_full(&self) -> bool221     pub fn is_full(&self) -> bool {
222         match self {
223             TrySendError::Full(_) => true,
224             _ => false,
225         }
226     }
227 
228     /// Returns `true` if the send operation failed because the channel is disconnected.
is_disconnected(&self) -> bool229     pub fn is_disconnected(&self) -> bool {
230         match self {
231             TrySendError::Disconnected(_) => true,
232             _ => false,
233         }
234     }
235 }
236 
237 impl<T> fmt::Debug for SendTimeoutError<T> {
fmt(&self, f: &mut fmt::Formatter) -> fmt::Result238     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
239         "SendTimeoutError(..)".fmt(f)
240     }
241 }
242 
243 impl<T> fmt::Display for SendTimeoutError<T> {
fmt(&self, f: &mut fmt::Formatter) -> fmt::Result244     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
245         match *self {
246             SendTimeoutError::Timeout(..) => "timed out waiting on send operation".fmt(f),
247             SendTimeoutError::Disconnected(..) => "sending on a disconnected channel".fmt(f),
248         }
249     }
250 }
251 
252 impl<T: Send> error::Error for SendTimeoutError<T> {
description(&self) -> &str253     fn description(&self) -> &str {
254         "sending on an empty and disconnected channel"
255     }
256 
cause(&self) -> Option<&error::Error>257     fn cause(&self) -> Option<&error::Error> {
258         None
259     }
260 }
261 
262 impl<T> From<SendError<T>> for SendTimeoutError<T> {
from(err: SendError<T>) -> SendTimeoutError<T>263     fn from(err: SendError<T>) -> SendTimeoutError<T> {
264         match err {
265             SendError(e) => SendTimeoutError::Disconnected(e),
266         }
267     }
268 }
269 
270 impl<T> SendTimeoutError<T> {
271     /// Unwraps the message.
272     ///
273     /// # Examples
274     ///
275     /// ```
276     /// use std::time::Duration;
277     /// use crossbeam_channel::unbounded;
278     ///
279     /// let (s, r) = unbounded();
280     ///
281     /// if let Err(err) = s.send_timeout("foo", Duration::from_secs(1)) {
282     ///     assert_eq!(err.into_inner(), "foo");
283     /// }
284     /// ```
into_inner(self) -> T285     pub fn into_inner(self) -> T {
286         match self {
287             SendTimeoutError::Timeout(v) => v,
288             SendTimeoutError::Disconnected(v) => v,
289         }
290     }
291 
292     /// Returns `true` if the send operation timed out.
is_timeout(&self) -> bool293     pub fn is_timeout(&self) -> bool {
294         match self {
295             SendTimeoutError::Timeout(_) => true,
296             _ => false,
297         }
298     }
299 
300     /// Returns `true` if the send operation failed because the channel is disconnected.
is_disconnected(&self) -> bool301     pub fn is_disconnected(&self) -> bool {
302         match self {
303             SendTimeoutError::Disconnected(_) => true,
304             _ => false,
305         }
306     }
307 }
308 
309 impl fmt::Display for RecvError {
fmt(&self, f: &mut fmt::Formatter) -> fmt::Result310     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
311         "receiving on an empty and disconnected channel".fmt(f)
312     }
313 }
314 
315 impl error::Error for RecvError {
description(&self) -> &str316     fn description(&self) -> &str {
317         "receiving on an empty and disconnected channel"
318     }
319 
cause(&self) -> Option<&error::Error>320     fn cause(&self) -> Option<&error::Error> {
321         None
322     }
323 }
324 
325 impl fmt::Display for TryRecvError {
fmt(&self, f: &mut fmt::Formatter) -> fmt::Result326     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
327         match *self {
328             TryRecvError::Empty => "receiving on an empty channel".fmt(f),
329             TryRecvError::Disconnected => "receiving on an empty and disconnected channel".fmt(f),
330         }
331     }
332 }
333 
334 impl error::Error for TryRecvError {
description(&self) -> &str335     fn description(&self) -> &str {
336         match *self {
337             TryRecvError::Empty => "receiving on an empty channel",
338             TryRecvError::Disconnected => "receiving on an empty and disconnected channel",
339         }
340     }
341 
cause(&self) -> Option<&error::Error>342     fn cause(&self) -> Option<&error::Error> {
343         None
344     }
345 }
346 
347 impl From<RecvError> for TryRecvError {
from(err: RecvError) -> TryRecvError348     fn from(err: RecvError) -> TryRecvError {
349         match err {
350             RecvError => TryRecvError::Disconnected,
351         }
352     }
353 }
354 
355 impl TryRecvError {
356     /// Returns `true` if the receive operation failed because the channel is empty.
is_empty(&self) -> bool357     pub fn is_empty(&self) -> bool {
358         match self {
359             TryRecvError::Empty => true,
360             _ => false,
361         }
362     }
363 
364     /// Returns `true` if the receive operation failed because the channel is disconnected.
is_disconnected(&self) -> bool365     pub fn is_disconnected(&self) -> bool {
366         match self {
367             TryRecvError::Disconnected => true,
368             _ => false,
369         }
370     }
371 }
372 
373 impl fmt::Display for RecvTimeoutError {
fmt(&self, f: &mut fmt::Formatter) -> fmt::Result374     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
375         match *self {
376             RecvTimeoutError::Timeout => "timed out waiting on receive operation".fmt(f),
377             RecvTimeoutError::Disconnected => "channel is empty and disconnected".fmt(f),
378         }
379     }
380 }
381 
382 impl error::Error for RecvTimeoutError {
description(&self) -> &str383     fn description(&self) -> &str {
384         match *self {
385             RecvTimeoutError::Timeout => "timed out waiting on receive operation",
386             RecvTimeoutError::Disconnected => "channel is empty and disconnected",
387         }
388     }
389 
cause(&self) -> Option<&error::Error>390     fn cause(&self) -> Option<&error::Error> {
391         None
392     }
393 }
394 
395 impl From<RecvError> for RecvTimeoutError {
from(err: RecvError) -> RecvTimeoutError396     fn from(err: RecvError) -> RecvTimeoutError {
397         match err {
398             RecvError => RecvTimeoutError::Disconnected,
399         }
400     }
401 }
402 
403 impl RecvTimeoutError {
404     /// Returns `true` if the receive operation timed out.
is_timeout(&self) -> bool405     pub fn is_timeout(&self) -> bool {
406         match self {
407             RecvTimeoutError::Timeout => true,
408             _ => false,
409         }
410     }
411 
412     /// Returns `true` if the receive operation failed because the channel is disconnected.
is_disconnected(&self) -> bool413     pub fn is_disconnected(&self) -> bool {
414         match self {
415             RecvTimeoutError::Disconnected => true,
416             _ => false,
417         }
418     }
419 }
420 
421 impl fmt::Display for TrySelectError {
fmt(&self, f: &mut fmt::Formatter) -> fmt::Result422     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
423         "all operations in select would block".fmt(f)
424     }
425 }
426 
427 impl error::Error for TrySelectError {
description(&self) -> &str428     fn description(&self) -> &str {
429         "all operations in select would block"
430     }
431 
cause(&self) -> Option<&error::Error>432     fn cause(&self) -> Option<&error::Error> {
433         None
434     }
435 }
436 
437 impl fmt::Display for SelectTimeoutError {
fmt(&self, f: &mut fmt::Formatter) -> fmt::Result438     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
439         "timed out waiting on select".fmt(f)
440     }
441 }
442 
443 impl error::Error for SelectTimeoutError {
description(&self) -> &str444     fn description(&self) -> &str {
445         "timed out waiting on select"
446     }
447 
cause(&self) -> Option<&error::Error>448     fn cause(&self) -> Option<&error::Error> {
449         None
450     }
451 }
452