mirror of
https://github.com/achanda/ipnetwork.git
synced 2025-06-16 16:58:50 +00:00
Compare commits
13 Commits
Author | SHA1 | Date | |
---|---|---|---|
fd452cd156 | |||
f0fd68e962 | |||
ae784fe161 | |||
ab7d5b32d0 | |||
cdd3dff549 | |||
ef378f9921 | |||
b70b551561 | |||
b442a7d598 | |||
5020a99401 | |||
24c9a24dae | |||
b3fd9f4f48 | |||
04d454b5ba | |||
f61db46006 |
@ -1,6 +1,6 @@
|
||||
[package]
|
||||
name = "ipnetwork"
|
||||
version = "0.12.2"
|
||||
version = "0.12.4"
|
||||
authors = ["Abhishek Chanda <abhishek.becs@gmail.com>", "Linus Färnstrand <faern@faern.net>"]
|
||||
description = "A library to work with IP CIDRs in Rust, heavily WIP"
|
||||
license = "Apache-2.0"
|
||||
|
@ -7,7 +7,7 @@ use common::{IpNetworkError, cidr_parts, parse_prefix, parse_addr};
|
||||
const IPV4_BITS: u8 = 32;
|
||||
|
||||
/// Represents a network range where the IP addresses are of v4
|
||||
#[derive(Debug,Clone,Copy,Hash,PartialEq,Eq)]
|
||||
#[derive(Debug,Clone,Copy,Hash,PartialEq,Eq,PartialOrd,Ord)]
|
||||
pub struct Ipv4Network {
|
||||
addr: Ipv4Addr,
|
||||
prefix: u8,
|
||||
|
@ -9,7 +9,7 @@ const IPV6_BITS: u8 = 128;
|
||||
const IPV6_SEGMENT_BITS: u8 = 16;
|
||||
|
||||
/// Represents a network range where the IP addresses are of v6
|
||||
#[derive(Debug,Clone,Copy,Hash,PartialEq,Eq)]
|
||||
#[derive(Debug,Clone,Copy,Hash,PartialEq,Eq,PartialOrd,Ord)]
|
||||
pub struct Ipv6Network {
|
||||
addr: Ipv6Addr,
|
||||
prefix: u8,
|
||||
|
47
src/lib.rs
47
src/lib.rs
@ -5,6 +5,7 @@
|
||||
#![cfg_attr(feature = "dev", plugin(clippy))]
|
||||
#![crate_type = "lib"]
|
||||
|
||||
use std::fmt;
|
||||
use std::net::IpAddr;
|
||||
|
||||
mod ipv4;
|
||||
@ -19,7 +20,7 @@ pub use common::IpNetworkError;
|
||||
|
||||
/// Represents a generic network range. This type can have two variants:
|
||||
/// the v4 and the v6 case.
|
||||
#[derive(Debug,Clone,Copy,Hash,PartialEq,Eq)]
|
||||
#[derive(Debug,Clone,Copy,Hash,PartialEq,Eq,PartialOrd,Ord)]
|
||||
pub enum IpNetwork {
|
||||
V4(Ipv4Network),
|
||||
V6(Ipv6Network),
|
||||
@ -61,14 +62,18 @@ impl IpNetwork {
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns the mask of the given `IpNetwork`
|
||||
/// Returns the mask for this `IpNetwork`.
|
||||
/// That means the `prefix` most significant bits will be 1 and the rest 0
|
||||
///
|
||||
/// # Example
|
||||
/// ```
|
||||
/// use ipnetwork::IpNetwork;
|
||||
/// use std::net::{Ipv4Addr, Ipv6Addr};
|
||||
///
|
||||
/// assert_eq!(IpNetwork::V4("10.9.0.32/16".parse().unwrap()).mask(), 16u8);
|
||||
/// assert_eq!(IpNetwork::V6("ff01::0/32".parse().unwrap()).mask(), 32u8);
|
||||
/// let v4_net: IpNetwork = "10.9.0.32/16".parse().unwrap();
|
||||
/// assert_eq!(v4_net.mask(), Ipv4Addr::new(255, 255, 0, 0));
|
||||
/// let v6_net: IpNetwork = "ff01::0/32".parse().unwrap();
|
||||
/// assert_eq!(v6_net.mask(), Ipv6Addr::new(0xffff, 0xffff, 0, 0, 0, 0, 0, 0));
|
||||
///```
|
||||
pub fn mask(&self) -> IpAddr {
|
||||
match *self {
|
||||
@ -116,30 +121,27 @@ impl IpNetwork {
|
||||
}
|
||||
}
|
||||
|
||||
/// Constructs a new `IpNetwork` from a given &str with a prefix denoting the
|
||||
/// network size. If the prefix is larger than 32 (for IPv4) or 128 (for IPv6), this
|
||||
/// will raise an `IpNetworkError::InvalidPrefix` error.
|
||||
/// Tries to parse the given string into a `IpNetwork`. Will first try to parse
|
||||
/// it as an `Ipv4Network` and if that fails as an `Ipv6Network`. If both
|
||||
/// fails it will return an `InvalidAddr` error.
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// ```
|
||||
/// use std::net::Ipv4Addr;
|
||||
/// use ipnetwork::Ipv4Network;
|
||||
/// use ipnetwork::IpNetwork;
|
||||
/// use ipnetwork::{IpNetwork, Ipv4Network};
|
||||
///
|
||||
/// let expected = IpNetwork::V4(Ipv4Network::new(Ipv4Addr::new(10, 1, 9, 32), 16).unwrap());
|
||||
/// let from_cidr: IpNetwork = "10.1.9.32/16".parse().unwrap();
|
||||
/// assert_eq!(expected.ip(), from_cidr.ip());
|
||||
/// assert_eq!(expected.prefix(), from_cidr.prefix());
|
||||
/// assert_eq!(expected, from_cidr);
|
||||
/// ```
|
||||
impl FromStr for IpNetwork {
|
||||
type Err = IpNetworkError;
|
||||
fn from_str(s: &str) -> Result<IpNetwork, IpNetworkError> {
|
||||
let v4addr: Result<Ipv4Network, IpNetworkError> = s.parse();
|
||||
let v6addr: Result<Ipv6Network, IpNetworkError> = s.parse();
|
||||
|
||||
if v4addr.is_ok() {
|
||||
Ok(IpNetwork::V4(v4addr.unwrap()))
|
||||
} else if v6addr.is_ok() {
|
||||
Ok(IpNetwork::V6(v6addr.unwrap()))
|
||||
if let Ok(net) = Ipv4Network::from_str(s) {
|
||||
Ok(IpNetwork::V4(net))
|
||||
} else if let Ok(net) = Ipv6Network::from_str(s) {
|
||||
Ok(IpNetwork::V6(net))
|
||||
} else {
|
||||
Err(IpNetworkError::InvalidAddr(s.to_string()))
|
||||
}
|
||||
@ -158,6 +160,15 @@ impl From<Ipv6Network> for IpNetwork {
|
||||
}
|
||||
}
|
||||
|
||||
impl fmt::Display for IpNetwork {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
match *self {
|
||||
IpNetwork::V4(net) => net.fmt(f),
|
||||
IpNetwork::V6(net) => net.fmt(f),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Converts a `IpAddr` network mask into a prefix.
|
||||
/// If the mask is invalid this will return an `IpNetworkError::InvalidPrefix`.
|
||||
pub fn ip_mask_to_prefix(mask: IpAddr) -> Result<u8, IpNetworkError> {
|
||||
|
Reference in New Issue
Block a user