1#[cfg(any(
2 target_os = "android",
3 target_os = "linux",
4 target_os = "dragonfly",
5 target_os = "freebsd",
6 target_os = "ios",
7 target_os = "tvos",
8 target_os = "macos",
9 target_os = "watchos",
10 target_os = "visionos",
11 target_os = "netbsd",
12 target_os = "openbsd",
13 target_os = "nto"
14))]
15use super::{peer_cred, UCred};
16#[cfg(any(doc, target_os = "android", target_os = "linux"))]
17use super::{recv_vectored_with_ancillary_from, send_vectored_with_ancillary_to, SocketAncillary};
18use super::{sockaddr_un, SocketAddr};
19use crate::fmt;
20use crate::io::{self, IoSlice, IoSliceMut};
21use crate::net::Shutdown;
22use crate::os::unix::io::{AsFd, AsRawFd, BorrowedFd, FromRawFd, IntoRawFd, OwnedFd, RawFd};
23use crate::path::Path;
24use crate::sealed::Sealed;
25use crate::sys::cvt;
26use crate::sys::net::Socket;
27use crate::sys_common::{AsInner, FromInner};
28use crate::time::Duration;
29
30/// A Unix stream socket.
31///
32/// # Examples
33///
34/// ```no_run
35/// use std::os::unix::net::UnixStream;
36/// use std::io::prelude::*;
37///
38/// fn main() -> std::io::Result<()> {
39/// let mut stream = UnixStream::connect("/path/to/my/socket")?;
40/// stream.write_all(b"hello world")?;
41/// let mut response = String::new();
42/// stream.read_to_string(&mut response)?;
43/// println!("{response}");
44/// Ok(())
45/// }
46/// ```
47#[stable(feature = "unix_socket", since = "1.10.0")]
48pub struct UnixStream(pub(super) Socket);
49
50/// Allows extension traits within `std`.
51#[unstable(feature = "sealed", issue = "none")]
52impl Sealed for UnixStream {}
53
54#[stable(feature = "unix_socket", since = "1.10.0")]
55impl fmt::Debug for UnixStream {
56 fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
57 let mut builder: DebugStruct<'_, '_> = fmt.debug_struct(name:"UnixStream");
58 builder.field(name:"fd", self.0.as_inner());
59 if let Ok(addr: SocketAddr) = self.local_addr() {
60 builder.field(name:"local", &addr);
61 }
62 if let Ok(addr: SocketAddr) = self.peer_addr() {
63 builder.field(name:"peer", &addr);
64 }
65 builder.finish()
66 }
67}
68
69impl UnixStream {
70 /// Connects to the socket named by `path`.
71 ///
72 /// # Examples
73 ///
74 /// ```no_run
75 /// use std::os::unix::net::UnixStream;
76 ///
77 /// let socket = match UnixStream::connect("/tmp/sock") {
78 /// Ok(sock) => sock,
79 /// Err(e) => {
80 /// println!("Couldn't connect: {e:?}");
81 /// return
82 /// }
83 /// };
84 /// ```
85 #[stable(feature = "unix_socket", since = "1.10.0")]
86 pub fn connect<P: AsRef<Path>>(path: P) -> io::Result<UnixStream> {
87 unsafe {
88 let inner = Socket::new_raw(libc::AF_UNIX, libc::SOCK_STREAM)?;
89 let (addr, len) = sockaddr_un(path.as_ref())?;
90
91 cvt(libc::connect(inner.as_raw_fd(), core::ptr::addr_of!(addr) as *const _, len))?;
92 Ok(UnixStream(inner))
93 }
94 }
95
96 /// Connects to the socket specified by [`address`].
97 ///
98 /// [`address`]: crate::os::unix::net::SocketAddr
99 ///
100 /// # Examples
101 ///
102 /// ```no_run
103 /// use std::os::unix::net::{UnixListener, UnixStream};
104 ///
105 /// fn main() -> std::io::Result<()> {
106 /// let listener = UnixListener::bind("/path/to/the/socket")?;
107 /// let addr = listener.local_addr()?;
108 ///
109 /// let sock = match UnixStream::connect_addr(&addr) {
110 /// Ok(sock) => sock,
111 /// Err(e) => {
112 /// println!("Couldn't connect: {e:?}");
113 /// return Err(e)
114 /// }
115 /// };
116 /// Ok(())
117 /// }
118 /// ````
119 #[stable(feature = "unix_socket_abstract", since = "1.70.0")]
120 pub fn connect_addr(socket_addr: &SocketAddr) -> io::Result<UnixStream> {
121 unsafe {
122 let inner = Socket::new_raw(libc::AF_UNIX, libc::SOCK_STREAM)?;
123 cvt(libc::connect(
124 inner.as_raw_fd(),
125 core::ptr::addr_of!(socket_addr.addr) as *const _,
126 socket_addr.len,
127 ))?;
128 Ok(UnixStream(inner))
129 }
130 }
131
132 /// Creates an unnamed pair of connected sockets.
133 ///
134 /// Returns two `UnixStream`s which are connected to each other.
135 ///
136 /// # Examples
137 ///
138 /// ```no_run
139 /// use std::os::unix::net::UnixStream;
140 ///
141 /// let (sock1, sock2) = match UnixStream::pair() {
142 /// Ok((sock1, sock2)) => (sock1, sock2),
143 /// Err(e) => {
144 /// println!("Couldn't create a pair of sockets: {e:?}");
145 /// return
146 /// }
147 /// };
148 /// ```
149 #[stable(feature = "unix_socket", since = "1.10.0")]
150 pub fn pair() -> io::Result<(UnixStream, UnixStream)> {
151 let (i1, i2) = Socket::new_pair(libc::AF_UNIX, libc::SOCK_STREAM)?;
152 Ok((UnixStream(i1), UnixStream(i2)))
153 }
154
155 /// Creates a new independently owned handle to the underlying socket.
156 ///
157 /// The returned `UnixStream` is a reference to the same stream that this
158 /// object references. Both handles will read and write the same stream of
159 /// data, and options set on one stream will be propagated to the other
160 /// stream.
161 ///
162 /// # Examples
163 ///
164 /// ```no_run
165 /// use std::os::unix::net::UnixStream;
166 ///
167 /// fn main() -> std::io::Result<()> {
168 /// let socket = UnixStream::connect("/tmp/sock")?;
169 /// let sock_copy = socket.try_clone().expect("Couldn't clone socket");
170 /// Ok(())
171 /// }
172 /// ```
173 #[stable(feature = "unix_socket", since = "1.10.0")]
174 pub fn try_clone(&self) -> io::Result<UnixStream> {
175 self.0.duplicate().map(UnixStream)
176 }
177
178 /// Returns the socket address of the local half of this connection.
179 ///
180 /// # Examples
181 ///
182 /// ```no_run
183 /// use std::os::unix::net::UnixStream;
184 ///
185 /// fn main() -> std::io::Result<()> {
186 /// let socket = UnixStream::connect("/tmp/sock")?;
187 /// let addr = socket.local_addr().expect("Couldn't get local address");
188 /// Ok(())
189 /// }
190 /// ```
191 #[stable(feature = "unix_socket", since = "1.10.0")]
192 pub fn local_addr(&self) -> io::Result<SocketAddr> {
193 SocketAddr::new(|addr, len| unsafe { libc::getsockname(self.as_raw_fd(), addr, len) })
194 }
195
196 /// Returns the socket address of the remote half of this connection.
197 ///
198 /// # Examples
199 ///
200 /// ```no_run
201 /// use std::os::unix::net::UnixStream;
202 ///
203 /// fn main() -> std::io::Result<()> {
204 /// let socket = UnixStream::connect("/tmp/sock")?;
205 /// let addr = socket.peer_addr().expect("Couldn't get peer address");
206 /// Ok(())
207 /// }
208 /// ```
209 #[stable(feature = "unix_socket", since = "1.10.0")]
210 pub fn peer_addr(&self) -> io::Result<SocketAddr> {
211 SocketAddr::new(|addr, len| unsafe { libc::getpeername(self.as_raw_fd(), addr, len) })
212 }
213
214 /// Gets the peer credentials for this Unix domain socket.
215 ///
216 /// # Examples
217 ///
218 /// ```no_run
219 /// #![feature(peer_credentials_unix_socket)]
220 /// use std::os::unix::net::UnixStream;
221 ///
222 /// fn main() -> std::io::Result<()> {
223 /// let socket = UnixStream::connect("/tmp/sock")?;
224 /// let peer_cred = socket.peer_cred().expect("Couldn't get peer credentials");
225 /// Ok(())
226 /// }
227 /// ```
228 #[unstable(feature = "peer_credentials_unix_socket", issue = "42839", reason = "unstable")]
229 #[cfg(any(
230 target_os = "android",
231 target_os = "linux",
232 target_os = "dragonfly",
233 target_os = "freebsd",
234 target_os = "ios",
235 target_os = "tvos",
236 target_os = "macos",
237 target_os = "watchos",
238 target_os = "visionos",
239 target_os = "netbsd",
240 target_os = "openbsd",
241 target_os = "nto"
242 ))]
243 pub fn peer_cred(&self) -> io::Result<UCred> {
244 peer_cred(self)
245 }
246
247 /// Sets the read timeout for the socket.
248 ///
249 /// If the provided value is [`None`], then [`read`] calls will block
250 /// indefinitely. An [`Err`] is returned if the zero [`Duration`] is passed to this
251 /// method.
252 ///
253 /// [`read`]: io::Read::read
254 ///
255 /// # Examples
256 ///
257 /// ```no_run
258 /// use std::os::unix::net::UnixStream;
259 /// use std::time::Duration;
260 ///
261 /// fn main() -> std::io::Result<()> {
262 /// let socket = UnixStream::connect("/tmp/sock")?;
263 /// socket.set_read_timeout(Some(Duration::new(1, 0))).expect("Couldn't set read timeout");
264 /// Ok(())
265 /// }
266 /// ```
267 ///
268 /// An [`Err`] is returned if the zero [`Duration`] is passed to this
269 /// method:
270 ///
271 /// ```no_run
272 /// use std::io;
273 /// use std::os::unix::net::UnixStream;
274 /// use std::time::Duration;
275 ///
276 /// fn main() -> std::io::Result<()> {
277 /// let socket = UnixStream::connect("/tmp/sock")?;
278 /// let result = socket.set_read_timeout(Some(Duration::new(0, 0)));
279 /// let err = result.unwrap_err();
280 /// assert_eq!(err.kind(), io::ErrorKind::InvalidInput);
281 /// Ok(())
282 /// }
283 /// ```
284 #[stable(feature = "unix_socket", since = "1.10.0")]
285 pub fn set_read_timeout(&self, timeout: Option<Duration>) -> io::Result<()> {
286 self.0.set_timeout(timeout, libc::SO_RCVTIMEO)
287 }
288
289 /// Sets the write timeout for the socket.
290 ///
291 /// If the provided value is [`None`], then [`write`] calls will block
292 /// indefinitely. An [`Err`] is returned if the zero [`Duration`] is
293 /// passed to this method.
294 ///
295 /// [`read`]: io::Read::read
296 ///
297 /// # Examples
298 ///
299 /// ```no_run
300 /// use std::os::unix::net::UnixStream;
301 /// use std::time::Duration;
302 ///
303 /// fn main() -> std::io::Result<()> {
304 /// let socket = UnixStream::connect("/tmp/sock")?;
305 /// socket.set_write_timeout(Some(Duration::new(1, 0)))
306 /// .expect("Couldn't set write timeout");
307 /// Ok(())
308 /// }
309 /// ```
310 ///
311 /// An [`Err`] is returned if the zero [`Duration`] is passed to this
312 /// method:
313 ///
314 /// ```no_run
315 /// use std::io;
316 /// use std::net::UdpSocket;
317 /// use std::time::Duration;
318 ///
319 /// fn main() -> std::io::Result<()> {
320 /// let socket = UdpSocket::bind("127.0.0.1:34254")?;
321 /// let result = socket.set_write_timeout(Some(Duration::new(0, 0)));
322 /// let err = result.unwrap_err();
323 /// assert_eq!(err.kind(), io::ErrorKind::InvalidInput);
324 /// Ok(())
325 /// }
326 /// ```
327 #[stable(feature = "unix_socket", since = "1.10.0")]
328 pub fn set_write_timeout(&self, timeout: Option<Duration>) -> io::Result<()> {
329 self.0.set_timeout(timeout, libc::SO_SNDTIMEO)
330 }
331
332 /// Returns the read timeout of this socket.
333 ///
334 /// # Examples
335 ///
336 /// ```no_run
337 /// use std::os::unix::net::UnixStream;
338 /// use std::time::Duration;
339 ///
340 /// fn main() -> std::io::Result<()> {
341 /// let socket = UnixStream::connect("/tmp/sock")?;
342 /// socket.set_read_timeout(Some(Duration::new(1, 0))).expect("Couldn't set read timeout");
343 /// assert_eq!(socket.read_timeout()?, Some(Duration::new(1, 0)));
344 /// Ok(())
345 /// }
346 /// ```
347 #[stable(feature = "unix_socket", since = "1.10.0")]
348 pub fn read_timeout(&self) -> io::Result<Option<Duration>> {
349 self.0.timeout(libc::SO_RCVTIMEO)
350 }
351
352 /// Returns the write timeout of this socket.
353 ///
354 /// # Examples
355 ///
356 /// ```no_run
357 /// use std::os::unix::net::UnixStream;
358 /// use std::time::Duration;
359 ///
360 /// fn main() -> std::io::Result<()> {
361 /// let socket = UnixStream::connect("/tmp/sock")?;
362 /// socket.set_write_timeout(Some(Duration::new(1, 0)))
363 /// .expect("Couldn't set write timeout");
364 /// assert_eq!(socket.write_timeout()?, Some(Duration::new(1, 0)));
365 /// Ok(())
366 /// }
367 /// ```
368 #[stable(feature = "unix_socket", since = "1.10.0")]
369 pub fn write_timeout(&self) -> io::Result<Option<Duration>> {
370 self.0.timeout(libc::SO_SNDTIMEO)
371 }
372
373 /// Moves the socket into or out of nonblocking mode.
374 ///
375 /// # Examples
376 ///
377 /// ```no_run
378 /// use std::os::unix::net::UnixStream;
379 ///
380 /// fn main() -> std::io::Result<()> {
381 /// let socket = UnixStream::connect("/tmp/sock")?;
382 /// socket.set_nonblocking(true).expect("Couldn't set nonblocking");
383 /// Ok(())
384 /// }
385 /// ```
386 #[stable(feature = "unix_socket", since = "1.10.0")]
387 pub fn set_nonblocking(&self, nonblocking: bool) -> io::Result<()> {
388 self.0.set_nonblocking(nonblocking)
389 }
390
391 /// Set the id of the socket for network filtering purpose
392 ///
393 #[cfg_attr(
394 any(target_os = "linux", target_os = "freebsd", target_os = "openbsd"),
395 doc = "```no_run"
396 )]
397 #[cfg_attr(
398 not(any(target_os = "linux", target_os = "freebsd", target_os = "openbsd")),
399 doc = "```ignore"
400 )]
401 /// #![feature(unix_set_mark)]
402 /// use std::os::unix::net::UnixStream;
403 ///
404 /// fn main() -> std::io::Result<()> {
405 /// let sock = UnixStream::connect("/tmp/sock")?;
406 /// sock.set_mark(32)?;
407 /// Ok(())
408 /// }
409 /// ```
410 #[cfg(any(doc, target_os = "linux", target_os = "freebsd", target_os = "openbsd",))]
411 #[unstable(feature = "unix_set_mark", issue = "96467")]
412 pub fn set_mark(&self, mark: u32) -> io::Result<()> {
413 self.0.set_mark(mark)
414 }
415
416 /// Returns the value of the `SO_ERROR` option.
417 ///
418 /// # Examples
419 ///
420 /// ```no_run
421 /// use std::os::unix::net::UnixStream;
422 ///
423 /// fn main() -> std::io::Result<()> {
424 /// let socket = UnixStream::connect("/tmp/sock")?;
425 /// if let Ok(Some(err)) = socket.take_error() {
426 /// println!("Got error: {err:?}");
427 /// }
428 /// Ok(())
429 /// }
430 /// ```
431 ///
432 /// # Platform specific
433 /// On Redox this always returns `None`.
434 #[stable(feature = "unix_socket", since = "1.10.0")]
435 pub fn take_error(&self) -> io::Result<Option<io::Error>> {
436 self.0.take_error()
437 }
438
439 /// Shuts down the read, write, or both halves of this connection.
440 ///
441 /// This function will cause all pending and future I/O calls on the
442 /// specified portions to immediately return with an appropriate value
443 /// (see the documentation of [`Shutdown`]).
444 ///
445 /// # Examples
446 ///
447 /// ```no_run
448 /// use std::os::unix::net::UnixStream;
449 /// use std::net::Shutdown;
450 ///
451 /// fn main() -> std::io::Result<()> {
452 /// let socket = UnixStream::connect("/tmp/sock")?;
453 /// socket.shutdown(Shutdown::Both).expect("shutdown function failed");
454 /// Ok(())
455 /// }
456 /// ```
457 #[stable(feature = "unix_socket", since = "1.10.0")]
458 pub fn shutdown(&self, how: Shutdown) -> io::Result<()> {
459 self.0.shutdown(how)
460 }
461
462 /// Receives data on the socket from the remote address to which it is
463 /// connected, without removing that data from the queue. On success,
464 /// returns the number of bytes peeked.
465 ///
466 /// Successive calls return the same data. This is accomplished by passing
467 /// `MSG_PEEK` as a flag to the underlying `recv` system call.
468 ///
469 /// # Examples
470 ///
471 /// ```no_run
472 /// #![feature(unix_socket_peek)]
473 ///
474 /// use std::os::unix::net::UnixStream;
475 ///
476 /// fn main() -> std::io::Result<()> {
477 /// let socket = UnixStream::connect("/tmp/sock")?;
478 /// let mut buf = [0; 10];
479 /// let len = socket.peek(&mut buf).expect("peek failed");
480 /// Ok(())
481 /// }
482 /// ```
483 #[unstable(feature = "unix_socket_peek", issue = "76923")]
484 pub fn peek(&self, buf: &mut [u8]) -> io::Result<usize> {
485 self.0.peek(buf)
486 }
487
488 /// Receives data and ancillary data from socket.
489 ///
490 /// On success, returns the number of bytes read.
491 ///
492 /// # Examples
493 ///
494 #[cfg_attr(any(target_os = "android", target_os = "linux"), doc = "```no_run")]
495 #[cfg_attr(not(any(target_os = "android", target_os = "linux")), doc = "```ignore")]
496 /// #![feature(unix_socket_ancillary_data)]
497 /// use std::os::unix::net::{UnixStream, SocketAncillary, AncillaryData};
498 /// use std::io::IoSliceMut;
499 ///
500 /// fn main() -> std::io::Result<()> {
501 /// let socket = UnixStream::connect("/tmp/sock")?;
502 /// let mut buf1 = [1; 8];
503 /// let mut buf2 = [2; 16];
504 /// let mut buf3 = [3; 8];
505 /// let mut bufs = &mut [
506 /// IoSliceMut::new(&mut buf1),
507 /// IoSliceMut::new(&mut buf2),
508 /// IoSliceMut::new(&mut buf3),
509 /// ][..];
510 /// let mut fds = [0; 8];
511 /// let mut ancillary_buffer = [0; 128];
512 /// let mut ancillary = SocketAncillary::new(&mut ancillary_buffer[..]);
513 /// let size = socket.recv_vectored_with_ancillary(bufs, &mut ancillary)?;
514 /// println!("received {size}");
515 /// for ancillary_result in ancillary.messages() {
516 /// if let AncillaryData::ScmRights(scm_rights) = ancillary_result.unwrap() {
517 /// for fd in scm_rights {
518 /// println!("receive file descriptor: {fd}");
519 /// }
520 /// }
521 /// }
522 /// Ok(())
523 /// }
524 /// ```
525 #[cfg(any(doc, target_os = "android", target_os = "linux"))]
526 #[unstable(feature = "unix_socket_ancillary_data", issue = "76915")]
527 pub fn recv_vectored_with_ancillary(
528 &self,
529 bufs: &mut [IoSliceMut<'_>],
530 ancillary: &mut SocketAncillary<'_>,
531 ) -> io::Result<usize> {
532 let (count, _, _) = recv_vectored_with_ancillary_from(&self.0, bufs, ancillary)?;
533
534 Ok(count)
535 }
536
537 /// Sends data and ancillary data on the socket.
538 ///
539 /// On success, returns the number of bytes written.
540 ///
541 /// # Examples
542 ///
543 #[cfg_attr(any(target_os = "android", target_os = "linux"), doc = "```no_run")]
544 #[cfg_attr(not(any(target_os = "android", target_os = "linux")), doc = "```ignore")]
545 /// #![feature(unix_socket_ancillary_data)]
546 /// use std::os::unix::net::{UnixStream, SocketAncillary};
547 /// use std::io::IoSlice;
548 ///
549 /// fn main() -> std::io::Result<()> {
550 /// let socket = UnixStream::connect("/tmp/sock")?;
551 /// let buf1 = [1; 8];
552 /// let buf2 = [2; 16];
553 /// let buf3 = [3; 8];
554 /// let bufs = &[
555 /// IoSlice::new(&buf1),
556 /// IoSlice::new(&buf2),
557 /// IoSlice::new(&buf3),
558 /// ][..];
559 /// let fds = [0, 1, 2];
560 /// let mut ancillary_buffer = [0; 128];
561 /// let mut ancillary = SocketAncillary::new(&mut ancillary_buffer[..]);
562 /// ancillary.add_fds(&fds[..]);
563 /// socket.send_vectored_with_ancillary(bufs, &mut ancillary)
564 /// .expect("send_vectored_with_ancillary function failed");
565 /// Ok(())
566 /// }
567 /// ```
568 #[cfg(any(doc, target_os = "android", target_os = "linux"))]
569 #[unstable(feature = "unix_socket_ancillary_data", issue = "76915")]
570 pub fn send_vectored_with_ancillary(
571 &self,
572 bufs: &[IoSlice<'_>],
573 ancillary: &mut SocketAncillary<'_>,
574 ) -> io::Result<usize> {
575 send_vectored_with_ancillary_to(&self.0, None, bufs, ancillary)
576 }
577}
578
579#[stable(feature = "unix_socket", since = "1.10.0")]
580impl io::Read for UnixStream {
581 fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
582 io::Read::read(&mut &*self, buf)
583 }
584
585 fn read_buf(&mut self, buf: io::BorrowedCursor<'_>) -> io::Result<()> {
586 io::Read::read_buf(&mut &*self, buf)
587 }
588
589 fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
590 io::Read::read_vectored(&mut &*self, bufs)
591 }
592
593 #[inline]
594 fn is_read_vectored(&self) -> bool {
595 io::Read::is_read_vectored(&&*self)
596 }
597}
598
599#[stable(feature = "unix_socket", since = "1.10.0")]
600impl<'a> io::Read for &'a UnixStream {
601 fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
602 self.0.read(buf)
603 }
604
605 fn read_buf(&mut self, buf: io::BorrowedCursor<'_>) -> io::Result<()> {
606 self.0.read_buf(buf)
607 }
608
609 fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
610 self.0.read_vectored(bufs)
611 }
612
613 #[inline]
614 fn is_read_vectored(&self) -> bool {
615 self.0.is_read_vectored()
616 }
617}
618
619#[stable(feature = "unix_socket", since = "1.10.0")]
620impl io::Write for UnixStream {
621 fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
622 io::Write::write(&mut &*self, buf)
623 }
624
625 fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> io::Result<usize> {
626 io::Write::write_vectored(&mut &*self, bufs)
627 }
628
629 #[inline]
630 fn is_write_vectored(&self) -> bool {
631 io::Write::is_write_vectored(&&*self)
632 }
633
634 fn flush(&mut self) -> io::Result<()> {
635 io::Write::flush(&mut &*self)
636 }
637}
638
639#[stable(feature = "unix_socket", since = "1.10.0")]
640impl<'a> io::Write for &'a UnixStream {
641 fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
642 self.0.write(buf)
643 }
644
645 fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> io::Result<usize> {
646 self.0.write_vectored(bufs)
647 }
648
649 #[inline]
650 fn is_write_vectored(&self) -> bool {
651 self.0.is_write_vectored()
652 }
653
654 #[inline]
655 fn flush(&mut self) -> io::Result<()> {
656 Ok(())
657 }
658}
659
660#[stable(feature = "unix_socket", since = "1.10.0")]
661impl AsRawFd for UnixStream {
662 #[inline]
663 fn as_raw_fd(&self) -> RawFd {
664 self.0.as_raw_fd()
665 }
666}
667
668#[stable(feature = "unix_socket", since = "1.10.0")]
669impl FromRawFd for UnixStream {
670 #[inline]
671 unsafe fn from_raw_fd(fd: RawFd) -> UnixStream {
672 UnixStream(Socket::from_inner(FromInner::from_inner(OwnedFd::from_raw_fd(fd))))
673 }
674}
675
676#[stable(feature = "unix_socket", since = "1.10.0")]
677impl IntoRawFd for UnixStream {
678 #[inline]
679 fn into_raw_fd(self) -> RawFd {
680 self.0.into_raw_fd()
681 }
682}
683
684#[stable(feature = "io_safety", since = "1.63.0")]
685impl AsFd for UnixStream {
686 #[inline]
687 fn as_fd(&self) -> BorrowedFd<'_> {
688 self.0.as_fd()
689 }
690}
691
692#[stable(feature = "io_safety", since = "1.63.0")]
693impl From<UnixStream> for OwnedFd {
694 /// Takes ownership of a [`UnixStream`]'s socket file descriptor.
695 #[inline]
696 fn from(unix_stream: UnixStream) -> OwnedFd {
697 unsafe { OwnedFd::from_raw_fd(unix_stream.into_raw_fd()) }
698 }
699}
700
701#[stable(feature = "io_safety", since = "1.63.0")]
702impl From<OwnedFd> for UnixStream {
703 #[inline]
704 fn from(owned: OwnedFd) -> Self {
705 unsafe { Self::from_raw_fd(owned.into_raw_fd()) }
706 }
707}
708
709impl AsInner<Socket> for UnixStream {
710 #[inline]
711 fn as_inner(&self) -> &Socket {
712 &self.0
713 }
714}
715