From 813ce7a688f716e53f3dd22a89ec059af3b67c13 Mon Sep 17 00:00:00 2001
From: Nathan West <Lucretiel@gmail.com>
Date: Wed, 20 May 2020 15:21:24 -0400
Subject: [PATCH 1/3] `SocketAddr(V4|V6)?`::Display now correctly pads its
 content

IpAddr and friends pad when displaying; SocketAddr now does this as well
---
 src/libstd/net/addr.rs | 30 +++++++++++++++++++++++++++---
 1 file changed, 27 insertions(+), 3 deletions(-)

diff --git a/src/libstd/net/addr.rs b/src/libstd/net/addr.rs
index 08536de4d55c3..8870c405a2674 100644
--- a/src/libstd/net/addr.rs
+++ b/src/libstd/net/addr.rs
@@ -2,7 +2,7 @@ use crate::cmp::Ordering;
 use crate::convert::TryInto;
 use crate::fmt;
 use crate::hash;
-use crate::io;
+use crate::io::{self, Write};
 use crate::iter;
 use crate::mem;
 use crate::net::{htons, ntohs, IpAddr, Ipv4Addr, Ipv6Addr};
@@ -600,7 +600,17 @@ impl fmt::Display for SocketAddr {
 #[stable(feature = "rust1", since = "1.0.0")]
 impl fmt::Display for SocketAddrV4 {
     fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
-        write!(f, "{}:{}", self.ip(), self.port())
+        const IPV4_SOCKET_BUF_LEN: usize = 21;
+        let mut buf = [0; IPV4_SOCKET_BUF_LEN];
+        let mut buf_slice = &mut buf[..];
+
+        // Unwrap is fine because writing to a buffer is infallible
+        write!(buf_slice, "{}:{}", self.ip(), self.port()).unwrap();
+        let len = IPV4_SOCKET_BUF_LEN - buf_slice.len();
+
+        // This unsafe is OK because we know what is being written to the buffer
+        let buf = unsafe { crate::str::from_utf8_unchecked(&buf[..len]) };
+        f.pad(buf)
     }
 }
 
@@ -614,7 +624,21 @@ impl fmt::Debug for SocketAddrV4 {
 #[stable(feature = "rust1", since = "1.0.0")]
 impl fmt::Display for SocketAddrV6 {
     fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
-        write!(f, "[{}]:{}", self.ip(), self.port())
+        const IPV6_SOCKET_BUF_LEN: usize = (4 * 8)  // The address
+            + 7  // The colon separators
+            + 2  // The brackets
+            + 1 + 5; // The port
+
+        let mut buf = [0; IPV6_SOCKET_BUF_LEN];
+        let mut buf_slice = &mut buf[..];
+
+        // Unwrap is fine because writing to a buffer is infallible
+        write!(buf_slice, "[{}]:{}", self.ip(), self.port()).unwrap();
+        let len = IPV6_SOCKET_BUF_LEN - buf_slice.len();
+
+        // This unsafe is OK because we know what is being written to the buffer
+        let buf = unsafe { crate::str::from_utf8_unchecked(&buf[..len]) };
+        f.pad(buf)
     }
 }
 

From defbd845a33cf3c61c3af77aae474964f92e34bb Mon Sep 17 00:00:00 2001
From: Nathan West <Lucretiel@gmail.com>
Date: Wed, 20 May 2020 16:29:36 -0400
Subject: [PATCH 2/3] Added fast-path, tests

---
 src/libstd/net/addr.rs | 74 ++++++++++++++++++++++++++++++------------
 1 file changed, 54 insertions(+), 20 deletions(-)

diff --git a/src/libstd/net/addr.rs b/src/libstd/net/addr.rs
index 8870c405a2674..2febe157a506d 100644
--- a/src/libstd/net/addr.rs
+++ b/src/libstd/net/addr.rs
@@ -600,17 +600,23 @@ impl fmt::Display for SocketAddr {
 #[stable(feature = "rust1", since = "1.0.0")]
 impl fmt::Display for SocketAddrV4 {
     fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
-        const IPV4_SOCKET_BUF_LEN: usize = 21;
-        let mut buf = [0; IPV4_SOCKET_BUF_LEN];
-        let mut buf_slice = &mut buf[..];
-
-        // Unwrap is fine because writing to a buffer is infallible
-        write!(buf_slice, "{}:{}", self.ip(), self.port()).unwrap();
-        let len = IPV4_SOCKET_BUF_LEN - buf_slice.len();
-
-        // This unsafe is OK because we know what is being written to the buffer
-        let buf = unsafe { crate::str::from_utf8_unchecked(&buf[..len]) };
-        f.pad(buf)
+        // Fast path: if there's no alignment stuff, write to the output buffer
+        // directly
+        if f.precision().is_none() && f.width().is_none() {
+            write!(f, "{}:{}", self.ip(), self.port())
+        } else {
+            const IPV4_SOCKET_BUF_LEN: usize = 21;
+            let mut buf = [0; IPV4_SOCKET_BUF_LEN];
+            let mut buf_slice = &mut buf[..];
+
+            // Unwrap is fine because writing to a buffer is infallible
+            write!(buf_slice, "{}:{}", self.ip(), self.port()).unwrap();
+            let len = IPV4_SOCKET_BUF_LEN - buf_slice.len();
+
+            // This unsafe is OK because we know what is being written to the buffer
+            let buf = unsafe { crate::str::from_utf8_unchecked(&buf[..len]) };
+            f.pad(buf)
+        }
     }
 }
 
@@ -624,21 +630,27 @@ impl fmt::Debug for SocketAddrV4 {
 #[stable(feature = "rust1", since = "1.0.0")]
 impl fmt::Display for SocketAddrV6 {
     fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
-        const IPV6_SOCKET_BUF_LEN: usize = (4 * 8)  // The address
+        // Fast path: if there's no alignment stuff, write to the output
+        // buffer directly
+        if f.precision().is_none() && f.width().is_none() {
+            write!(f, "[{}]:{}", self.ip(), self.port())
+        } else {
+            const IPV6_SOCKET_BUF_LEN: usize = (4 * 8)  // The address
             + 7  // The colon separators
             + 2  // The brackets
             + 1 + 5; // The port
 
-        let mut buf = [0; IPV6_SOCKET_BUF_LEN];
-        let mut buf_slice = &mut buf[..];
+            let mut buf = [0; IPV6_SOCKET_BUF_LEN];
+            let mut buf_slice = &mut buf[..];
 
-        // Unwrap is fine because writing to a buffer is infallible
-        write!(buf_slice, "[{}]:{}", self.ip(), self.port()).unwrap();
-        let len = IPV6_SOCKET_BUF_LEN - buf_slice.len();
+            // Unwrap is fine because writing to a buffer is infallible
+            write!(buf_slice, "[{}]:{}", self.ip(), self.port()).unwrap();
+            let len = IPV6_SOCKET_BUF_LEN - buf_slice.len();
 
-        // This unsafe is OK because we know what is being written to the buffer
-        let buf = unsafe { crate::str::from_utf8_unchecked(&buf[..len]) };
-        f.pad(buf)
+            // This unsafe is OK because we know what is being written to the buffer
+            let buf = unsafe { crate::str::from_utf8_unchecked(&buf[..len]) };
+            f.pad(buf)
+        }
     }
 }
 
@@ -1192,6 +1204,28 @@ mod tests {
         assert!(v6.is_ipv6());
     }
 
+    #[test]
+    fn socket_v4_to_str() {
+        let socket = SocketAddrV4::new(Ipv4Addr::new(192, 168, 0, 1), 8080);
+
+        assert_eq!(format!("{}", socket), "192.168.0.1:8080");
+        assert_eq!(format!("{:<20}", socket), "192.168.0.1:8080    ");
+        assert_eq!(format!("{:>20}", socket), "    192.168.0.1:8080");
+        assert_eq!(format!("{:^20}", socket), "  192.168.0.1:8080  ");
+        assert_eq!(format!("{:.10}", socket), "192.168.0.");
+    }
+
+    #[test]
+    fn socket_v6_to_str() {
+        let socket: SocketAddrV6 = "[2a02:6b8:0:1::1]:53".parse().unwrap();
+
+        assert_eq!(format!("{}", socket), "[2a02:6b8:0:1::1]:53");
+        assert_eq!(format!("{:<24}", socket), "[2a02:6b8:0:1::1]:53    ");
+        assert_eq!(format!("{:>24}", socket), "    [2a02:6b8:0:1::1]:53");
+        assert_eq!(format!("{:^24}", socket), "  [2a02:6b8:0:1::1]:53  ");
+        assert_eq!(format!("{:.15}", socket), "[2a02:6b8:0:1::");
+    }
+
     #[test]
     fn compare() {
         let v4_1 = "224.120.45.1:23456".parse::<SocketAddrV4>().unwrap();

From 06a97a027a21f6fe67f91b0630291fbb62d2de83 Mon Sep 17 00:00:00 2001
From: Nathan West <Lucretiel@gmail.com>
Date: Fri, 22 May 2020 15:59:38 -0400
Subject: [PATCH 3/3] Clarify comment message & MAX_LENGTH const

---
 src/libstd/net/addr.rs | 10 +++++++---
 1 file changed, 7 insertions(+), 3 deletions(-)

diff --git a/src/libstd/net/addr.rs b/src/libstd/net/addr.rs
index 2febe157a506d..b780340884e1f 100644
--- a/src/libstd/net/addr.rs
+++ b/src/libstd/net/addr.rs
@@ -605,11 +605,14 @@ impl fmt::Display for SocketAddrV4 {
         if f.precision().is_none() && f.width().is_none() {
             write!(f, "{}:{}", self.ip(), self.port())
         } else {
-            const IPV4_SOCKET_BUF_LEN: usize = 21;
+            const IPV4_SOCKET_BUF_LEN: usize = (3 * 4)  // the segments
+                + 3  // the separators
+                + 1 + 5; // the port
             let mut buf = [0; IPV4_SOCKET_BUF_LEN];
             let mut buf_slice = &mut buf[..];
 
-            // Unwrap is fine because writing to a buffer is infallible
+            // Unwrap is fine because writing to a sufficiently-sized
+            // buffer is infallible
             write!(buf_slice, "{}:{}", self.ip(), self.port()).unwrap();
             let len = IPV4_SOCKET_BUF_LEN - buf_slice.len();
 
@@ -643,7 +646,8 @@ impl fmt::Display for SocketAddrV6 {
             let mut buf = [0; IPV6_SOCKET_BUF_LEN];
             let mut buf_slice = &mut buf[..];
 
-            // Unwrap is fine because writing to a buffer is infallible
+            // Unwrap is fine because writing to a sufficiently-sized
+            // buffer is infallible
             write!(buf_slice, "[{}]:{}", self.ip(), self.port()).unwrap();
             let len = IPV6_SOCKET_BUF_LEN - buf_slice.len();