Skip to content

Commit 322fa3e

Browse files
Merge pull request #1582 from rust-osdev/bishop-core-ip-conv
uefi-raw: Add conversions to/from core::net IP address types
2 parents 6fed32e + dd6750f commit 322fa3e

File tree

3 files changed

+76
-1
lines changed

3 files changed

+76
-1
lines changed

uefi-raw/CHANGELOG.md

+3
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,12 @@
11
# uefi-raw - [Unreleased]
22

33
## Added
4+
- MSRV increased to 1.77.
45
- Added `Boolean` type
56
- Added `protocol::network::pxe` module.
67
- Added conversions between `MacAddress` and the `[u8; 6]` type that's more commonly used to represent MAC addresses.
8+
- Implemented `From` conversions between the `core::net` and `uefi_raw` IP
9+
address types.
710
- Added `DiskInfoProtocol`.
811
- Added `ExtScsiPassThruProtocol`.
912

uefi-raw/Cargo.toml

+1-1
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ license.workspace = true
1616
repository.workspace = true
1717
# uefi-raw is much less likely to need the latest bleeding-edge features.
1818
# Hence, it is okay to not use the workspace MSRV.
19-
rust-version = "1.70"
19+
rust-version = "1.77"
2020

2121
[dependencies]
2222
bitflags.workspace = true

uefi-raw/src/lib.rs

+72
Original file line numberDiff line numberDiff line change
@@ -111,11 +111,35 @@ impl From<Boolean> for bool {
111111
#[repr(transparent)]
112112
pub struct Ipv4Address(pub [u8; 4]);
113113

114+
impl From<core::net::Ipv4Addr> for Ipv4Address {
115+
fn from(ip: core::net::Ipv4Addr) -> Self {
116+
Self(ip.octets())
117+
}
118+
}
119+
120+
impl From<Ipv4Address> for core::net::Ipv4Addr {
121+
fn from(ip: Ipv4Address) -> Self {
122+
Self::from(ip.0)
123+
}
124+
}
125+
114126
/// An IPv6 internet protocol address.
115127
#[derive(Clone, Copy, Debug, Default, Eq, PartialEq, Ord, PartialOrd, Hash)]
116128
#[repr(transparent)]
117129
pub struct Ipv6Address(pub [u8; 16]);
118130

131+
impl From<core::net::Ipv6Addr> for Ipv6Address {
132+
fn from(ip: core::net::Ipv6Addr) -> Self {
133+
Self(ip.octets())
134+
}
135+
}
136+
137+
impl From<Ipv6Address> for core::net::Ipv6Addr {
138+
fn from(ip: Ipv6Address) -> Self {
139+
Self::from(ip.0)
140+
}
141+
}
142+
119143
/// An IPv4 or IPv6 internet protocol address.
120144
///
121145
/// Corresponds to the `EFI_IP_ADDRESS` type in the UEFI specification. This
@@ -170,6 +194,19 @@ impl Default for IpAddress {
170194
}
171195
}
172196

197+
impl From<core::net::IpAddr> for IpAddress {
198+
fn from(t: core::net::IpAddr) -> Self {
199+
match t {
200+
core::net::IpAddr::V4(ip) => Self {
201+
v4: Ipv4Address::from(ip),
202+
},
203+
core::net::IpAddr::V6(ip) => Self {
204+
v6: Ipv6Address::from(ip),
205+
},
206+
}
207+
}
208+
}
209+
173210
/// A Media Access Control (MAC) address.
174211
#[derive(Clone, Copy, Debug, Default, Eq, PartialEq, Ord, PartialOrd, Hash)]
175212
#[repr(transparent)]
@@ -198,6 +235,11 @@ impl From<MacAddress> for [u8; 6] {
198235
mod tests {
199236
use super::*;
200237

238+
const TEST_IPV4: [u8; 4] = [91, 92, 93, 94];
239+
const TEST_IPV6: [u8; 16] = [
240+
101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116,
241+
];
242+
201243
#[test]
202244
/// Test the properties promised in [0]. This also applies for the other
203245
/// architectures.
@@ -215,4 +257,34 @@ mod tests {
215257
assert!(bool::from(Boolean(0b11111110)));
216258
assert!(bool::from(Boolean(0b11111111)));
217259
}
260+
261+
/// Test round-trip conversion between `Ipv4Address` and `core::net::Ipv4Addr`.
262+
#[test]
263+
fn test_ip_addr4_conversion() {
264+
let uefi_addr = Ipv4Address(TEST_IPV4);
265+
let core_addr = core::net::Ipv4Addr::from(uefi_addr);
266+
assert_eq!(uefi_addr, Ipv4Address::from(core_addr));
267+
}
268+
269+
/// Test round-trip conversion between `Ipv6Address` and `core::net::Ipv6Addr`.
270+
#[test]
271+
fn test_ip_addr6_conversion() {
272+
let uefi_addr = Ipv6Address(TEST_IPV6);
273+
let core_addr = core::net::Ipv6Addr::from(uefi_addr);
274+
assert_eq!(uefi_addr, Ipv6Address::from(core_addr));
275+
}
276+
277+
/// Test conversion from `core::net::IpAddr` to `IpvAddress`.
278+
///
279+
/// Note that conversion in the other direction is not possible.
280+
#[test]
281+
fn test_ip_addr_conversion() {
282+
let core_addr = core::net::IpAddr::V4(core::net::Ipv4Addr::from(TEST_IPV4));
283+
let uefi_addr = IpAddress::from(core_addr);
284+
assert_eq!(unsafe { uefi_addr.v4.0 }, TEST_IPV4);
285+
286+
let core_addr = core::net::IpAddr::V6(core::net::Ipv6Addr::from(TEST_IPV6));
287+
let uefi_addr = IpAddress::from(core_addr);
288+
assert_eq!(unsafe { uefi_addr.v6.0 }, TEST_IPV6);
289+
}
218290
}

0 commit comments

Comments
 (0)