cidr/
traits.rs

1use crate::{
2	errors::{
3		InetTupleError,
4		NetworkLengthTooLongError,
5		NetworkParseError,
6	},
7	internal_traits::{
8		PrivCidr,
9		PrivInet,
10		PrivInetPair,
11		PrivUnspecAddress,
12	},
13	Family,
14	InetIterator,
15};
16use core::{
17	fmt::Debug,
18	hash::Hash,
19};
20
21/// Maps IP address type to other types based on this address type
22///
23/// Implemented for [`IPv4Addr`], [`IPv6Addr`] and [`IpAddr`].
24///
25/// [`Ipv4Addr`]: std::net::Ipv4Addr
26/// [`Ipv6Addr`]: std::net::Ipv6Addr
27/// [`IpAddr`]: std::net::IpAddr
28pub trait Address: Copy + Debug + Ord + Hash + PrivUnspecAddress {
29	/// Corresponding [`Inet`] type (representing an address + a network
30	/// containing it)
31	type Inet: Inet<Address = Self>;
32
33	/// Corresponding [`Cidr`] type (representing only a network, not a specific
34	/// address within)
35	type Cidr: Cidr<Address = Self>;
36
37	/// Corresponding [`InetPair`] type (representing two addresses in the same network)
38	type InetPair: InetPair<Address = Self>;
39}
40
41/// Types implementing [`Cidr`] represent IP networks.  An IP network in
42/// this case is a set of IP addresses which share a common prefix (when
43/// viewed as a bitstring).  The length of this prefix is called
44/// `network_length`.
45///
46/// In the standard representation the network is identified by the
47/// first address and the network length, separated by a '/'.
48///
49/// The parsers will expect the input in the same format, i.e. only the
50/// first address of the network is accepted.
51///
52/// The first network length bits in an address representing the network
53/// are the network part, the remaining bits are the host part.
54/// Requiring an address to be the first in a network is equivalent to
55/// requiring the host part being zero.
56pub trait Cidr: Copy + Debug + Ord + Hash + PrivCidr {
57	/// Type for the underlying address ([`IpAddr`], [`Ipv4Addr`] or
58	/// [`Ipv6Addr`]).
59	///
60	/// [`Ipv4Addr`]: std::net::Ipv4Addr
61	/// [`Ipv6Addr`]: std::net::Ipv6Addr
62	/// [`IpAddr`]: std::net::IpAddr
63	type Address: Address<Cidr = Self>;
64
65	/// Create new network from address and prefix length.  If the
66	/// network length exceeds the address length or the address is not
67	/// the first address in the network ("host part not zero") an
68	/// error is returned.
69	fn new(addr: Self::Address, len: u8) -> Result<Self, NetworkParseError>;
70
71	/// Create a network containing a single address (network length =
72	/// address length).
73	fn new_host(addr: Self::Address) -> Self;
74
75	/// Iterate over all addresses in the range.  With IPv6 addresses
76	/// this can produce really long iterations (up to 2<sup>128</sup>
77	/// addresses).
78	fn iter(&self) -> InetIterator<Self::Address>;
79
80	/// first address in the network as plain address
81	fn first_address(&self) -> Self::Address;
82	/// first address in the network
83	fn first(&self) -> <Self::Address as Address>::Inet;
84	/// last address in the network as plain address
85	fn last_address(&self) -> Self::Address;
86	/// last address in the network
87	fn last(&self) -> <Self::Address as Address>::Inet;
88	/// length in bits of the shared prefix of the contained addresses
89	fn network_length(&self) -> u8;
90	/// IP family of the contained address ([`Ipv4`] or [`Ipv6`]).
91	///
92	/// [`Ipv4`]: Family::Ipv4
93	/// [`Ipv6`]: Family::Ipv6
94	fn family(&self) -> Family;
95
96	/// whether network represents a single host address
97	fn is_host_address(&self) -> bool;
98
99	/// network mask: an pseudo address which has the first `network
100	/// length` bits set to 1 and the remaining to 0.
101	fn mask(&self) -> Self::Address;
102
103	/// check whether an address is contained in the network
104	fn contains(&self, addr: &Self::Address) -> bool;
105}
106
107/// Types implementing Inet represent IP hosts within networks.
108///
109/// In addition to the network represented by the corresponding [`Cidr`]
110/// type, an [`Inet`] type also stores a single host address which is part
111/// of the network.
112///
113/// The host address is not really stored as separate data, but is
114/// stored together with the network address.
115///
116/// The representation of a [`Inet`] type is similar to that of the
117/// corresponding [`Cidr`] type, but uses the host address instead of the
118/// first address of the network.
119pub trait Inet: Copy + Debug + Ord + Hash + PrivInet {
120	/// Type for the underlying address ([`IpAddr`], [`Ipv4Addr`] or
121	/// [`Ipv6Addr`]).
122	///
123	/// [`Ipv4Addr`]: std::net::Ipv4Addr
124	/// [`Ipv6Addr`]: std::net::Ipv6Addr
125	/// [`IpAddr`]: std::net::IpAddr
126	type Address: Address<Inet = Self>;
127
128	/// Create new host within a network from address and prefix length.
129	/// If the network length exceeds the address length an error is
130	/// returned.
131	fn new(addr: Self::Address, len: u8) -> Result<Self, NetworkLengthTooLongError>;
132
133	/// Create a network containing a single address as host and the
134	/// network (network length = address length).
135	fn new_host(addr: Self::Address) -> Self;
136
137	/// increments host part (without changing the network part);
138	/// returns true on wrap around
139	fn increment(&mut self) -> bool;
140
141	/// Returns next address in network or `None` if it was the last address in the network
142	fn next(self) -> Option<Self>;
143
144	/// decrements host part (without changing the network part);
145	/// returns true on wrap around
146	fn decrement(&mut self) -> bool;
147
148	/// Returns previous address in network or `None` if it was the first address in the network
149	fn previous(self) -> Option<Self>;
150
151	/// Find the nth host after the current one in the current network
152	///
153	/// Returned boolean indicates whether an overflow occured.
154	fn overflowing_add(self, step: u128) -> (Self, bool);
155
156	/// Find the nth host before the current one in the current network
157	///
158	/// Returned boolean indicates whether an overflow occured.
159	fn overflowing_sub(self, step: u128) -> (Self, bool);
160
161	/// network (i.e. drops the host information)
162	fn network(&self) -> <Self::Address as Address>::Cidr;
163
164	/// the host
165	fn address(&self) -> Self::Address;
166
167	/// first address in the network as plain address
168	fn first_address(&self) -> Self::Address;
169	/// first address in the network
170	fn first(&self) -> Self;
171	/// last address in the network as plain address
172	fn last_address(&self) -> Self::Address;
173	/// last address in the network
174	fn last(&self) -> Self;
175	/// length in bits of the shared prefix of the contained addresses
176	fn network_length(&self) -> u8;
177	/// IP family of the contained address ([`Ipv4`] or [`Ipv6`]).
178	///
179	/// [`Ipv4`]: Family::Ipv4
180	/// [`Ipv6`]: Family::Ipv6
181	fn family(&self) -> Family;
182
183	/// whether network represents a single host address
184	fn is_host_address(&self) -> bool;
185
186	/// network mask: an pseudo address which has the first `network
187	/// length` bits set to 1 and the remaining to 0.
188	fn mask(&self) -> Self::Address;
189
190	/// check whether an address is contained in the network
191	fn contains(&self, addr: &Self::Address) -> bool;
192}
193
194/// Pair of two addresses in the same network
195pub trait InetPair: Copy + Debug + Eq + Hash + PrivInetPair {
196	/// Type for the underlying address ([`IpAddr`], [`Ipv4Addr`] or
197	/// [`Ipv6Addr`]).
198	///
199	/// [`Ipv4Addr`]: std::net::Ipv4Addr
200	/// [`Ipv6Addr`]: std::net::Ipv6Addr
201	/// [`IpAddr`]: std::net::IpAddr
202	type Address: Address<InetPair = Self>;
203
204	/// Create new pair from two addresses in the same network
205	///
206	/// Fails if the addresses are not in the same network.
207	fn new(
208		first: <Self::Address as Address>::Inet,
209		second: <Self::Address as Address>::Inet,
210	) -> Result<Self, InetTupleError>;
211
212	/// Create new pair from two addresses and a common length
213	///
214	/// Fails if the network length is invalid for the addresses or the addresses are not in the same network.
215	fn new_from_addresses(
216		first: Self::Address,
217		second: Self::Address,
218		len: u8,
219	) -> Result<Self, InetTupleError>;
220
221	/// First address
222	fn first(&self) -> <Self::Address as Address>::Inet;
223
224	/// Second address
225	fn second(&self) -> <Self::Address as Address>::Inet;
226
227	/// network (i.e. drops the host information)
228	fn network(&self) -> <Self::Address as Address>::Cidr;
229
230	/// length in bits of the shared prefix of the contained addresses
231	fn network_length(&self) -> u8;
232
233	/// IP family of the contained address ([`Ipv4`] or [`Ipv6`]).
234	///
235	/// [`Ipv4`]: Family::Ipv4
236	/// [`Ipv6`]: Family::Ipv6
237	fn family(&self) -> Family;
238
239	/// Iterate over `first..=second` (inclusive)
240	fn iter(self) -> InetIterator<Self::Address>;
241}