From 4bb0a5ed7ff9f959c1a61f43dd796c3f18e8b260 Mon Sep 17 00:00:00 2001
From: EFanZh <efanzh@gmail.com>
Date: Tue, 7 Feb 2023 00:57:43 +0800
Subject: [PATCH 1/7] Inline `Poll` methods

---
 library/core/src/task/poll.rs | 5 +++++
 1 file changed, 5 insertions(+)

diff --git a/library/core/src/task/poll.rs b/library/core/src/task/poll.rs
index 25b61c0e66641..af5bf441bb25f 100644
--- a/library/core/src/task/poll.rs
+++ b/library/core/src/task/poll.rs
@@ -45,6 +45,7 @@ impl<T> Poll<T> {
     /// assert_eq!(poll_some_len, Poll::Ready(13));
     /// ```
     #[stable(feature = "futures_api", since = "1.36.0")]
+    #[inline]
     pub fn map<U, F>(self, f: F) -> Poll<U>
     where
         F: FnOnce(T) -> U,
@@ -144,6 +145,7 @@ impl<T, E> Poll<Result<T, E>> {
     /// assert_eq!(squared, Poll::Ready(Ok(144)));
     /// ```
     #[stable(feature = "futures_api", since = "1.36.0")]
+    #[inline]
     pub fn map_ok<U, F>(self, f: F) -> Poll<Result<U, E>>
     where
         F: FnOnce(T) -> U,
@@ -171,6 +173,7 @@ impl<T, E> Poll<Result<T, E>> {
     /// assert_eq!(res, Poll::Ready(Err(0)));
     /// ```
     #[stable(feature = "futures_api", since = "1.36.0")]
+    #[inline]
     pub fn map_err<U, F>(self, f: F) -> Poll<Result<T, U>>
     where
         F: FnOnce(E) -> U,
@@ -199,6 +202,7 @@ impl<T, E> Poll<Option<Result<T, E>>> {
     /// assert_eq!(squared, Poll::Ready(Some(Ok(144))));
     /// ```
     #[stable(feature = "poll_map", since = "1.51.0")]
+    #[inline]
     pub fn map_ok<U, F>(self, f: F) -> Poll<Option<Result<U, E>>>
     where
         F: FnOnce(T) -> U,
@@ -228,6 +232,7 @@ impl<T, E> Poll<Option<Result<T, E>>> {
     /// assert_eq!(res, Poll::Ready(Some(Err(0))));
     /// ```
     #[stable(feature = "poll_map", since = "1.51.0")]
+    #[inline]
     pub fn map_err<U, F>(self, f: F) -> Poll<Option<Result<T, U>>>
     where
         F: FnOnce(E) -> U,

From 8ffb6af439fe6662cc90794fb75934a0f525be40 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Tomasz=20Mi=C4=85sko?= <tomasz.miasko@gmail.com>
Date: Tue, 21 Feb 2023 00:00:00 +0000
Subject: [PATCH 2/7] Implement read_buf for a few more types

Implement read_buf for TcpStream, Stdin, StdinLock, ChildStdout,
ChildStderr (and internally for AnonPipe, Handle, Socket), so
that it skips buffer initialization.

The other provided methods like read_to_string and read_to_end are
implemented in terms of read_buf and so benefit from the optimization
as well.

This commit also implements read_vectored and is_read_vectored where
applicable.
---
 library/std/src/fs/tests.rs             | 20 +++++++++++++++-
 library/std/src/io/stdio.rs             | 13 ++++++++++-
 library/std/src/net/tcp.rs              | 10 +++++++-
 library/std/src/net/tcp/tests.rs        | 24 ++++++++++++++++++-
 library/std/src/process.rs              | 10 +++++++-
 library/std/src/process/tests.rs        | 31 ++++++++++++++++++++++++-
 library/std/src/sys/unix/fd.rs          |  9 +++++++
 library/std/src/sys/unix/net.rs         | 28 +++++++++++++++++-----
 library/std/src/sys/unix/pipe.rs        |  6 ++++-
 library/std/src/sys/unix/stdio.rs       |  6 ++++-
 library/std/src/sys/unsupported/pipe.rs |  6 ++++-
 library/std/src/sys/windows/handle.rs   |  9 +++++++
 library/std/src/sys/windows/net.rs      | 28 +++++++++++++++-------
 library/std/src/sys/windows/pipe.rs     | 24 ++++++++++++++++++-
 library/std/src/sys_common/net.rs       |  6 ++++-
 15 files changed, 205 insertions(+), 25 deletions(-)

diff --git a/library/std/src/fs/tests.rs b/library/std/src/fs/tests.rs
index 839fdc96632d1..960cbc99c9767 100644
--- a/library/std/src/fs/tests.rs
+++ b/library/std/src/fs/tests.rs
@@ -2,7 +2,8 @@ use crate::io::prelude::*;
 
 use crate::env;
 use crate::fs::{self, File, OpenOptions};
-use crate::io::{ErrorKind, SeekFrom};
+use crate::io::{BorrowedBuf, ErrorKind, SeekFrom};
+use crate::mem::MaybeUninit;
 use crate::path::Path;
 use crate::str;
 use crate::sync::Arc;
@@ -401,6 +402,23 @@ fn file_test_io_seek_read_write() {
     check!(fs::remove_file(&filename));
 }
 
+#[test]
+fn file_test_read_buf() {
+    let tmpdir = tmpdir();
+    let filename = &tmpdir.join("test");
+    check!(fs::write(filename, &[1, 2, 3, 4]));
+
+    let mut buf: [MaybeUninit<u8>; 128] = MaybeUninit::uninit_array();
+    let mut buf = BorrowedBuf::from(buf.as_mut_slice());
+    let mut file = check!(File::open(filename));
+    check!(file.read_buf(buf.unfilled()));
+    assert_eq!(buf.filled(), &[1, 2, 3, 4]);
+    // File::read_buf should omit buffer initialization.
+    assert_eq!(buf.init_len(), 4);
+
+    check!(fs::remove_file(filename));
+}
+
 #[test]
 fn file_test_stat_is_correct_on_is_file() {
     let tmpdir = tmpdir();
diff --git a/library/std/src/io/stdio.rs b/library/std/src/io/stdio.rs
index 14bfef4c7aad9..0455a00956e6f 100644
--- a/library/std/src/io/stdio.rs
+++ b/library/std/src/io/stdio.rs
@@ -8,7 +8,7 @@ use crate::io::prelude::*;
 use crate::cell::{Cell, RefCell};
 use crate::fmt;
 use crate::fs::File;
-use crate::io::{self, BufReader, IoSlice, IoSliceMut, LineWriter, Lines};
+use crate::io::{self, BorrowedCursor, BufReader, IoSlice, IoSliceMut, LineWriter, Lines};
 use crate::sync::atomic::{AtomicBool, Ordering};
 use crate::sync::{Arc, Mutex, MutexGuard, OnceLock, ReentrantMutex, ReentrantMutexGuard};
 use crate::sys::stdio;
@@ -97,6 +97,10 @@ impl Read for StdinRaw {
         handle_ebadf(self.0.read(buf), 0)
     }
 
+    fn read_buf(&mut self, buf: BorrowedCursor<'_>) -> io::Result<()> {
+        handle_ebadf(self.0.read_buf(buf), ())
+    }
+
     fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
         handle_ebadf(self.0.read_vectored(bufs), 0)
     }
@@ -418,6 +422,9 @@ impl Read for Stdin {
     fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
         self.lock().read(buf)
     }
+    fn read_buf(&mut self, buf: BorrowedCursor<'_>) -> io::Result<()> {
+        self.lock().read_buf(buf)
+    }
     fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
         self.lock().read_vectored(bufs)
     }
@@ -450,6 +457,10 @@ impl Read for StdinLock<'_> {
         self.inner.read(buf)
     }
 
+    fn read_buf(&mut self, buf: BorrowedCursor<'_>) -> io::Result<()> {
+        self.inner.read_buf(buf)
+    }
+
     fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
         self.inner.read_vectored(bufs)
     }
diff --git a/library/std/src/net/tcp.rs b/library/std/src/net/tcp.rs
index ac09a805975ef..3982d3636614e 100644
--- a/library/std/src/net/tcp.rs
+++ b/library/std/src/net/tcp.rs
@@ -6,7 +6,7 @@ mod tests;
 use crate::io::prelude::*;
 
 use crate::fmt;
-use crate::io::{self, IoSlice, IoSliceMut};
+use crate::io::{self, BorrowedCursor, IoSlice, IoSliceMut};
 use crate::iter::FusedIterator;
 use crate::net::{Shutdown, SocketAddr, ToSocketAddrs};
 use crate::sys_common::net as net_imp;
@@ -619,6 +619,10 @@ impl Read for TcpStream {
         self.0.read(buf)
     }
 
+    fn read_buf(&mut self, buf: BorrowedCursor<'_>) -> io::Result<()> {
+        self.0.read_buf(buf)
+    }
+
     fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
         self.0.read_vectored(bufs)
     }
@@ -653,6 +657,10 @@ impl Read for &TcpStream {
         self.0.read(buf)
     }
 
+    fn read_buf(&mut self, buf: BorrowedCursor<'_>) -> io::Result<()> {
+        self.0.read_buf(buf)
+    }
+
     fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
         self.0.read_vectored(bufs)
     }
diff --git a/library/std/src/net/tcp/tests.rs b/library/std/src/net/tcp/tests.rs
index 8c0adcfb0ebbb..b8cfead19d7ee 100644
--- a/library/std/src/net/tcp/tests.rs
+++ b/library/std/src/net/tcp/tests.rs
@@ -1,6 +1,7 @@
 use crate::fmt;
 use crate::io::prelude::*;
-use crate::io::{ErrorKind, IoSlice, IoSliceMut};
+use crate::io::{BorrowedBuf, ErrorKind, IoSlice, IoSliceMut};
+use crate::mem::MaybeUninit;
 use crate::net::test::{next_test_ip4, next_test_ip6};
 use crate::net::*;
 use crate::sync::mpsc::channel;
@@ -279,6 +280,27 @@ fn partial_read() {
     })
 }
 
+#[test]
+fn read_buf() {
+    each_ip(&mut |addr| {
+        let srv = t!(TcpListener::bind(&addr));
+        let t = thread::spawn(move || {
+            let mut s = t!(TcpStream::connect(&addr));
+            s.write_all(&[1, 2, 3, 4]).unwrap();
+        });
+
+        let mut s = t!(srv.accept()).0;
+        let mut buf: [MaybeUninit<u8>; 128] = MaybeUninit::uninit_array();
+        let mut buf = BorrowedBuf::from(buf.as_mut_slice());
+        t!(s.read_buf(buf.unfilled()));
+        assert_eq!(buf.filled(), &[1, 2, 3, 4]);
+        // TcpStream::read_buf should omit buffer initialization.
+        assert_eq!(buf.init_len(), 4);
+
+        t.join().ok().expect("thread panicked");
+    })
+}
+
 #[test]
 fn read_vectored() {
     each_ip(&mut |addr| {
diff --git a/library/std/src/process.rs b/library/std/src/process.rs
index 62ce2cb33dc55..27116f4b6139b 100644
--- a/library/std/src/process.rs
+++ b/library/std/src/process.rs
@@ -110,7 +110,7 @@ use crate::convert::Infallible;
 use crate::ffi::OsStr;
 use crate::fmt;
 use crate::fs;
-use crate::io::{self, IoSlice, IoSliceMut};
+use crate::io::{self, BorrowedCursor, IoSlice, IoSliceMut};
 use crate::num::NonZeroI32;
 use crate::path::Path;
 use crate::str;
@@ -354,6 +354,10 @@ impl Read for ChildStdout {
         self.inner.read(buf)
     }
 
+    fn read_buf(&mut self, buf: BorrowedCursor<'_>) -> io::Result<()> {
+        self.inner.read_buf(buf)
+    }
+
     fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
         self.inner.read_vectored(bufs)
     }
@@ -419,6 +423,10 @@ impl Read for ChildStderr {
         self.inner.read(buf)
     }
 
+    fn read_buf(&mut self, buf: BorrowedCursor<'_>) -> io::Result<()> {
+        self.inner.read_buf(buf)
+    }
+
     fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
         self.inner.read_vectored(bufs)
     }
diff --git a/library/std/src/process/tests.rs b/library/std/src/process/tests.rs
index b4f6cc2dabae3..0e3494e53d24b 100644
--- a/library/std/src/process/tests.rs
+++ b/library/std/src/process/tests.rs
@@ -1,7 +1,8 @@
 use crate::io::prelude::*;
 
 use super::{Command, Output, Stdio};
-use crate::io::ErrorKind;
+use crate::io::{BorrowedBuf, ErrorKind};
+use crate::mem::MaybeUninit;
 use crate::str;
 
 fn known_command() -> Command {
@@ -119,6 +120,34 @@ fn stdin_works() {
     assert_eq!(out, "foobar\n");
 }
 
+#[test]
+#[cfg_attr(any(target_os = "vxworks"), ignore)]
+fn child_stdout_read_buf() {
+    let mut cmd = shell_cmd();
+    if cfg!(target_os = "windows") {
+        cmd.arg("/C").arg("echo abc");
+    } else {
+        cmd.arg("-c").arg("echo abc");
+    };
+    cmd.stdin(Stdio::null());
+    cmd.stdout(Stdio::piped());
+    let child = cmd.spawn().unwrap();
+
+    let mut stdout = child.stdout.unwrap();
+    let mut buf: [MaybeUninit<u8>; 128] = MaybeUninit::uninit_array();
+    let mut buf = BorrowedBuf::from(buf.as_mut_slice());
+    stdout.read_buf(buf.unfilled()).unwrap();
+
+    // ChildStdout::read_buf should omit buffer initialization.
+    if cfg!(target_os = "windows") {
+        assert_eq!(buf.filled(), b"abc\r\n");
+        assert_eq!(buf.init_len(), 5);
+    } else {
+        assert_eq!(buf.filled(), b"abc\n");
+        assert_eq!(buf.init_len(), 4);
+    };
+}
+
 #[test]
 #[cfg_attr(any(target_os = "vxworks"), ignore)]
 fn test_process_status() {
diff --git a/library/std/src/sys/unix/fd.rs b/library/std/src/sys/unix/fd.rs
index 66c33d58d6ca3..4798992c6b07c 100644
--- a/library/std/src/sys/unix/fd.rs
+++ b/library/std/src/sys/unix/fd.rs
@@ -283,6 +283,15 @@ impl<'a> Read for &'a FileDesc {
     fn read_buf(&mut self, cursor: BorrowedCursor<'_>) -> io::Result<()> {
         (**self).read_buf(cursor)
     }
+
+    fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
+        (**self).read_vectored(bufs)
+    }
+
+    #[inline]
+    fn is_read_vectored(&self) -> bool {
+        (**self).is_read_vectored()
+    }
 }
 
 impl AsInner<OwnedFd> for FileDesc {
diff --git a/library/std/src/sys/unix/net.rs b/library/std/src/sys/unix/net.rs
index c86f80972a69d..58431a479f045 100644
--- a/library/std/src/sys/unix/net.rs
+++ b/library/std/src/sys/unix/net.rs
@@ -1,6 +1,6 @@
 use crate::cmp;
 use crate::ffi::CStr;
-use crate::io::{self, IoSlice, IoSliceMut};
+use crate::io::{self, BorrowedBuf, BorrowedCursor, IoSlice, IoSliceMut};
 use crate::mem;
 use crate::net::{Shutdown, SocketAddr};
 use crate::os::unix::io::{AsFd, AsRawFd, BorrowedFd, FromRawFd, IntoRawFd, RawFd};
@@ -240,19 +240,35 @@ impl Socket {
         self.0.duplicate().map(Socket)
     }
 
-    fn recv_with_flags(&self, buf: &mut [u8], flags: c_int) -> io::Result<usize> {
+    fn recv_with_flags(&self, mut buf: BorrowedCursor<'_>, flags: c_int) -> io::Result<()> {
         let ret = cvt(unsafe {
-            libc::recv(self.as_raw_fd(), buf.as_mut_ptr() as *mut c_void, buf.len(), flags)
+            libc::recv(
+                self.as_raw_fd(),
+                buf.as_mut().as_mut_ptr() as *mut c_void,
+                buf.capacity(),
+                flags,
+            )
         })?;
-        Ok(ret as usize)
+        unsafe {
+            buf.advance(ret as usize);
+        }
+        Ok(())
     }
 
     pub fn read(&self, buf: &mut [u8]) -> io::Result<usize> {
-        self.recv_with_flags(buf, 0)
+        let mut buf = BorrowedBuf::from(buf);
+        self.recv_with_flags(buf.unfilled(), 0)?;
+        Ok(buf.len())
     }
 
     pub fn peek(&self, buf: &mut [u8]) -> io::Result<usize> {
-        self.recv_with_flags(buf, MSG_PEEK)
+        let mut buf = BorrowedBuf::from(buf);
+        self.recv_with_flags(buf.unfilled(), MSG_PEEK)?;
+        Ok(buf.len())
+    }
+
+    pub fn read_buf(&self, buf: BorrowedCursor<'_>) -> io::Result<()> {
+        self.recv_with_flags(buf, 0)
     }
 
     pub fn read_vectored(&self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
diff --git a/library/std/src/sys/unix/pipe.rs b/library/std/src/sys/unix/pipe.rs
index a744d0ab64043..dc17c9fac460a 100644
--- a/library/std/src/sys/unix/pipe.rs
+++ b/library/std/src/sys/unix/pipe.rs
@@ -1,4 +1,4 @@
-use crate::io::{self, IoSlice, IoSliceMut};
+use crate::io::{self, BorrowedCursor, IoSlice, IoSliceMut};
 use crate::mem;
 use crate::os::unix::io::{AsFd, AsRawFd, BorrowedFd, FromRawFd, IntoRawFd, RawFd};
 use crate::sys::fd::FileDesc;
@@ -49,6 +49,10 @@ impl AnonPipe {
         self.0.read(buf)
     }
 
+    pub fn read_buf(&self, buf: BorrowedCursor<'_>) -> io::Result<()> {
+        self.0.read_buf(buf)
+    }
+
     pub fn read_vectored(&self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
         self.0.read_vectored(bufs)
     }
diff --git a/library/std/src/sys/unix/stdio.rs b/library/std/src/sys/unix/stdio.rs
index b3626c564e86a..a26f20795a191 100644
--- a/library/std/src/sys/unix/stdio.rs
+++ b/library/std/src/sys/unix/stdio.rs
@@ -1,4 +1,4 @@
-use crate::io::{self, IoSlice, IoSliceMut};
+use crate::io::{self, BorrowedCursor, IoSlice, IoSliceMut};
 use crate::mem::ManuallyDrop;
 use crate::os::unix::io::FromRawFd;
 use crate::sys::fd::FileDesc;
@@ -18,6 +18,10 @@ impl io::Read for Stdin {
         unsafe { ManuallyDrop::new(FileDesc::from_raw_fd(libc::STDIN_FILENO)).read(buf) }
     }
 
+    fn read_buf(&mut self, buf: BorrowedCursor<'_>) -> io::Result<()> {
+        unsafe { ManuallyDrop::new(FileDesc::from_raw_fd(libc::STDIN_FILENO)).read_buf(buf) }
+    }
+
     fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
         unsafe { ManuallyDrop::new(FileDesc::from_raw_fd(libc::STDIN_FILENO)).read_vectored(bufs) }
     }
diff --git a/library/std/src/sys/unsupported/pipe.rs b/library/std/src/sys/unsupported/pipe.rs
index 0bba673b458cb..d7d8f297ae586 100644
--- a/library/std/src/sys/unsupported/pipe.rs
+++ b/library/std/src/sys/unsupported/pipe.rs
@@ -1,4 +1,4 @@
-use crate::io::{self, IoSlice, IoSliceMut};
+use crate::io::{self, BorrowedCursor, IoSlice, IoSliceMut};
 
 pub struct AnonPipe(!);
 
@@ -7,6 +7,10 @@ impl AnonPipe {
         self.0
     }
 
+    pub fn read_buf(&self, _buf: BorrowedCursor<'_>) -> io::Result<()> {
+        self.0
+    }
+
     pub fn read_vectored(&self, _bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
         self.0
     }
diff --git a/library/std/src/sys/windows/handle.rs b/library/std/src/sys/windows/handle.rs
index ae33d48c612ee..b290f4070e8fd 100644
--- a/library/std/src/sys/windows/handle.rs
+++ b/library/std/src/sys/windows/handle.rs
@@ -327,7 +327,16 @@ impl<'a> Read for &'a Handle {
         (**self).read(buf)
     }
 
+    fn read_buf(&mut self, buf: BorrowedCursor<'_>) -> io::Result<()> {
+        (**self).read_buf(buf)
+    }
+
     fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
         (**self).read_vectored(bufs)
     }
+
+    #[inline]
+    fn is_read_vectored(&self) -> bool {
+        (**self).is_read_vectored()
+    }
 }
diff --git a/library/std/src/sys/windows/net.rs b/library/std/src/sys/windows/net.rs
index e0701a498fad7..ee1f5482b47ee 100644
--- a/library/std/src/sys/windows/net.rs
+++ b/library/std/src/sys/windows/net.rs
@@ -1,7 +1,7 @@
 #![unstable(issue = "none", feature = "windows_net")]
 
 use crate::cmp;
-use crate::io::{self, IoSlice, IoSliceMut, Read};
+use crate::io::{self, BorrowedBuf, BorrowedCursor, IoSlice, IoSliceMut, Read};
 use crate::mem;
 use crate::net::{Shutdown, SocketAddr};
 use crate::os::windows::io::{
@@ -214,28 +214,38 @@ impl Socket {
         Ok(Self(self.0.try_clone()?))
     }
 
-    fn recv_with_flags(&self, buf: &mut [u8], flags: c_int) -> io::Result<usize> {
+    fn recv_with_flags(&self, mut buf: BorrowedCursor<'_>, flags: c_int) -> io::Result<()> {
         // On unix when a socket is shut down all further reads return 0, so we
         // do the same on windows to map a shut down socket to returning EOF.
-        let length = cmp::min(buf.len(), i32::MAX as usize) as i32;
-        let result =
-            unsafe { c::recv(self.as_raw_socket(), buf.as_mut_ptr() as *mut _, length, flags) };
+        let length = cmp::min(buf.capacity(), i32::MAX as usize) as i32;
+        let result = unsafe {
+            c::recv(self.as_raw_socket(), buf.as_mut().as_mut_ptr() as *mut _, length, flags)
+        };
 
         match result {
             c::SOCKET_ERROR => {
                 let error = unsafe { c::WSAGetLastError() };
 
                 if error == c::WSAESHUTDOWN {
-                    Ok(0)
+                    Ok(())
                 } else {
                     Err(io::Error::from_raw_os_error(error))
                 }
             }
-            _ => Ok(result as usize),
+            _ => {
+                unsafe { buf.advance(result as usize) };
+                Ok(())
+            }
         }
     }
 
     pub fn read(&self, buf: &mut [u8]) -> io::Result<usize> {
+        let mut buf = BorrowedBuf::from(buf);
+        self.recv_with_flags(buf.unfilled(), 0)?;
+        Ok(buf.len())
+    }
+
+    pub fn read_buf(&self, buf: BorrowedCursor<'_>) -> io::Result<()> {
         self.recv_with_flags(buf, 0)
     }
 
@@ -277,7 +287,9 @@ impl Socket {
     }
 
     pub fn peek(&self, buf: &mut [u8]) -> io::Result<usize> {
-        self.recv_with_flags(buf, c::MSG_PEEK)
+        let mut buf = BorrowedBuf::from(buf);
+        self.recv_with_flags(buf.unfilled(), c::MSG_PEEK)?;
+        Ok(buf.len())
     }
 
     fn recv_from_with_flags(
diff --git a/library/std/src/sys/windows/pipe.rs b/library/std/src/sys/windows/pipe.rs
index 7b25edaa556f0..0780b29584da4 100644
--- a/library/std/src/sys/windows/pipe.rs
+++ b/library/std/src/sys/windows/pipe.rs
@@ -1,7 +1,7 @@
 use crate::os::windows::prelude::*;
 
 use crate::ffi::OsStr;
-use crate::io::{self, IoSlice, IoSliceMut, Read};
+use crate::io::{self, BorrowedCursor, IoSlice, IoSliceMut, Read};
 use crate::mem;
 use crate::path::Path;
 use crate::ptr;
@@ -252,6 +252,28 @@ impl AnonPipe {
         }
     }
 
+    pub fn read_buf(&self, mut buf: BorrowedCursor<'_>) -> io::Result<()> {
+        let result = unsafe {
+            let len = crate::cmp::min(buf.capacity(), c::DWORD::MAX as usize) as c::DWORD;
+            self.alertable_io_internal(c::ReadFileEx, buf.as_mut().as_mut_ptr() as _, len)
+        };
+
+        match result {
+            // The special treatment of BrokenPipe is to deal with Windows
+            // pipe semantics, which yields this error when *reading* from
+            // a pipe after the other end has closed; we interpret that as
+            // EOF on the pipe.
+            Err(ref e) if e.kind() == io::ErrorKind::BrokenPipe => Ok(()),
+            Err(e) => Err(e),
+            Ok(n) => {
+                unsafe {
+                    buf.advance(n);
+                }
+                Ok(())
+            }
+        }
+    }
+
     pub fn read_vectored(&self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
         self.inner.read_vectored(bufs)
     }
diff --git a/library/std/src/sys_common/net.rs b/library/std/src/sys_common/net.rs
index 2c38dfecf9734..ab988b97193c4 100644
--- a/library/std/src/sys_common/net.rs
+++ b/library/std/src/sys_common/net.rs
@@ -4,7 +4,7 @@ mod tests;
 use crate::cmp;
 use crate::convert::{TryFrom, TryInto};
 use crate::fmt;
-use crate::io::{self, ErrorKind, IoSlice, IoSliceMut};
+use crate::io::{self, BorrowedCursor, ErrorKind, IoSlice, IoSliceMut};
 use crate::mem;
 use crate::net::{Ipv4Addr, Ipv6Addr, Shutdown, SocketAddr};
 use crate::ptr;
@@ -271,6 +271,10 @@ impl TcpStream {
         self.inner.read(buf)
     }
 
+    pub fn read_buf(&self, buf: BorrowedCursor<'_>) -> io::Result<()> {
+        self.inner.read_buf(buf)
+    }
+
     pub fn read_vectored(&self, bufs: &mut [IoSliceMut<'_>]) -> io::Result<usize> {
         self.inner.read_vectored(bufs)
     }

From 506ce7e3cc5637bd5832bbb3d1f3ba3725797477 Mon Sep 17 00:00:00 2001
From: Michael Goulet <michael@errs.io>
Date: Wed, 22 Feb 2023 22:13:52 +0000
Subject: [PATCH 3/7] Re-apply "switch to the macos-12-xl builder"

This reverts commit e63ec2e1402eaff949e5c53b8f6062b152010fcc.
---
 .github/workflows/ci.yml     | 12 ++++++------
 src/ci/github-actions/ci.yml |  2 +-
 2 files changed, 7 insertions(+), 7 deletions(-)

diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
index 7c17dfd8c8edc..44f789c592ba2 100644
--- a/.github/workflows/ci.yml
+++ b/.github/workflows/ci.yml
@@ -322,7 +322,7 @@ jobs:
               NO_DEBUG_ASSERTIONS: 1
               NO_OVERFLOW_CHECKS: 1
               DIST_REQUIRE_ALL_TOOLS: 1
-            os: macos-latest
+            os: macos-12-xl
           - name: dist-apple-various
             env:
               SCRIPT: "./x.py dist bootstrap --include-default-paths --host='' --target=aarch64-apple-ios,x86_64-apple-ios,aarch64-apple-ios-sim"
@@ -333,7 +333,7 @@ jobs:
               NO_LLVM_ASSERTIONS: 1
               NO_DEBUG_ASSERTIONS: 1
               NO_OVERFLOW_CHECKS: 1
-            os: macos-latest
+            os: macos-12-xl
           - name: dist-x86_64-apple-alt
             env:
               SCRIPT: "./x.py dist bootstrap --include-default-paths"
@@ -344,7 +344,7 @@ jobs:
               NO_LLVM_ASSERTIONS: 1
               NO_DEBUG_ASSERTIONS: 1
               NO_OVERFLOW_CHECKS: 1
-            os: macos-latest
+            os: macos-12-xl
           - name: x86_64-apple-1
             env:
               SCRIPT: "./x.py --stage 2 test --exclude tests/ui --exclude tests/rustdoc --exclude tests/run-make-fulldeps"
@@ -355,7 +355,7 @@ jobs:
               NO_LLVM_ASSERTIONS: 1
               NO_DEBUG_ASSERTIONS: 1
               NO_OVERFLOW_CHECKS: 1
-            os: macos-latest
+            os: macos-12-xl
           - name: x86_64-apple-2
             env:
               SCRIPT: "./x.py --stage 2 test tests/ui tests/rustdoc tests/run-make-fulldeps"
@@ -366,7 +366,7 @@ jobs:
               NO_LLVM_ASSERTIONS: 1
               NO_DEBUG_ASSERTIONS: 1
               NO_OVERFLOW_CHECKS: 1
-            os: macos-latest
+            os: macos-12-xl
           - name: dist-aarch64-apple
             env:
               SCRIPT: "./x.py dist bootstrap --include-default-paths --stage 2"
@@ -381,7 +381,7 @@ jobs:
               NO_OVERFLOW_CHECKS: 1
               DIST_REQUIRE_ALL_TOOLS: 1
               JEMALLOC_SYS_WITH_LG_PAGE: 14
-            os: macos-latest
+            os: macos-12-xl
           - name: x86_64-msvc-1
             env:
               RUST_CONFIGURE_ARGS: "--build=x86_64-pc-windows-msvc --enable-profiler"
diff --git a/src/ci/github-actions/ci.yml b/src/ci/github-actions/ci.yml
index ad9c308ad852d..11f1532bef594 100644
--- a/src/ci/github-actions/ci.yml
+++ b/src/ci/github-actions/ci.yml
@@ -78,7 +78,7 @@ x--expand-yaml-anchors--remove:
     <<: *base-job
 
   - &job-macos-xl
-    os: macos-latest  # We don't have an XL builder for this
+    os: macos-12-xl
     <<: *base-job
 
   - &job-windows-xl

From 11fbb573951d61b7de9b773750c206253a5db974 Mon Sep 17 00:00:00 2001
From: Camille GILLOT <gillot.camille@gmail.com>
Date: Tue, 25 Oct 2022 18:34:58 +0000
Subject: [PATCH 4/7] Simplify diagnostic_items.

---
 compiler/rustc_middle/src/hir/mod.rs          | 14 +++--
 compiler/rustc_passes/src/diagnostic_items.rs | 63 +++++++++----------
 2 files changed, 39 insertions(+), 38 deletions(-)

diff --git a/compiler/rustc_middle/src/hir/mod.rs b/compiler/rustc_middle/src/hir/mod.rs
index 2e2ca6a27888e..ad119c4e07306 100644
--- a/compiler/rustc_middle/src/hir/mod.rs
+++ b/compiler/rustc_middle/src/hir/mod.rs
@@ -64,13 +64,17 @@ impl ModuleItems {
         self.foreign_items.iter().copied()
     }
 
-    pub fn definitions(&self) -> impl Iterator<Item = LocalDefId> + '_ {
+    pub fn owners(&self) -> impl Iterator<Item = OwnerId> + '_ {
         self.items
             .iter()
-            .map(|id| id.owner_id.def_id)
-            .chain(self.trait_items.iter().map(|id| id.owner_id.def_id))
-            .chain(self.impl_items.iter().map(|id| id.owner_id.def_id))
-            .chain(self.foreign_items.iter().map(|id| id.owner_id.def_id))
+            .map(|id| id.owner_id)
+            .chain(self.trait_items.iter().map(|id| id.owner_id))
+            .chain(self.impl_items.iter().map(|id| id.owner_id))
+            .chain(self.foreign_items.iter().map(|id| id.owner_id))
+    }
+
+    pub fn definitions(&self) -> impl Iterator<Item = LocalDefId> + '_ {
+        self.owners().map(|id| id.def_id)
     }
 
     pub fn par_items(&self, f: impl Fn(ItemId) + Send + Sync) {
diff --git a/compiler/rustc_passes/src/diagnostic_items.rs b/compiler/rustc_passes/src/diagnostic_items.rs
index 0ae7096642cf1..ae3d40b0ec516 100644
--- a/compiler/rustc_passes/src/diagnostic_items.rs
+++ b/compiler/rustc_passes/src/diagnostic_items.rs
@@ -11,19 +11,19 @@
 
 use rustc_ast as ast;
 use rustc_hir::diagnostic_items::DiagnosticItems;
+use rustc_hir::OwnerId;
 use rustc_middle::ty::query::Providers;
 use rustc_middle::ty::TyCtxt;
-use rustc_span::def_id::{CrateNum, DefId, LocalDefId, LOCAL_CRATE};
+use rustc_span::def_id::{CrateNum, DefId, LOCAL_CRATE};
 use rustc_span::symbol::{kw::Empty, sym, Symbol};
 
 use crate::errors::{DuplicateDiagnosticItem, DuplicateDiagnosticItemInCrate};
 
-fn observe_item(tcx: TyCtxt<'_>, diagnostic_items: &mut DiagnosticItems, def_id: LocalDefId) {
-    let hir_id = tcx.hir().local_def_id_to_hir_id(def_id);
-    let attrs = tcx.hir().attrs(hir_id);
+fn observe_item<'tcx>(tcx: TyCtxt<'tcx>, diagnostic_items: &mut DiagnosticItems, owner: OwnerId) {
+    let attrs = tcx.hir().attrs(owner.into());
     if let Some(name) = extract(attrs) {
         // insert into our table
-        collect_item(tcx, diagnostic_items, name, def_id.to_def_id());
+        collect_item(tcx, diagnostic_items, name, owner.to_def_id());
     }
 }
 
@@ -31,23 +31,33 @@ fn collect_item(tcx: TyCtxt<'_>, items: &mut DiagnosticItems, name: Symbol, item
     items.id_to_name.insert(item_def_id, name);
     if let Some(original_def_id) = items.name_to_id.insert(name, item_def_id) {
         if original_def_id != item_def_id {
-            let orig_span = tcx.hir().span_if_local(original_def_id);
-            let orig_crate_name =
-                orig_span.is_none().then(|| tcx.crate_name(original_def_id.krate));
-            match tcx.hir().span_if_local(item_def_id) {
-                Some(span) => tcx.sess.emit_err(DuplicateDiagnosticItem { span, name }),
-                None => tcx.sess.emit_err(DuplicateDiagnosticItemInCrate {
-                    span: orig_span,
-                    orig_crate_name: orig_crate_name.unwrap_or(Empty),
-                    have_orig_crate_name: orig_crate_name.map(|_| ()),
-                    crate_name: tcx.crate_name(item_def_id.krate),
-                    name,
-                }),
-            };
+            report_duplicate_item(tcx, name, original_def_id, item_def_id);
         }
     }
 }
 
+fn report_duplicate_item(
+    tcx: TyCtxt<'_>,
+    name: Symbol,
+    original_def_id: DefId,
+    item_def_id: DefId,
+) {
+    let (orig_span, orig_crate_name, have_orig_crate_name) = match original_def_id.as_local() {
+        Some(local_original) => (Some(tcx.def_span(local_original)), Empty, None),
+        None => (None, tcx.crate_name(original_def_id.krate), Some(())),
+    };
+    match tcx.hir().span_if_local(item_def_id) {
+        Some(span) => tcx.sess.emit_err(DuplicateDiagnosticItem { span, name }),
+        None => tcx.sess.emit_err(DuplicateDiagnosticItemInCrate {
+            span: orig_span,
+            orig_crate_name,
+            have_orig_crate_name,
+            crate_name: tcx.crate_name(item_def_id.krate),
+            name,
+        }),
+    };
+}
+
 /// Extract the first `rustc_diagnostic_item = "$name"` out of a list of attributes.
 fn extract(attrs: &[ast::Attribute]) -> Option<Symbol> {
     attrs.iter().find_map(|attr| {
@@ -64,21 +74,8 @@ fn diagnostic_items(tcx: TyCtxt<'_>, cnum: CrateNum) -> DiagnosticItems {
 
     // Collect diagnostic items in this crate.
     let crate_items = tcx.hir_crate_items(());
-
-    for id in crate_items.items() {
-        observe_item(tcx, &mut diagnostic_items, id.owner_id.def_id);
-    }
-
-    for id in crate_items.trait_items() {
-        observe_item(tcx, &mut diagnostic_items, id.owner_id.def_id);
-    }
-
-    for id in crate_items.impl_items() {
-        observe_item(tcx, &mut diagnostic_items, id.owner_id.def_id);
-    }
-
-    for id in crate_items.foreign_items() {
-        observe_item(tcx, &mut diagnostic_items, id.owner_id.def_id);
+    for id in crate_items.owners() {
+        observe_item(tcx, &mut diagnostic_items, id);
     }
 
     diagnostic_items

From 752ddd028c877c2033940d0dcd4e3dcbf569ae9d Mon Sep 17 00:00:00 2001
From: Camille GILLOT <gillot.camille@gmail.com>
Date: Sun, 26 Feb 2023 10:29:25 +0000
Subject: [PATCH 5/7] Merge the two diagnostics.

---
 compiler/rustc_passes/locales/en-US.ftl       |  3 --
 compiler/rustc_passes/src/diagnostic_items.rs | 28 ++++++++-----------
 compiler/rustc_passes/src/errors.rs           | 16 ++++-------
 .../tool-attributes/duplicate-diagnostic.rs   |  2 +-
 .../duplicate-diagnostic.stderr               |  4 ++-
 5 files changed, 21 insertions(+), 32 deletions(-)

diff --git a/compiler/rustc_passes/locales/en-US.ftl b/compiler/rustc_passes/locales/en-US.ftl
index 0ed29ce0d4795..3fa78efc290ba 100644
--- a/compiler/rustc_passes/locales/en-US.ftl
+++ b/compiler/rustc_passes/locales/en-US.ftl
@@ -402,9 +402,6 @@ passes_invalid_attr_at_crate_level =
     `{$name}` attribute cannot be used at crate level
     .suggestion = perhaps you meant to use an outer attribute
 
-passes_duplicate_diagnostic_item =
-    duplicate diagnostic item found: `{$name}`.
-
 passes_duplicate_diagnostic_item_in_crate =
     duplicate diagnostic item in crate `{$crate_name}`: `{$name}`.
     .note = the diagnostic item is first defined in crate `{$orig_crate_name}`.
diff --git a/compiler/rustc_passes/src/diagnostic_items.rs b/compiler/rustc_passes/src/diagnostic_items.rs
index ae3d40b0ec516..110eb210df9ad 100644
--- a/compiler/rustc_passes/src/diagnostic_items.rs
+++ b/compiler/rustc_passes/src/diagnostic_items.rs
@@ -15,9 +15,9 @@ use rustc_hir::OwnerId;
 use rustc_middle::ty::query::Providers;
 use rustc_middle::ty::TyCtxt;
 use rustc_span::def_id::{CrateNum, DefId, LOCAL_CRATE};
-use rustc_span::symbol::{kw::Empty, sym, Symbol};
+use rustc_span::symbol::{sym, Symbol};
 
-use crate::errors::{DuplicateDiagnosticItem, DuplicateDiagnosticItemInCrate};
+use crate::errors::DuplicateDiagnosticItemInCrate;
 
 fn observe_item<'tcx>(tcx: TyCtxt<'tcx>, diagnostic_items: &mut DiagnosticItems, owner: OwnerId) {
     let attrs = tcx.hir().attrs(owner.into());
@@ -42,20 +42,16 @@ fn report_duplicate_item(
     original_def_id: DefId,
     item_def_id: DefId,
 ) {
-    let (orig_span, orig_crate_name, have_orig_crate_name) = match original_def_id.as_local() {
-        Some(local_original) => (Some(tcx.def_span(local_original)), Empty, None),
-        None => (None, tcx.crate_name(original_def_id.krate), Some(())),
-    };
-    match tcx.hir().span_if_local(item_def_id) {
-        Some(span) => tcx.sess.emit_err(DuplicateDiagnosticItem { span, name }),
-        None => tcx.sess.emit_err(DuplicateDiagnosticItemInCrate {
-            span: orig_span,
-            orig_crate_name,
-            have_orig_crate_name,
-            crate_name: tcx.crate_name(item_def_id.krate),
-            name,
-        }),
-    };
+    let orig_span = tcx.hir().span_if_local(original_def_id);
+    let duplicate_span = tcx.hir().span_if_local(item_def_id);
+    tcx.sess.emit_err(DuplicateDiagnosticItemInCrate {
+        duplicate_span,
+        orig_span,
+        crate_name: tcx.crate_name(item_def_id.krate),
+        orig_crate_name: tcx.crate_name(original_def_id.krate),
+        different_crates: (item_def_id.krate != original_def_id.krate).then_some(()),
+        name,
+    });
 }
 
 /// Extract the first `rustc_diagnostic_item = "$name"` out of a list of attributes.
diff --git a/compiler/rustc_passes/src/errors.rs b/compiler/rustc_passes/src/errors.rs
index 2c0d21b479848..9f1c0b5a0b7bd 100644
--- a/compiler/rustc_passes/src/errors.rs
+++ b/compiler/rustc_passes/src/errors.rs
@@ -809,23 +809,17 @@ impl IntoDiagnostic<'_> for InvalidAttrAtCrateLevel {
     }
 }
 
-#[derive(Diagnostic)]
-#[diag(passes_duplicate_diagnostic_item)]
-pub struct DuplicateDiagnosticItem {
-    #[primary_span]
-    pub span: Span,
-    pub name: Symbol,
-}
-
 #[derive(Diagnostic)]
 #[diag(passes_duplicate_diagnostic_item_in_crate)]
 pub struct DuplicateDiagnosticItemInCrate {
+    #[primary_span]
+    pub duplicate_span: Option<Span>,
     #[note(passes_diagnostic_item_first_defined)]
-    pub span: Option<Span>,
-    pub orig_crate_name: Symbol,
+    pub orig_span: Option<Span>,
     #[note]
-    pub have_orig_crate_name: Option<()>,
+    pub different_crates: Option<()>,
     pub crate_name: Symbol,
+    pub orig_crate_name: Symbol,
     pub name: Symbol,
 }
 
diff --git a/tests/ui/tool-attributes/duplicate-diagnostic.rs b/tests/ui/tool-attributes/duplicate-diagnostic.rs
index 39c2ca1cb860c..e2cf9508757be 100644
--- a/tests/ui/tool-attributes/duplicate-diagnostic.rs
+++ b/tests/ui/tool-attributes/duplicate-diagnostic.rs
@@ -9,5 +9,5 @@ extern crate p1;
 extern crate p2;
 
 #[rustc_diagnostic_item = "Foo"]
-pub struct Foo {} //~ ERROR duplicate diagnostic item found
+pub struct Foo {} //~ ERROR duplicate diagnostic item in crate `duplicate_diagnostic`: `Foo`
 fn main() {}
diff --git a/tests/ui/tool-attributes/duplicate-diagnostic.stderr b/tests/ui/tool-attributes/duplicate-diagnostic.stderr
index e315fdc7d84bc..26bd6a82e3417 100644
--- a/tests/ui/tool-attributes/duplicate-diagnostic.stderr
+++ b/tests/ui/tool-attributes/duplicate-diagnostic.stderr
@@ -2,11 +2,13 @@ error: duplicate diagnostic item in crate `p2`: `Foo`.
    |
    = note: the diagnostic item is first defined in crate `p1`.
 
-error: duplicate diagnostic item found: `Foo`.
+error: duplicate diagnostic item in crate `duplicate_diagnostic`: `Foo`.
   --> $DIR/duplicate-diagnostic.rs:12:1
    |
 LL | pub struct Foo {}
    | ^^^^^^^^^^^^^^
+   |
+   = note: the diagnostic item is first defined in crate `p2`.
 
 error: aborting due to 2 previous errors
 

From 32da026c35d07e1e256421b0860d136f01ee3bf0 Mon Sep 17 00:00:00 2001
From: y21 <30553356+y21@users.noreply.github.com>
Date: Sun, 26 Feb 2023 01:39:43 +0100
Subject: [PATCH 6/7] generalize help message

---
 compiler/rustc_parse/locales/en-US.ftl          |  2 +-
 tests/ui/parser/match-arm-without-braces.stderr | 10 +++++++---
 2 files changed, 8 insertions(+), 4 deletions(-)

diff --git a/compiler/rustc_parse/locales/en-US.ftl b/compiler/rustc_parse/locales/en-US.ftl
index a31b1f6ac1a0a..4ddeeed5b7e0a 100644
--- a/compiler/rustc_parse/locales/en-US.ftl
+++ b/compiler/rustc_parse/locales/en-US.ftl
@@ -220,7 +220,7 @@ parse_match_arm_body_without_braces = `match` arm body without braces
             [one] statement
            *[other] statements
         } with a body
-    .suggestion_use_comma_not_semicolon = use a comma to end a `match` arm expression
+    .suggestion_use_comma_not_semicolon = replace `;` with `,` to end a `match` arm expression
 
 parse_inclusive_range_extra_equals = unexpected `=` after inclusive range
     .suggestion_remove_eq = use `..=` instead
diff --git a/tests/ui/parser/match-arm-without-braces.stderr b/tests/ui/parser/match-arm-without-braces.stderr
index 37d55aa53f87c..ee1c8e562fc33 100644
--- a/tests/ui/parser/match-arm-without-braces.stderr
+++ b/tests/ui/parser/match-arm-without-braces.stderr
@@ -2,10 +2,14 @@ error: `match` arm body without braces
   --> $DIR/match-arm-without-braces.rs:26:27
    |
 LL |         Some(Val::Foo) => 3;
-   |                        -- ^- help: use a comma to end a `match` arm expression: `,`
-   |                        |  |
-   |                        |  this statement is not surrounded by a body
+   |                        -- ^ this statement is not surrounded by a body
+   |                        |
    |                        while parsing the `match` arm starting here
+   |
+help: replace `;` with `,` to end a `match` arm expression
+   |
+LL |         Some(Val::Foo) => 3,
+   |                            ~
 
 error: `match` arm body without braces
   --> $DIR/match-arm-without-braces.rs:31:11

From 27db6882038b67d83b8aecf108b18dd350f7e7cc Mon Sep 17 00:00:00 2001
From: Guillaume Gomez <guillaume.gomez@huawei.com>
Date: Sun, 26 Feb 2023 16:26:59 +0100
Subject: [PATCH 7/7] Clean up JS files code a bit

---
 src/librustdoc/html/static/js/search.js        | 17 ++++++-----------
 src/librustdoc/html/static/js/source-script.js |  3 +--
 2 files changed, 7 insertions(+), 13 deletions(-)

diff --git a/src/librustdoc/html/static/js/search.js b/src/librustdoc/html/static/js/search.js
index 1e6c94d29ba47..b3fc889431b38 100644
--- a/src/librustdoc/html/static/js/search.js
+++ b/src/librustdoc/html/static/js/search.js
@@ -463,11 +463,10 @@ function initSearch(rawSearchIndex) {
      * @param {ParserState} parserState
      */
     function parseInput(query, parserState) {
-        let c, before;
         let foundStopChar = true;
 
         while (parserState.pos < parserState.length) {
-            c = parserState.userQuery[parserState.pos];
+            const c = parserState.userQuery[parserState.pos];
             if (isStopCharacter(c)) {
                 foundStopChar = true;
                 if (isSeparatorCharacter(c)) {
@@ -506,7 +505,7 @@ function initSearch(rawSearchIndex) {
                 }
                 throw new Error(`Expected \`,\`, \` \`, \`:\` or \`->\`, found \`${c}\``);
             }
-            before = query.elems.length;
+            const before = query.elems.length;
             getNextElem(query, parserState, query.elems, false);
             if (query.elems.length === before) {
                 // Nothing was added, weird... Let's increase the position to not remain stuck.
@@ -515,7 +514,6 @@ function initSearch(rawSearchIndex) {
             foundStopChar = false;
         }
         while (parserState.pos < parserState.length) {
-            c = parserState.userQuery[parserState.pos];
             if (isReturnArrow(parserState)) {
                 parserState.pos += 2;
                 // Get returned elements.
@@ -1940,7 +1938,6 @@ function initSearch(rawSearchIndex) {
          */
         const searchWords = [];
         const charA = "A".charCodeAt(0);
-        let i, word;
         let currentIndex = 0;
         let id = 0;
 
@@ -2035,7 +2032,7 @@ function initSearch(rawSearchIndex) {
             // convert `rawPaths` entries into object form
             // generate normalizedPaths for function search mode
             let len = paths.length;
-            for (i = 0; i < len; ++i) {
+            for (let i = 0; i < len; ++i) {
                 lowercasePaths.push({ty: paths[i][0], name: paths[i][1].toLowerCase()});
                 paths[i] = {ty: paths[i][0], name: paths[i][1]};
             }
@@ -2049,16 +2046,14 @@ function initSearch(rawSearchIndex) {
             // faster analysis operations
             len = itemTypes.length;
             let lastPath = "";
-            for (i = 0; i < len; ++i) {
+            for (let i = 0; i < len; ++i) {
+                let word = "";
                 // This object should have exactly the same set of fields as the "crateRow"
                 // object defined above.
                 if (typeof itemNames[i] === "string") {
                     word = itemNames[i].toLowerCase();
-                    searchWords.push(word);
-                } else {
-                    word = "";
-                    searchWords.push("");
                 }
+                searchWords.push(word);
                 const row = {
                     crate: crate,
                     ty: itemTypes.charCodeAt(i) - charA,
diff --git a/src/librustdoc/html/static/js/source-script.js b/src/librustdoc/html/static/js/source-script.js
index 0e1c864e62d84..6c0f03b5bb072 100644
--- a/src/librustdoc/html/static/js/source-script.js
+++ b/src/librustdoc/html/static/js/source-script.js
@@ -117,8 +117,7 @@ function createSourceSidebar() {
     sidebar.appendChild(title);
     Object.keys(sourcesIndex).forEach(key => {
         sourcesIndex[key][NAME_OFFSET] = key;
-        hasFoundFile = createDirEntry(sourcesIndex[key], sidebar, "",
-            hasFoundFile);
+        hasFoundFile = createDirEntry(sourcesIndex[key], sidebar, "", hasFoundFile);
     });
 
     container.appendChild(sidebar);