Skip to content

Commit

Permalink
Merge branch 'master' into into-slice-trait
Browse files Browse the repository at this point in the history
  • Loading branch information
Noah-Kennedy authored Jul 31, 2022
2 parents 8efb9bd + 89a9bd7 commit ed7c0b3
Show file tree
Hide file tree
Showing 5 changed files with 87 additions and 5 deletions.
20 changes: 16 additions & 4 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -13,34 +13,46 @@ env:
RUST_BACKTRACE: 1

jobs:
# Depends on all actions that are required for a "successful" CI run.
# Based on the ci here: https://github.com/tokio-rs/tokio/blob/master/.github/workflows/ci.yml
all-systems-go:
runs-on: ubuntu-latest
needs:
- check
- fmt
- test
- docs
steps:
- run: exit 0

check:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v3
- name: Install Rust
run: rustup update stable
- run: cargo check

test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v3
- name: Install Rust
run: rustup update stable
- run: cargo test

fmt:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v3
- name: Install Rust
run: rustup update stable
- run: cargo fmt -- --check

docs:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v3
- name: Install Rust
run: rustup update nightly && rustup default nightly
- run: cargo doc --no-deps --all-features
Expand Down
3 changes: 3 additions & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -30,3 +30,6 @@ bencher = "0.1.5"
tempfile = "3.2.0"
tokio = { version = "1.2", features = ["macros", "io-util"] }
tokio-test = "0.4.2"

[package.metadata.docs.rs]
all-features = true
5 changes: 5 additions & 0 deletions src/driver/socket.rs
Original file line number Diff line number Diff line change
Expand Up @@ -117,6 +117,11 @@ impl Socket {
Self::bind_internal(addr, libc::AF_UNIX.into(), socket_type.into())
}

pub(crate) fn from_std(socket: std::net::UdpSocket) -> Socket {
let fd = SharedFd::new(socket.into_raw_fd());
Self { fd }
}

fn bind_internal(
socket_addr: socket2::SockAddr,
domain: socket2::Domain,
Expand Down
8 changes: 7 additions & 1 deletion src/fs/file.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ use crate::fs::OpenOptions;

use std::fmt;
use std::io;
use std::os::unix::io::{AsRawFd, RawFd};
use std::os::unix::io::{AsRawFd, FromRawFd, RawFd};
use std::path::Path;

/// A reference to an open file on the filesystem.
Expand Down Expand Up @@ -338,6 +338,12 @@ impl File {
}
}

impl FromRawFd for File {
unsafe fn from_raw_fd(fd: RawFd) -> Self {
File::from_shared_fd(SharedFd::new(fd))
}
}

impl AsRawFd for File {
fn as_raw_fd(&self) -> RawFd {
self.fd.raw_fd()
Expand Down
56 changes: 56 additions & 0 deletions src/net/udp.rs
Original file line number Diff line number Diff line change
Expand Up @@ -92,6 +92,62 @@ impl UdpSocket {
Ok(UdpSocket { inner: socket })
}

/// Creates new `UdpSocket` from a previously bound `std::net::UdpSocket`.
///
/// This function is intended to be used to wrap a UDP socket from the
/// standard library in the Tokio equivalent. The conversion assumes nothing
/// about the underlying socket; it is left up to the user to decide what socket
/// options are appropriate for their use case.
///
/// This can be used in conjunction with socket2's `Socket` interface to
/// configure a socket before it's handed off, such as setting options like
/// `reuse_address` or binding to multiple addresses.
///
/// # Example
///
/// ```
/// use socket2::{Protocol, Socket, Type};
/// use std::net::{Ipv4Addr, SocketAddr, SocketAddrV4};
/// use tokio_uring::net::UdpSocket;
///
/// fn main() -> std::io::Result<()> {
/// tokio_uring::start(async {
/// let std_addr: SocketAddr = "127.0.0.1:2401".parse().unwrap();
/// let second_addr: SocketAddr = "127.0.0.1:8080".parse().unwrap();
/// let sock = Socket::new(socket2::Domain::IPV4, Type::DGRAM, Some(Protocol::UDP))?;
/// sock.set_reuse_port(true)?;
/// sock.set_nonblocking(true)?;
/// sock.bind(&std_addr.into())?;
///
/// let std_socket = UdpSocket::from_std(sock.into());
/// let other_socket = UdpSocket::bind(second_addr).await?;
///
/// let buf = vec![0; 32];
///
/// // write data
/// let (result, _) = std_socket
/// .send_to(b"hello world".as_slice(), second_addr)
/// .await;
/// result.unwrap();
///
/// // read data
/// let (result, buf) = other_socket.recv_from(buf).await;
/// let (n_bytes, addr) = result.unwrap();
///
/// assert_eq!(addr, std_addr);
/// assert_eq!(b"hello world", &buf[..n_bytes]);
///
/// Ok(())
/// })
/// }
/// ```
pub fn from_std(socket: std::net::UdpSocket) -> UdpSocket {
let inner_socket = Socket::from_std(socket);
Self {
inner: inner_socket,
}
}

/// Connects this UDP socket to a remote address, allowing the `write` and
/// `read` syscalls to be used to send data and also applies filters to only
/// receive data from the specified address.
Expand Down

0 comments on commit ed7c0b3

Please sign in to comment.