Revision control

Copy as Markdown

Other Tools

//! Low-level Linux network device access
//!
//! The methods in this module take a socket's file descriptor to communicate
//! with the kernel in their ioctl call:
//! - glibc uses an `AF_UNIX`, `AF_INET`, or `AF_INET6` socket.
//! The address family itself does not matter and glibc tries the next address
//! family if socket creation with one fails.
//! - Android (bionic) uses an `AF_INET` socket.
//! - Both create the socket with `SOCK_DGRAM|SOCK_CLOEXEC` type/flag.
//! - The [man-pages] specify, that the ioctl calls "can be used on any
//! socket's file descriptor regardless of the
//! family or type".
//!
//! # References
//! - [Linux]
//!
use crate::fd::AsFd;
use crate::io;
#[cfg(feature = "alloc")]
use alloc::string::String;
/// `ioctl(fd, SIOCGIFINDEX, ifreq)`—Returns the interface index for a given
/// name.
///
/// See the [module-level documentation] for information about `fd` usage.
///
/// # References
/// - [Linux]
///
/// [module-level documentation]: self
#[inline]
#[doc(alias = "SIOCGIFINDEX")]
pub fn name_to_index(fd: impl AsFd, if_name: &str) -> io::Result<u32> {
crate::backend::net::netdevice::name_to_index(fd, if_name)
}
/// `ioctl(fd, SIOCGIFNAME, ifreq)`—Returns the interface name for a given
/// index.
///
/// See the [module-level documentation] for information about `fd` usage.
///
/// # References
/// - [Linux]
///
/// [module-level documentation]: self
#[inline]
#[doc(alias = "SIOCGIFNAME")]
#[cfg(feature = "alloc")]
pub fn index_to_name(fd: impl AsFd, index: u32) -> io::Result<String> {
crate::backend::net::netdevice::index_to_name(fd, index)
}
#[cfg(test)]
mod tests {
use crate::backend::net::netdevice::{index_to_name, name_to_index};
use crate::net::{AddressFamily, SocketFlags, SocketType};
#[test]
fn test_name_to_index() {
let fd = crate::net::socket_with(
AddressFamily::INET,
SocketType::DGRAM,
SocketFlags::CLOEXEC,
None,
)
.unwrap();
let loopback_index = std::fs::read_to_string("/sys/class/net/lo/ifindex")
.unwrap()
.as_str()
.split_at(1)
.0
.parse::<u32>()
.unwrap();
assert_eq!(Ok(loopback_index), name_to_index(fd, "lo"));
}
#[test]
#[cfg(feature = "alloc")]
fn test_index_to_name() {
let fd = crate::net::socket_with(
AddressFamily::INET,
SocketType::DGRAM,
SocketFlags::CLOEXEC,
None,
)
.unwrap();
let loopback_index = std::fs::read_to_string("/sys/class/net/lo/ifindex")
.unwrap()
.as_str()
.split_at(1)
.0
.parse::<u32>()
.unwrap();
assert_eq!(Ok("lo".to_owned()), index_to_name(fd, loopback_index));
}
}