@@ -13,6 +13,13 @@ use core::mem;
13
13
use core:: net:: { IpAddr as StdIpAddr , Ipv4Addr as StdIpv4Addr , Ipv6Addr as StdIpv6Addr } ;
14
14
15
15
/// An IPv4 internet protocol address.
16
+ ///
17
+ /// # Conversions and Relation to [`core::net`]
18
+ ///
19
+ /// The following [`From`] implementations exist:
20
+ /// - `[u8; 4]` -> [`Ipv4Address`]
21
+ /// - [`core::net::Ipv4Addr`] -> [`Ipv4Address`]
22
+ /// - [`core::net::IpAddr`] -> [`Ipv4Address`]
16
23
#[ derive( Clone , Copy , Debug , Default , Eq , PartialEq , Ord , PartialOrd , Hash ) ]
17
24
#[ repr( transparent) ]
18
25
pub struct Ipv4Address ( pub [ u8 ; 4 ] ) ;
@@ -37,7 +44,20 @@ impl From<Ipv4Address> for StdIpv4Addr {
37
44
}
38
45
}
39
46
47
+ impl From < [ u8 ; 4 ] > for Ipv4Address {
48
+ fn from ( octets : [ u8 ; 4 ] ) -> Self {
49
+ Self ( octets)
50
+ }
51
+ }
52
+
40
53
/// An IPv6 internet protocol address.
54
+ ///
55
+ /// # Conversions and Relation to [`core::net`]
56
+ ///
57
+ /// The following [`From`] implementations exist:
58
+ /// - `[u8; 16]` -> [`Ipv6Address`]
59
+ /// - [`core::net::Ipv6Addr`] -> [`Ipv6Address`]
60
+ /// - [`core::net::IpAddr`] -> [`Ipv6Address`]
41
61
#[ derive( Clone , Copy , Debug , Default , Eq , PartialEq , Ord , PartialOrd , Hash ) ]
42
62
#[ repr( transparent) ]
43
63
pub struct Ipv6Address ( pub [ u8 ; 16 ] ) ;
@@ -62,12 +82,27 @@ impl From<Ipv6Address> for StdIpv6Addr {
62
82
}
63
83
}
64
84
65
- /// An IPv4 or IPv6 internet protocol address that is ABI compatible with EFI.
85
+ impl From < [ u8 ; 16 ] > for Ipv6Address {
86
+ fn from ( octets : [ u8 ; 16 ] ) -> Self {
87
+ Self ( octets)
88
+ }
89
+ }
90
+
91
+ /// EFI ABI-compatible union of an IPv4 or IPv6 internet protocol address.
66
92
///
67
93
/// Corresponds to the `EFI_IP_ADDRESS` type in the UEFI specification. This
68
94
/// type is defined in the same way as edk2 for compatibility with C code. Note
69
95
/// that this is an untagged union, so there's no way to tell which type of
70
96
/// address an `IpAddress` value contains without additional context.
97
+ ///
98
+ /// # Conversions and Relation to [`core::net`]
99
+ ///
100
+ /// The following [`From`] implementations exist:
101
+ /// - `[u8; 4]` -> [`IpAddress`]
102
+ /// - `[u8; 16]` -> [`IpAddress`]
103
+ /// - [`core::net::Ipv4Addr`] -> [`IpAddress`]
104
+ /// - [`core::net::Ipv6Addr`] -> [`IpAddress`]
105
+ /// - [`core::net::IpAddr`] -> [`IpAddress`]
71
106
#[ derive( Clone , Copy ) ]
72
107
#[ repr( C ) ]
73
108
pub union IpAddress {
@@ -162,6 +197,30 @@ impl From<StdIpAddr> for IpAddress {
162
197
}
163
198
}
164
199
200
+ impl From < StdIpv4Addr > for IpAddress {
201
+ fn from ( value : StdIpv4Addr ) -> Self {
202
+ Self :: new_v4 ( value. octets ( ) )
203
+ }
204
+ }
205
+
206
+ impl From < StdIpv6Addr > for IpAddress {
207
+ fn from ( value : StdIpv6Addr ) -> Self {
208
+ Self :: new_v6 ( value. octets ( ) )
209
+ }
210
+ }
211
+
212
+ impl From < [ u8 ; 4 ] > for IpAddress {
213
+ fn from ( octets : [ u8 ; 4 ] ) -> Self {
214
+ Self :: new_v4 ( octets)
215
+ }
216
+ }
217
+
218
+ impl From < [ u8 ; 16 ] > for IpAddress {
219
+ fn from ( octets : [ u8 ; 16 ] ) -> Self {
220
+ Self :: new_v6 ( octets)
221
+ }
222
+ }
223
+
165
224
/// UEFI Media Access Control (MAC) address.
166
225
///
167
226
/// UEFI supports multiple network protocols and hardware types, not just
@@ -171,6 +230,13 @@ impl From<StdIpAddr> for IpAddress {
171
230
///
172
231
/// In most cases, this is just a typical `[u8; 6]` Ethernet style MAC
173
232
/// address with the rest of the bytes being zero.
233
+ ///
234
+ /// # Conversions and Relation to [`core::net`]
235
+ ///
236
+ /// There is no matching type in [`core::net`] but the following [`From`]
237
+ /// implementations exist:
238
+ /// - `[u8; 6]` -> [`MacAddress`]
239
+ /// - `[u8; 32]` -> [`MacAddress`]
174
240
#[ derive( Clone , Copy , Debug , Default , Eq , PartialEq , Ord , PartialOrd , Hash ) ]
175
241
#[ repr( transparent) ]
176
242
pub struct MacAddress ( pub [ u8 ; 32 ] ) ;
@@ -192,9 +258,10 @@ impl From<[u8; 6]> for MacAddress {
192
258
}
193
259
}
194
260
195
- impl From < MacAddress > for [ u8 ; 6 ] {
196
- fn from ( MacAddress ( o) : MacAddress ) -> Self {
197
- [ o[ 0 ] , o[ 1 ] , o[ 2 ] , o[ 3 ] , o[ 4 ] , o[ 5 ] ]
261
+ // UEFI MAC addresses.
262
+ impl From < [ u8 ; 32 ] > for MacAddress {
263
+ fn from ( octets : [ u8 ; 32 ] ) -> Self {
264
+ Self ( octets)
198
265
}
199
266
}
200
267
@@ -236,4 +303,64 @@ mod tests {
236
303
let uefi_addr = IpAddress :: from ( core_addr) ;
237
304
assert_eq ! ( unsafe { uefi_addr. v6. 0 } , TEST_IPV6 ) ;
238
305
}
306
+
307
+ /// Tests the From-impls from the documentation.
308
+ #[ test]
309
+ fn test_promised_from_impls ( ) {
310
+ // octets -> Ipv4Address
311
+ {
312
+ let octets = [ 0_u8 , 1 , 2 , 3 ] ;
313
+ assert_eq ! ( Ipv4Address :: from( octets) , Ipv4Address ( octets) ) ;
314
+ let uefi_addr = IpAddress :: from ( octets) ;
315
+ assert_eq ! ( & octets, & unsafe { uefi_addr. octets( ) } [ 0 ..4 ] ) ;
316
+ }
317
+ // octets -> Ipv6Address
318
+ {
319
+ let octets = [ 0_u8 , 1 , 2 , 3 , 4 , 5 , 6 , 7 , 8 , 9 , 10 , 11 , 12 , 13 , 14 , 15 ] ;
320
+ assert_eq ! ( Ipv6Address :: from( octets) , Ipv6Address ( octets) ) ;
321
+ let uefi_addr = IpAddress :: from ( octets) ;
322
+ assert_eq ! ( & octets, & unsafe { uefi_addr. octets( ) } ) ;
323
+ }
324
+ // StdIpv4Addr -> Ipv4Address
325
+ {
326
+ let octets = [ 7 , 5 , 3 , 1 ] ;
327
+ let core_ipv4_addr = StdIpv4Addr :: from ( octets) ;
328
+ assert_eq ! ( Ipv4Address :: from( core_ipv4_addr) . octets( ) , octets) ;
329
+ assert_eq ! (
330
+ unsafe { IpAddress :: from( core_ipv4_addr) . octets( ) } [ 0 ..4 ] ,
331
+ octets
332
+ ) ;
333
+ }
334
+ // StdIpv6Addr -> Ipv6Address
335
+ {
336
+ let octets = [ 7 , 5 , 3 , 1 , 6 , 3 , 8 , 5 , 2 , 5 , 2 , 7 , 3 , 5 , 2 , 6 ] ;
337
+ let core_ipv6_addr = StdIpv6Addr :: from ( octets) ;
338
+ assert_eq ! ( Ipv6Address :: from( core_ipv6_addr) . octets( ) , octets) ;
339
+ assert_eq ! ( unsafe { IpAddress :: from( core_ipv6_addr) . octets( ) } , octets) ;
340
+ }
341
+ // StdIpAddr -> IpAddress
342
+ {
343
+ let octets = [ 8 , 8 , 2 , 6 ] ;
344
+ let core_ip_addr = StdIpAddr :: from ( octets) ;
345
+ assert_eq ! (
346
+ unsafe { IpAddress :: from( core_ip_addr) . octets( ) } [ 0 ..4 ] ,
347
+ octets
348
+ ) ;
349
+ }
350
+ // octets -> MacAddress
351
+ {
352
+ let octets = [ 8 , 8 , 2 , 6 , 6 , 7 ] ;
353
+ let uefi_mac_addr = MacAddress :: from ( octets) ;
354
+ assert_eq ! ( uefi_mac_addr. octets( ) [ 0 ..6 ] , octets) ;
355
+ }
356
+ // octets -> MacAddress
357
+ {
358
+ let octets = [
359
+ 8_u8 , 8 , 2 , 6 , 6 , 7 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 5 , 7 , 0 , 0 , 0 ,
360
+ 0 , 0 , 0 , 0 , 42 ,
361
+ ] ;
362
+ let uefi_mac_addr = MacAddress :: from ( octets) ;
363
+ assert_eq ! ( uefi_mac_addr. octets( ) , octets) ;
364
+ }
365
+ }
239
366
}
0 commit comments