about summary refs log tree commit diff
path: root/src/libstd
diff options
context:
space:
mode:
authorAbhishek Chanda <abhishek@cloudscaling.com>2015-04-11 23:32:30 -0700
committerAbhishek Chanda <abhishek@cloudscaling.com>2015-04-13 12:38:09 -0700
commitf60f4b7d7cde90edb248159cf5e351816cce8d8a (patch)
tree47f6f24896c9ffcbb2b0682cb47d2b6ebe4b631d /src/libstd
parent67a8f61730418768f07d8ed0f9735a31d0c5d84d (diff)
downloadrust-f60f4b7d7cde90edb248159cf5e351816cce8d8a.tar.gz
rust-f60f4b7d7cde90edb248159cf5e351816cce8d8a.zip
Fix check for globally routable IPv4 address
- Adds two more functions for broadcast address and special
  address classes reserved for documentation
- Modifies the globally routable IP check to include these
  new functions

Fixes #24314
Diffstat (limited to 'src/libstd')
-rw-r--r--src/libstd/net/addr.rs29
-rw-r--r--src/libstd/net/ip.rs29
2 files changed, 43 insertions, 15 deletions
diff --git a/src/libstd/net/addr.rs b/src/libstd/net/addr.rs
index 702b76e7d1c..05a3ca91948 100644
--- a/src/libstd/net/addr.rs
+++ b/src/libstd/net/addr.rs
@@ -615,7 +615,7 @@ mod tests {
     fn ipv4_properties() {
         fn check(octets: &[u8; 4], unspec: bool, loopback: bool,
                  private: bool, link_local: bool, global: bool,
-                 multicast: bool) {
+                 multicast: bool, broadcast: bool, documentation: bool) {
             let ip = Ipv4Addr::new(octets[0], octets[1], octets[2], octets[3]);
             assert_eq!(octets, &ip.octets());
 
@@ -625,20 +625,23 @@ mod tests {
             assert_eq!(ip.is_link_local(), link_local);
             assert_eq!(ip.is_global(), global);
             assert_eq!(ip.is_multicast(), multicast);
+            assert_eq!(ip.is_broadcast(), broadcast);
+            assert_eq!(ip.is_documentation(), documentation);
         }
 
-        //    address                unspec loopbk privt  linloc global multicast
-        check(&[0, 0, 0, 0],         true,  false, false, false, true,  false);
-        check(&[0, 0, 0, 1],         false, false, false, false, true,  false);
-        check(&[1, 0, 0, 0],         false, false, false, false, true,  false);
-        check(&[10, 9, 8, 7],        false, false, true,  false, false, false);
-        check(&[127, 1, 2, 3],       false, true,  false, false, false, false);
-        check(&[172, 31, 254, 253],  false, false, true,  false, false,  false);
-        check(&[169, 254, 253, 242], false, false, false, true,  false, false);
-        check(&[192, 168, 254, 253], false, false, true,  false, false, false);
-        check(&[224, 0, 0, 0],       false, false, false, false, true,  true);
-        check(&[239, 255, 255, 255], false, false, false, false, true,  true);
-        check(&[255, 255, 255, 255], false, false, false, false, true,  false);
+        //    address                unspec loopbk privt  linloc global multicast brdcast doc
+        check(&[0, 0, 0, 0],         true,  false, false, false, true,  false,    false,  false);
+        check(&[0, 0, 0, 1],         false, false, false, false, true,  false,    false,  false);
+        check(&[1, 0, 0, 0],         false, false, false, false, true,  false,    false,  false);
+        check(&[10, 9, 8, 7],        false, false, true,  false, false, false,    false,  false);
+        check(&[127, 1, 2, 3],       false, true,  false, false, false, false,    false,  false);
+        check(&[172, 31, 254, 253],  false, false, true,  false, false, false,    false,  false);
+        check(&[169, 254, 253, 242], false, false, false, true,  false, false,    false,  false);
+        check(&[192, 168, 254, 253], false, false, true,  false, false, false,    false,  false);
+        check(&[224, 0, 0, 0],       false, false, false, false, true,  true,     false,  false);
+        check(&[239, 255, 255, 255], false, false, false, false, true,  true,     false,  false);
+        check(&[255, 255, 255, 255], false, false, false, false, false, false,    true,  false);
+        check(&[198, 51, 100, 0],    false, false, false, false, false, false,    false,  true);
     }
 
     #[test]
diff --git a/src/libstd/net/ip.rs b/src/libstd/net/ip.rs
index c8b19287477..a8608378e3f 100644
--- a/src/libstd/net/ip.rs
+++ b/src/libstd/net/ip.rs
@@ -115,9 +115,11 @@ impl Ipv4Addr {
     ///
     /// Non-globally-routable networks include the private networks (10.0.0.0/8,
     /// 172.16.0.0/12 and 192.168.0.0/16), the loopback network (127.0.0.0/8),
-    /// and the link-local network (169.254.0.0/16).
+    /// the link-local network (169.254.0.0/16), the broadcast address (255.255.255.255/32) and
+    /// the test networks used for documentation (192.0.2.0/24, 198.51.100.0/24 and 203.0.113.0/24)
     pub fn is_global(&self) -> bool {
-        !self.is_private() && !self.is_loopback() && !self.is_link_local()
+        !self.is_private() && !self.is_loopback() && !self.is_link_local() &&
+        !self.is_broadcast() && !self.is_documentation()
     }
 
     /// Returns true if this is a multicast address.
@@ -127,6 +129,29 @@ impl Ipv4Addr {
         self.octets()[0] >= 224 && self.octets()[0] <= 239
     }
 
+    /// Returns true if this is a broadcast address.
+    ///
+    /// A broadcast address has all octets set to 255 as defined in RFC 919
+    pub fn is_broadcast(&self) -> bool {
+        self.octets()[0] == 255 && self.octets()[1] == 255 &&
+        self.octets()[2] == 255 && self.octets()[3] == 255
+    }
+
+    /// Returns true if this address is in a range designated for documentation
+    ///
+    /// This is defined in RFC 5737
+    /// - 192.0.2.0/24 (TEST-NET-1)
+    /// - 198.51.100.0/24 (TEST-NET-2)
+    /// - 203.0.113.0/24 (TEST-NET-3)
+    pub fn is_documentation(&self) -> bool {
+        match(self.octets()[0], self.octets()[1], self.octets()[2], self.octets()[3]) {
+            (192, _, 2, _) => true,
+            (198, 51, 100, _) => true,
+            (203, _, 113, _) => true,
+            _ => false
+        }
+    }
+
     /// Convert this address to an IPv4-compatible IPv6 address
     ///
     /// a.b.c.d becomes ::a.b.c.d