1 //! libc syscalls supporting `rustix::net`.
2
3 #[cfg(unix)]
4 use super::addr::SocketAddrUnix;
5 #[cfg(target_os = "linux")]
6 use super::msghdr::with_xdp_msghdr;
7 #[cfg(target_os = "linux")]
8 use super::write_sockaddr::encode_sockaddr_xdp;
9 use crate::backend::c;
10 use crate::backend::conv::{borrowed_fd, ret, ret_owned_fd, ret_send_recv, send_recv_len};
11 use crate::fd::{BorrowedFd, OwnedFd};
12 use crate::io;
13 #[cfg(target_os = "linux")]
14 use crate::net::xdp::SocketAddrXdp;
15 use crate::net::{SocketAddrAny, SocketAddrV4, SocketAddrV6};
16 use crate::utils::as_ptr;
17 use core::mem::{size_of, MaybeUninit};
18 #[cfg(not(any(
19 windows,
20 target_os = "espidf",
21 target_os = "redox",
22 target_os = "vita",
23 target_os = "wasi"
24 )))]
25 use {
26 super::msghdr::{with_noaddr_msghdr, with_recv_msghdr, with_v4_msghdr, with_v6_msghdr},
27 crate::io::{IoSlice, IoSliceMut},
28 crate::net::{RecvAncillaryBuffer, RecvMsgReturn, SendAncillaryBuffer},
29 };
30 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
31 use {
32 super::read_sockaddr::{initialize_family_to_unspec, maybe_read_sockaddr_os, read_sockaddr_os},
33 super::send_recv::{RecvFlags, SendFlags},
34 super::write_sockaddr::{encode_sockaddr_v4, encode_sockaddr_v6},
35 crate::net::{AddressFamily, Protocol, Shutdown, SocketFlags, SocketType},
36 core::ptr::null_mut,
37 };
38
39 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
recv( fd: BorrowedFd<'_>, buf: *mut u8, len: usize, flags: RecvFlags, ) -> io::Result<usize>40 pub(crate) unsafe fn recv(
41 fd: BorrowedFd<'_>,
42 buf: *mut u8,
43 len: usize,
44 flags: RecvFlags,
45 ) -> io::Result<usize> {
46 ret_send_recv(c::recv(
47 borrowed_fd(fd),
48 buf.cast(),
49 send_recv_len(len),
50 bitflags_bits!(flags),
51 ))
52 }
53
54 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
send(fd: BorrowedFd<'_>, buf: &[u8], flags: SendFlags) -> io::Result<usize>55 pub(crate) fn send(fd: BorrowedFd<'_>, buf: &[u8], flags: SendFlags) -> io::Result<usize> {
56 unsafe {
57 ret_send_recv(c::send(
58 borrowed_fd(fd),
59 buf.as_ptr().cast(),
60 send_recv_len(buf.len()),
61 bitflags_bits!(flags),
62 ))
63 }
64 }
65
66 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
recvfrom( fd: BorrowedFd<'_>, buf: *mut u8, buf_len: usize, flags: RecvFlags, ) -> io::Result<(usize, Option<SocketAddrAny>)>67 pub(crate) unsafe fn recvfrom(
68 fd: BorrowedFd<'_>,
69 buf: *mut u8,
70 buf_len: usize,
71 flags: RecvFlags,
72 ) -> io::Result<(usize, Option<SocketAddrAny>)> {
73 let mut storage = MaybeUninit::<c::sockaddr_storage>::uninit();
74 let mut len = size_of::<c::sockaddr_storage>() as c::socklen_t;
75
76 // `recvfrom` does not write to the storage if the socket is
77 // connection-oriented sockets, so we initialize the family field to
78 // `AF_UNSPEC` so that we can detect this case.
79 initialize_family_to_unspec(storage.as_mut_ptr());
80
81 ret_send_recv(c::recvfrom(
82 borrowed_fd(fd),
83 buf.cast(),
84 send_recv_len(buf_len),
85 bitflags_bits!(flags),
86 storage.as_mut_ptr().cast(),
87 &mut len,
88 ))
89 .map(|nread| {
90 (
91 nread,
92 maybe_read_sockaddr_os(storage.as_ptr(), len.try_into().unwrap()),
93 )
94 })
95 }
96
97 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
sendto_v4( fd: BorrowedFd<'_>, buf: &[u8], flags: SendFlags, addr: &SocketAddrV4, ) -> io::Result<usize>98 pub(crate) fn sendto_v4(
99 fd: BorrowedFd<'_>,
100 buf: &[u8],
101 flags: SendFlags,
102 addr: &SocketAddrV4,
103 ) -> io::Result<usize> {
104 unsafe {
105 ret_send_recv(c::sendto(
106 borrowed_fd(fd),
107 buf.as_ptr().cast(),
108 send_recv_len(buf.len()),
109 bitflags_bits!(flags),
110 as_ptr(&encode_sockaddr_v4(addr)).cast::<c::sockaddr>(),
111 size_of::<c::sockaddr_in>() as c::socklen_t,
112 ))
113 }
114 }
115
116 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
sendto_v6( fd: BorrowedFd<'_>, buf: &[u8], flags: SendFlags, addr: &SocketAddrV6, ) -> io::Result<usize>117 pub(crate) fn sendto_v6(
118 fd: BorrowedFd<'_>,
119 buf: &[u8],
120 flags: SendFlags,
121 addr: &SocketAddrV6,
122 ) -> io::Result<usize> {
123 unsafe {
124 ret_send_recv(c::sendto(
125 borrowed_fd(fd),
126 buf.as_ptr().cast(),
127 send_recv_len(buf.len()),
128 bitflags_bits!(flags),
129 as_ptr(&encode_sockaddr_v6(addr)).cast::<c::sockaddr>(),
130 size_of::<c::sockaddr_in6>() as c::socklen_t,
131 ))
132 }
133 }
134
135 #[cfg(not(any(windows, target_os = "redox", target_os = "wasi")))]
sendto_unix( fd: BorrowedFd<'_>, buf: &[u8], flags: SendFlags, addr: &SocketAddrUnix, ) -> io::Result<usize>136 pub(crate) fn sendto_unix(
137 fd: BorrowedFd<'_>,
138 buf: &[u8],
139 flags: SendFlags,
140 addr: &SocketAddrUnix,
141 ) -> io::Result<usize> {
142 unsafe {
143 ret_send_recv(c::sendto(
144 borrowed_fd(fd),
145 buf.as_ptr().cast(),
146 send_recv_len(buf.len()),
147 bitflags_bits!(flags),
148 as_ptr(&addr.unix).cast(),
149 addr.addr_len(),
150 ))
151 }
152 }
153
154 #[cfg(target_os = "linux")]
sendto_xdp( fd: BorrowedFd<'_>, buf: &[u8], flags: SendFlags, addr: &SocketAddrXdp, ) -> io::Result<usize>155 pub(crate) fn sendto_xdp(
156 fd: BorrowedFd<'_>,
157 buf: &[u8],
158 flags: SendFlags,
159 addr: &SocketAddrXdp,
160 ) -> io::Result<usize> {
161 unsafe {
162 ret_send_recv(c::sendto(
163 borrowed_fd(fd),
164 buf.as_ptr().cast(),
165 send_recv_len(buf.len()),
166 bitflags_bits!(flags),
167 as_ptr(&encode_sockaddr_xdp(addr)).cast::<c::sockaddr>(),
168 size_of::<c::sockaddr_xdp>() as _,
169 ))
170 }
171 }
172
173 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
socket( domain: AddressFamily, type_: SocketType, protocol: Option<Protocol>, ) -> io::Result<OwnedFd>174 pub(crate) fn socket(
175 domain: AddressFamily,
176 type_: SocketType,
177 protocol: Option<Protocol>,
178 ) -> io::Result<OwnedFd> {
179 let raw_protocol = match protocol {
180 Some(p) => p.0.get(),
181 None => 0,
182 };
183 unsafe {
184 ret_owned_fd(c::socket(
185 domain.0 as c::c_int,
186 type_.0 as c::c_int,
187 raw_protocol as c::c_int,
188 ))
189 }
190 }
191
192 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
socket_with( domain: AddressFamily, type_: SocketType, flags: SocketFlags, protocol: Option<Protocol>, ) -> io::Result<OwnedFd>193 pub(crate) fn socket_with(
194 domain: AddressFamily,
195 type_: SocketType,
196 flags: SocketFlags,
197 protocol: Option<Protocol>,
198 ) -> io::Result<OwnedFd> {
199 let raw_protocol = match protocol {
200 Some(p) => p.0.get(),
201 None => 0,
202 };
203 unsafe {
204 ret_owned_fd(c::socket(
205 domain.0 as c::c_int,
206 (type_.0 | flags.bits()) as c::c_int,
207 raw_protocol as c::c_int,
208 ))
209 }
210 }
211
212 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
bind_v4(sockfd: BorrowedFd<'_>, addr: &SocketAddrV4) -> io::Result<()>213 pub(crate) fn bind_v4(sockfd: BorrowedFd<'_>, addr: &SocketAddrV4) -> io::Result<()> {
214 unsafe {
215 ret(c::bind(
216 borrowed_fd(sockfd),
217 as_ptr(&encode_sockaddr_v4(addr)).cast(),
218 size_of::<c::sockaddr_in>() as c::socklen_t,
219 ))
220 }
221 }
222
223 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
bind_v6(sockfd: BorrowedFd<'_>, addr: &SocketAddrV6) -> io::Result<()>224 pub(crate) fn bind_v6(sockfd: BorrowedFd<'_>, addr: &SocketAddrV6) -> io::Result<()> {
225 unsafe {
226 ret(c::bind(
227 borrowed_fd(sockfd),
228 as_ptr(&encode_sockaddr_v6(addr)).cast(),
229 size_of::<c::sockaddr_in6>() as c::socklen_t,
230 ))
231 }
232 }
233
234 #[cfg(not(any(windows, target_os = "redox", target_os = "wasi")))]
bind_unix(sockfd: BorrowedFd<'_>, addr: &SocketAddrUnix) -> io::Result<()>235 pub(crate) fn bind_unix(sockfd: BorrowedFd<'_>, addr: &SocketAddrUnix) -> io::Result<()> {
236 unsafe {
237 ret(c::bind(
238 borrowed_fd(sockfd),
239 as_ptr(&addr.unix).cast(),
240 addr.addr_len(),
241 ))
242 }
243 }
244
245 #[cfg(target_os = "linux")]
bind_xdp(sockfd: BorrowedFd<'_>, addr: &SocketAddrXdp) -> io::Result<()>246 pub(crate) fn bind_xdp(sockfd: BorrowedFd<'_>, addr: &SocketAddrXdp) -> io::Result<()> {
247 unsafe {
248 ret(c::bind(
249 borrowed_fd(sockfd),
250 as_ptr(&encode_sockaddr_xdp(addr)).cast(),
251 size_of::<c::sockaddr_xdp>() as c::socklen_t,
252 ))
253 }
254 }
255
256 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
connect_v4(sockfd: BorrowedFd<'_>, addr: &SocketAddrV4) -> io::Result<()>257 pub(crate) fn connect_v4(sockfd: BorrowedFd<'_>, addr: &SocketAddrV4) -> io::Result<()> {
258 unsafe {
259 ret(c::connect(
260 borrowed_fd(sockfd),
261 as_ptr(&encode_sockaddr_v4(addr)).cast(),
262 size_of::<c::sockaddr_in>() as c::socklen_t,
263 ))
264 }
265 }
266
267 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
connect_v6(sockfd: BorrowedFd<'_>, addr: &SocketAddrV6) -> io::Result<()>268 pub(crate) fn connect_v6(sockfd: BorrowedFd<'_>, addr: &SocketAddrV6) -> io::Result<()> {
269 unsafe {
270 ret(c::connect(
271 borrowed_fd(sockfd),
272 as_ptr(&encode_sockaddr_v6(addr)).cast(),
273 size_of::<c::sockaddr_in6>() as c::socklen_t,
274 ))
275 }
276 }
277
278 #[cfg(not(any(windows, target_os = "redox", target_os = "wasi")))]
connect_unix(sockfd: BorrowedFd<'_>, addr: &SocketAddrUnix) -> io::Result<()>279 pub(crate) fn connect_unix(sockfd: BorrowedFd<'_>, addr: &SocketAddrUnix) -> io::Result<()> {
280 unsafe {
281 ret(c::connect(
282 borrowed_fd(sockfd),
283 as_ptr(&addr.unix).cast(),
284 addr.addr_len(),
285 ))
286 }
287 }
288
289 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
connect_unspec(sockfd: BorrowedFd<'_>) -> io::Result<()>290 pub(crate) fn connect_unspec(sockfd: BorrowedFd<'_>) -> io::Result<()> {
291 debug_assert_eq!(c::AF_UNSPEC, 0);
292 let addr = MaybeUninit::<c::sockaddr_storage>::zeroed();
293 unsafe {
294 ret(c::connect(
295 borrowed_fd(sockfd),
296 as_ptr(&addr).cast(),
297 size_of::<c::sockaddr_storage>() as c::socklen_t,
298 ))
299 }
300 }
301
302 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
listen(sockfd: BorrowedFd<'_>, backlog: c::c_int) -> io::Result<()>303 pub(crate) fn listen(sockfd: BorrowedFd<'_>, backlog: c::c_int) -> io::Result<()> {
304 unsafe { ret(c::listen(borrowed_fd(sockfd), backlog)) }
305 }
306
307 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
accept(sockfd: BorrowedFd<'_>) -> io::Result<OwnedFd>308 pub(crate) fn accept(sockfd: BorrowedFd<'_>) -> io::Result<OwnedFd> {
309 unsafe {
310 let owned_fd = ret_owned_fd(c::accept(borrowed_fd(sockfd), null_mut(), null_mut()))?;
311 Ok(owned_fd)
312 }
313 }
314
315 #[cfg(not(any(
316 windows,
317 target_os = "espidf",
318 target_os = "redox",
319 target_os = "vita",
320 target_os = "wasi"
321 )))]
recvmsg( sockfd: BorrowedFd<'_>, iov: &mut [IoSliceMut<'_>], control: &mut RecvAncillaryBuffer<'_>, msg_flags: RecvFlags, ) -> io::Result<RecvMsgReturn>322 pub(crate) fn recvmsg(
323 sockfd: BorrowedFd<'_>,
324 iov: &mut [IoSliceMut<'_>],
325 control: &mut RecvAncillaryBuffer<'_>,
326 msg_flags: RecvFlags,
327 ) -> io::Result<RecvMsgReturn> {
328 let mut storage = MaybeUninit::<c::sockaddr_storage>::uninit();
329
330 with_recv_msghdr(&mut storage, iov, control, |msghdr| {
331 let result = unsafe {
332 ret_send_recv(c::recvmsg(
333 borrowed_fd(sockfd),
334 msghdr,
335 bitflags_bits!(msg_flags),
336 ))
337 };
338
339 result.map(|bytes| {
340 // Get the address of the sender, if any.
341 let addr =
342 unsafe { maybe_read_sockaddr_os(msghdr.msg_name as _, msghdr.msg_namelen as _) };
343
344 RecvMsgReturn {
345 bytes,
346 address: addr,
347 flags: RecvFlags::from_bits_retain(bitcast!(msghdr.msg_flags)),
348 }
349 })
350 })
351 }
352
353 #[cfg(not(any(
354 windows,
355 target_os = "espidf",
356 target_os = "redox",
357 target_os = "vita",
358 target_os = "wasi"
359 )))]
sendmsg( sockfd: BorrowedFd<'_>, iov: &[IoSlice<'_>], control: &mut SendAncillaryBuffer<'_, '_, '_>, msg_flags: SendFlags, ) -> io::Result<usize>360 pub(crate) fn sendmsg(
361 sockfd: BorrowedFd<'_>,
362 iov: &[IoSlice<'_>],
363 control: &mut SendAncillaryBuffer<'_, '_, '_>,
364 msg_flags: SendFlags,
365 ) -> io::Result<usize> {
366 with_noaddr_msghdr(iov, control, |msghdr| unsafe {
367 ret_send_recv(c::sendmsg(
368 borrowed_fd(sockfd),
369 &msghdr,
370 bitflags_bits!(msg_flags),
371 ))
372 })
373 }
374
375 #[cfg(not(any(
376 windows,
377 target_os = "espidf",
378 target_os = "redox",
379 target_os = "vita",
380 target_os = "wasi"
381 )))]
sendmsg_v4( sockfd: BorrowedFd<'_>, addr: &SocketAddrV4, iov: &[IoSlice<'_>], control: &mut SendAncillaryBuffer<'_, '_, '_>, msg_flags: SendFlags, ) -> io::Result<usize>382 pub(crate) fn sendmsg_v4(
383 sockfd: BorrowedFd<'_>,
384 addr: &SocketAddrV4,
385 iov: &[IoSlice<'_>],
386 control: &mut SendAncillaryBuffer<'_, '_, '_>,
387 msg_flags: SendFlags,
388 ) -> io::Result<usize> {
389 with_v4_msghdr(addr, iov, control, |msghdr| unsafe {
390 ret_send_recv(c::sendmsg(
391 borrowed_fd(sockfd),
392 &msghdr,
393 bitflags_bits!(msg_flags),
394 ))
395 })
396 }
397
398 #[cfg(not(any(
399 windows,
400 target_os = "espidf",
401 target_os = "redox",
402 target_os = "vita",
403 target_os = "wasi"
404 )))]
sendmsg_v6( sockfd: BorrowedFd<'_>, addr: &SocketAddrV6, iov: &[IoSlice<'_>], control: &mut SendAncillaryBuffer<'_, '_, '_>, msg_flags: SendFlags, ) -> io::Result<usize>405 pub(crate) fn sendmsg_v6(
406 sockfd: BorrowedFd<'_>,
407 addr: &SocketAddrV6,
408 iov: &[IoSlice<'_>],
409 control: &mut SendAncillaryBuffer<'_, '_, '_>,
410 msg_flags: SendFlags,
411 ) -> io::Result<usize> {
412 with_v6_msghdr(addr, iov, control, |msghdr| unsafe {
413 ret_send_recv(c::sendmsg(
414 borrowed_fd(sockfd),
415 &msghdr,
416 bitflags_bits!(msg_flags),
417 ))
418 })
419 }
420
421 #[cfg(all(
422 unix,
423 not(any(target_os = "espidf", target_os = "redox", target_os = "vita"))
424 ))]
sendmsg_unix( sockfd: BorrowedFd<'_>, addr: &SocketAddrUnix, iov: &[IoSlice<'_>], control: &mut SendAncillaryBuffer<'_, '_, '_>, msg_flags: SendFlags, ) -> io::Result<usize>425 pub(crate) fn sendmsg_unix(
426 sockfd: BorrowedFd<'_>,
427 addr: &SocketAddrUnix,
428 iov: &[IoSlice<'_>],
429 control: &mut SendAncillaryBuffer<'_, '_, '_>,
430 msg_flags: SendFlags,
431 ) -> io::Result<usize> {
432 super::msghdr::with_unix_msghdr(addr, iov, control, |msghdr| unsafe {
433 ret_send_recv(c::sendmsg(
434 borrowed_fd(sockfd),
435 &msghdr,
436 bitflags_bits!(msg_flags),
437 ))
438 })
439 }
440
441 #[cfg(target_os = "linux")]
sendmsg_xdp( sockfd: BorrowedFd<'_>, addr: &SocketAddrXdp, iov: &[IoSlice<'_>], control: &mut SendAncillaryBuffer<'_, '_, '_>, msg_flags: SendFlags, ) -> io::Result<usize>442 pub(crate) fn sendmsg_xdp(
443 sockfd: BorrowedFd<'_>,
444 addr: &SocketAddrXdp,
445 iov: &[IoSlice<'_>],
446 control: &mut SendAncillaryBuffer<'_, '_, '_>,
447 msg_flags: SendFlags,
448 ) -> io::Result<usize> {
449 with_xdp_msghdr(addr, iov, control, |msghdr| unsafe {
450 ret_send_recv(c::sendmsg(
451 borrowed_fd(sockfd),
452 &msghdr,
453 bitflags_bits!(msg_flags),
454 ))
455 })
456 }
457
458 #[cfg(not(any(
459 apple,
460 windows,
461 target_os = "aix",
462 target_os = "espidf",
463 target_os = "haiku",
464 target_os = "redox",
465 target_os = "nto",
466 target_os = "vita",
467 target_os = "wasi",
468 )))]
accept_with(sockfd: BorrowedFd<'_>, flags: SocketFlags) -> io::Result<OwnedFd>469 pub(crate) fn accept_with(sockfd: BorrowedFd<'_>, flags: SocketFlags) -> io::Result<OwnedFd> {
470 unsafe {
471 let owned_fd = ret_owned_fd(c::accept4(
472 borrowed_fd(sockfd),
473 null_mut(),
474 null_mut(),
475 flags.bits() as c::c_int,
476 ))?;
477 Ok(owned_fd)
478 }
479 }
480
481 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
acceptfrom(sockfd: BorrowedFd<'_>) -> io::Result<(OwnedFd, Option<SocketAddrAny>)>482 pub(crate) fn acceptfrom(sockfd: BorrowedFd<'_>) -> io::Result<(OwnedFd, Option<SocketAddrAny>)> {
483 unsafe {
484 let mut storage = MaybeUninit::<c::sockaddr_storage>::uninit();
485 let mut len = size_of::<c::sockaddr_storage>() as c::socklen_t;
486 let owned_fd = ret_owned_fd(c::accept(
487 borrowed_fd(sockfd),
488 storage.as_mut_ptr().cast(),
489 &mut len,
490 ))?;
491 Ok((
492 owned_fd,
493 maybe_read_sockaddr_os(storage.as_ptr(), len.try_into().unwrap()),
494 ))
495 }
496 }
497
498 #[cfg(not(any(
499 apple,
500 windows,
501 target_os = "aix",
502 target_os = "espidf",
503 target_os = "haiku",
504 target_os = "nto",
505 target_os = "redox",
506 target_os = "vita",
507 target_os = "wasi",
508 )))]
acceptfrom_with( sockfd: BorrowedFd<'_>, flags: SocketFlags, ) -> io::Result<(OwnedFd, Option<SocketAddrAny>)>509 pub(crate) fn acceptfrom_with(
510 sockfd: BorrowedFd<'_>,
511 flags: SocketFlags,
512 ) -> io::Result<(OwnedFd, Option<SocketAddrAny>)> {
513 unsafe {
514 let mut storage = MaybeUninit::<c::sockaddr_storage>::uninit();
515 let mut len = size_of::<c::sockaddr_storage>() as c::socklen_t;
516 let owned_fd = ret_owned_fd(c::accept4(
517 borrowed_fd(sockfd),
518 storage.as_mut_ptr().cast(),
519 &mut len,
520 flags.bits() as c::c_int,
521 ))?;
522 Ok((
523 owned_fd,
524 maybe_read_sockaddr_os(storage.as_ptr(), len.try_into().unwrap()),
525 ))
526 }
527 }
528
529 /// Darwin lacks `accept4`, but does have `accept`. We define
530 /// `SocketFlags` to have no flags, so we can discard it here.
531 #[cfg(any(
532 apple,
533 windows,
534 target_os = "aix",
535 target_os = "espidf",
536 target_os = "haiku",
537 target_os = "nto",
538 target_os = "vita",
539 ))]
accept_with(sockfd: BorrowedFd<'_>, _flags: SocketFlags) -> io::Result<OwnedFd>540 pub(crate) fn accept_with(sockfd: BorrowedFd<'_>, _flags: SocketFlags) -> io::Result<OwnedFd> {
541 accept(sockfd)
542 }
543
544 /// Darwin lacks `accept4`, but does have `accept`. We define
545 /// `SocketFlags` to have no flags, so we can discard it here.
546 #[cfg(any(
547 apple,
548 windows,
549 target_os = "aix",
550 target_os = "espidf",
551 target_os = "haiku",
552 target_os = "nto",
553 target_os = "vita",
554 ))]
acceptfrom_with( sockfd: BorrowedFd<'_>, _flags: SocketFlags, ) -> io::Result<(OwnedFd, Option<SocketAddrAny>)>555 pub(crate) fn acceptfrom_with(
556 sockfd: BorrowedFd<'_>,
557 _flags: SocketFlags,
558 ) -> io::Result<(OwnedFd, Option<SocketAddrAny>)> {
559 acceptfrom(sockfd)
560 }
561
562 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
shutdown(sockfd: BorrowedFd<'_>, how: Shutdown) -> io::Result<()>563 pub(crate) fn shutdown(sockfd: BorrowedFd<'_>, how: Shutdown) -> io::Result<()> {
564 unsafe { ret(c::shutdown(borrowed_fd(sockfd), how as c::c_int)) }
565 }
566
567 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
getsockname(sockfd: BorrowedFd<'_>) -> io::Result<SocketAddrAny>568 pub(crate) fn getsockname(sockfd: BorrowedFd<'_>) -> io::Result<SocketAddrAny> {
569 unsafe {
570 let mut storage = MaybeUninit::<c::sockaddr_storage>::uninit();
571 let mut len = size_of::<c::sockaddr_storage>() as c::socklen_t;
572 ret(c::getsockname(
573 borrowed_fd(sockfd),
574 storage.as_mut_ptr().cast(),
575 &mut len,
576 ))?;
577 Ok(read_sockaddr_os(storage.as_ptr(), len.try_into().unwrap()))
578 }
579 }
580
581 #[cfg(not(any(target_os = "redox", target_os = "wasi")))]
getpeername(sockfd: BorrowedFd<'_>) -> io::Result<Option<SocketAddrAny>>582 pub(crate) fn getpeername(sockfd: BorrowedFd<'_>) -> io::Result<Option<SocketAddrAny>> {
583 unsafe {
584 let mut storage = MaybeUninit::<c::sockaddr_storage>::uninit();
585 let mut len = size_of::<c::sockaddr_storage>() as c::socklen_t;
586 ret(c::getpeername(
587 borrowed_fd(sockfd),
588 storage.as_mut_ptr().cast(),
589 &mut len,
590 ))?;
591 Ok(maybe_read_sockaddr_os(
592 storage.as_ptr(),
593 len.try_into().unwrap(),
594 ))
595 }
596 }
597
598 #[cfg(not(any(windows, target_os = "redox", target_os = "wasi")))]
socketpair( domain: AddressFamily, type_: SocketType, flags: SocketFlags, protocol: Option<Protocol>, ) -> io::Result<(OwnedFd, OwnedFd)>599 pub(crate) fn socketpair(
600 domain: AddressFamily,
601 type_: SocketType,
602 flags: SocketFlags,
603 protocol: Option<Protocol>,
604 ) -> io::Result<(OwnedFd, OwnedFd)> {
605 let raw_protocol = match protocol {
606 Some(p) => p.0.get(),
607 None => 0,
608 };
609 unsafe {
610 let mut fds = MaybeUninit::<[OwnedFd; 2]>::uninit();
611 ret(c::socketpair(
612 c::c_int::from(domain.0),
613 (type_.0 | flags.bits()) as c::c_int,
614 raw_protocol as c::c_int,
615 fds.as_mut_ptr().cast::<c::c_int>(),
616 ))?;
617
618 let [fd0, fd1] = fds.assume_init();
619 Ok((fd0, fd1))
620 }
621 }
622