Auto merge of #60172 - varkor:tidy-double-trailing-newline, r=kennytm

Disallow double trailing newlines in tidy

This wasn't done previously in https://github.com/rust-lang/rust/pull/47064#issuecomment-354533010 as it affected too many files, but I think it's best to fix it now so that the number of files with double trailing newlines doesn't keep increasing.

r? kennytm
diff --git a/Cargo.lock b/Cargo.lock
index 4c493b2..b62c7ff 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -10,7 +10,7 @@
 version = "0.6.9"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 dependencies = [
- "memchr 2.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
+ "memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
 ]
 
 [[package]]
@@ -972,7 +972,7 @@
 version = "1.0.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 dependencies = [
- "memchr 2.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
+ "memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "termcolor 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)",
 ]
 
@@ -1027,7 +1027,7 @@
  "aho-corasick 0.6.9 (registry+https://github.com/rust-lang/crates.io-index)",
  "fnv 1.0.6 (registry+https://github.com/rust-lang/crates.io-index)",
  "log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
- "memchr 2.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
+ "memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
 ]
 
@@ -1143,7 +1143,7 @@
  "globset 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)",
  "lazy_static 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
- "memchr 2.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
+ "memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "same-file 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)",
  "thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -1441,7 +1441,7 @@
  "itertools 0.7.8 (registry+https://github.com/rust-lang/crates.io-index)",
  "lazy_static 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
- "memchr 2.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
+ "memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "open 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)",
  "pulldown-cmark 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)",
  "regex 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -1469,7 +1469,7 @@
  "itertools 0.7.8 (registry+https://github.com/rust-lang/crates.io-index)",
  "lazy_static 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
- "memchr 2.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
+ "memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "open 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)",
  "pulldown-cmark 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)",
  "regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -1494,13 +1494,8 @@
 
 [[package]]
 name = "memchr"
-version = "2.1.1"
+version = "2.2.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-dependencies = [
- "cfg-if 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
- "libc 0.2.51 (registry+https://github.com/rust-lang/crates.io-index)",
- "version_check 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)",
-]
 
 [[package]]
 name = "memmap"
@@ -2005,6 +2000,16 @@
 ]
 
 [[package]]
+name = "pulldown-cmark"
+version = "0.4.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+dependencies = [
+ "bitflags 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)",
+ "memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
+ "unicase 2.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
+]
+
+[[package]]
 name = "quick-error"
 version = "1.2.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -2169,7 +2174,7 @@
 source = "registry+https://github.com/rust-lang/crates.io-index"
 dependencies = [
  "aho-corasick 0.6.9 (registry+https://github.com/rust-lang/crates.io-index)",
- "memchr 2.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
+ "memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "regex-syntax 0.5.6 (registry+https://github.com/rust-lang/crates.io-index)",
  "thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
  "utf8-ranges 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -2181,7 +2186,7 @@
 source = "registry+https://github.com/rust-lang/crates.io-index"
 dependencies = [
  "aho-corasick 0.6.9 (registry+https://github.com/rust-lang/crates.io-index)",
- "memchr 2.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
+ "memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "regex-syntax 0.6.4 (registry+https://github.com/rust-lang/crates.io-index)",
  "thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
  "utf8-ranges 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -3015,7 +3020,7 @@
 dependencies = [
  "minifier 0.0.29 (registry+https://github.com/rust-lang/crates.io-index)",
  "parking_lot 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)",
- "pulldown-cmark 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)",
+ "pulldown-cmark 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)",
  "tempfile 3.0.5 (registry+https://github.com/rust-lang/crates.io-index)",
 ]
 
@@ -3775,6 +3780,14 @@
 source = "registry+https://github.com/rust-lang/crates.io-index"
 
 [[package]]
+name = "unicase"
+version = "2.3.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+dependencies = [
+ "version_check 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)",
+]
+
+[[package]]
 name = "unicode-bidi"
 version = "0.3.4"
 source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -4132,7 +4145,7 @@
 "checksum mdbook 0.1.7 (registry+https://github.com/rust-lang/crates.io-index)" = "90b5a8d7e341ceee5db3882a06078d42661ddcfa2b3687319cc5da76ec4e782f"
 "checksum mdbook 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "0ba0d44cb4089c741b9a91f3e5218298a40699c2f3a070a85014eed290c60819"
 "checksum measureme 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "36bb2b263a6795d352035024d6b30ce465bb79a5e5280d74c3b5f8464c657bcc"
-"checksum memchr 2.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "0a3eb002f0535929f1199681417029ebea04aadc0c7a4224b46be99c7f5d6a16"
+"checksum memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "2efc7bc57c883d4a4d6e3246905283d8dae951bb3bd32f49d6ef297f546e1c39"
 "checksum memmap 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)" = "e2ffa2c986de11a9df78620c01eeaaf27d94d3ff02bf81bfcca953102dd0c6ff"
 "checksum memoffset 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "0f9dc261e2b62d7a622bf416ea3c5245cdd5d9a7fcc428c0d06804dfce1775b3"
 "checksum minifier 0.0.29 (registry+https://github.com/rust-lang/crates.io-index)" = "1f4950cb2617b1933e2da0446e864dfe0d6a22c22ff72297996c46e6a63b210b"
@@ -4184,6 +4197,7 @@
 "checksum proptest 0.9.2 (registry+https://github.com/rust-lang/crates.io-index)" = "24f5844db2f839e97e3021980975f6ebf8691d9b9b2ca67ed3feb38dc3edb52c"
 "checksum pulldown-cmark 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "d6fdf85cda6cadfae5428a54661d431330b312bc767ddbc57adbedc24da66e32"
 "checksum pulldown-cmark 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "eef52fac62d0ea7b9b4dc7da092aa64ea7ec3d90af6679422d3d7e0e14b6ee15"
+"checksum pulldown-cmark 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)" = "d1b74cc784b038a9921fd1a48310cc2e238101aa8ae0b94201e2d85121dd68b5"
 "checksum quick-error 1.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "9274b940887ce9addde99c4eee6b5c44cc494b182b97e73dc8ffdcb3397fd3f0"
 "checksum quine-mc_cluskey 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)" = "07589615d719a60c8dd8a4622e7946465dfef20d1a428f969e3443e7386d5f45"
 "checksum quote 0.3.15 (registry+https://github.com/rust-lang/crates.io-index)" = "7a6e920b65c65f10b2ae65c831a81a073a89edd28c7cce89475bff467ab4167a"
@@ -4293,6 +4307,7 @@
 "checksum typenum 1.10.0 (registry+https://github.com/rust-lang/crates.io-index)" = "612d636f949607bdf9b123b4a6f6d966dedf3ff669f7f045890d3a4a73948169"
 "checksum ucd-trie 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "71a9c5b1fe77426cf144cc30e49e955270f5086e31a6441dfa8b32efc09b9d77"
 "checksum ucd-util 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "535c204ee4d8434478593480b8f86ab45ec9aae0e83c568ca81abf0fd0e88f86"
+"checksum unicase 2.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "41d17211f887da8e4a70a45b9536f26fc5de166b81e2d5d80de4a17fd22553bd"
 "checksum unicode-bidi 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)" = "49f2bd0c6468a8230e1db229cff8029217cf623c767ea5d60bfbd42729ea54d5"
 "checksum unicode-normalization 0.1.7 (registry+https://github.com/rust-lang/crates.io-index)" = "6a0180bc61fc5a987082bfa111f4cc95c4caff7f9799f3e46df09163a937aa25"
 "checksum unicode-segmentation 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "aa6024fc12ddfd1c6dbc14a80fa2324d4568849869b779f6bd37e5e4c03344d1"
diff --git a/src/librustc_interface/passes.rs b/src/librustc_interface/passes.rs
index 2f01254..fddf706 100644
--- a/src/librustc_interface/passes.rs
+++ b/src/librustc_interface/passes.rs
@@ -966,8 +966,7 @@
     time(sess, "layout testing", || layout_test::test_layout(tcx));
 
     // Avoid overwhelming user with errors if borrow checking failed.
-    // I'm not sure how helpful this is, to be honest, but it avoids
-    // a
+    // I'm not sure how helpful this is, to be honest, but it avoids a
     // lot of annoying errors in the compile-fail tests (basically,
     // lint warnings and so on -- kindck used to do this abort, but
     // kindck is gone now). -nmatsakis
diff --git a/src/librustc_typeck/lib.rs b/src/librustc_typeck/lib.rs
index 9bc221f..95f7c29 100644
--- a/src/librustc_typeck/lib.rs
+++ b/src/librustc_typeck/lib.rs
@@ -357,12 +357,10 @@
     time(tcx.sess, "wf checking", || check::check_wf_new(tcx))?;
 
     time(tcx.sess, "item-types checking", || {
-        tcx.sess.track_errors(|| {
-            for &module in tcx.hir().krate().modules.keys() {
-                tcx.ensure().check_mod_item_types(tcx.hir().local_def_id(module));
-            }
-        })
-    })?;
+        for &module in tcx.hir().krate().modules.keys() {
+            tcx.ensure().check_mod_item_types(tcx.hir().local_def_id(module));
+        }
+    });
 
     time(tcx.sess, "item-bodies checking", || tcx.typeck_item_bodies(LOCAL_CRATE));
 
diff --git a/src/librustdoc/Cargo.toml b/src/librustdoc/Cargo.toml
index 4d2c03a..4941867 100644
--- a/src/librustdoc/Cargo.toml
+++ b/src/librustdoc/Cargo.toml
@@ -9,7 +9,7 @@
 path = "lib.rs"
 
 [dependencies]
-pulldown-cmark = { version = "0.1.2", default-features = false }
+pulldown-cmark = { version = "0.4.1", default-features = false }
 minifier = "0.0.29"
 tempfile = "3"
 parking_lot = "0.7"
diff --git a/src/librustdoc/html/markdown.rs b/src/librustdoc/html/markdown.rs
index a70fe36..a3b041c 100644
--- a/src/librustdoc/html/markdown.rs
+++ b/src/librustdoc/html/markdown.rs
@@ -33,8 +33,11 @@
 use crate::html::highlight;
 use crate::test;
 
-use pulldown_cmark::{html, Event, Tag, Parser};
-use pulldown_cmark::{Options, OPTION_ENABLE_FOOTNOTES, OPTION_ENABLE_TABLES};
+use pulldown_cmark::{html, CowStr, Event, Options, Parser, Tag};
+
+fn opts() -> Options {
+    Options::ENABLE_TABLES | Options::ENABLE_FOOTNOTES
+}
 
 /// A unit struct which has the `fmt::Display` trait implemented. When
 /// formatted, this struct will emit the HTML corresponding to the rendered
@@ -297,12 +300,11 @@
 
     fn next(&mut self) -> Option<Self::Item> {
         let event = self.inner.next();
-        if let Some(Event::Start(Tag::Link(dest, text))) = event {
-            if let Some(&(_, ref replace)) = self.links.into_iter().find(|link| &*link.0 == &*dest)
-            {
-                Some(Event::Start(Tag::Link(replace.to_owned().into(), text)))
+        if let Some(Event::Start(Tag::Link(kind, dest, text))) = event {
+            if let Some(&(_, ref replace)) = self.links.iter().find(|link| link.0 == *dest) {
+                Some(Event::Start(Tag::Link(kind, replace.to_owned().into(), text)))
             } else {
-                Some(Event::Start(Tag::Link(dest, text)))
+                Some(Event::Start(Tag::Link(kind, dest, text)))
             }
         } else {
             event
@@ -393,7 +395,7 @@
         | Tag::Emphasis
         | Tag::Strong
         | Tag::Code
-        | Tag::Link(_, _)
+        | Tag::Link(..)
         | Tag::BlockQuote => true,
         _ => false,
     }
@@ -520,63 +522,39 @@
     }
 }
 
-pub struct TestableCodeError(());
-
-impl fmt::Display for TestableCodeError {
-    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
-        write!(f, "invalid start of a new code block")
-    }
-}
-
-pub fn find_testable_code<T: test::Tester>(
-    doc: &str,
-    tests: &mut T,
-    error_codes: ErrorCodes,
-) -> Result<(), TestableCodeError> {
+pub fn find_testable_code<T: test::Tester>(doc: &str, tests: &mut T, error_codes: ErrorCodes) {
     let mut parser = Parser::new(doc);
     let mut prev_offset = 0;
     let mut nb_lines = 0;
     let mut register_header = None;
-    'main: while let Some(event) = parser.next() {
+    while let Some(event) = parser.next() {
         match event {
             Event::Start(Tag::CodeBlock(s)) => {
+                let offset = parser.get_offset();
+
                 let block_info = if s.is_empty() {
                     LangString::all_false()
                 } else {
                     LangString::parse(&*s, error_codes)
                 };
                 if !block_info.rust {
-                    continue
+                    continue;
                 }
                 let mut test_s = String::new();
-                let mut offset = None;
-                loop {
-                    let event = parser.next();
-                    if let Some(event) = event {
-                        match event {
-                            Event::End(Tag::CodeBlock(_)) => break,
-                            Event::Text(ref s) => {
-                                test_s.push_str(s);
-                                if offset.is_none() {
-                                    offset = Some(parser.get_offset());
-                                }
-                            }
-                            _ => {}
-                        }
-                    } else {
-                        break 'main;
-                    }
+
+                while let Some(Event::Text(s)) = parser.next() {
+                    test_s.push_str(&s);
                 }
-                if let Some(offset) = offset {
-                    let lines = test_s.lines().map(|l| map_line(l).for_code());
-                    let text = lines.collect::<Vec<Cow<'_, str>>>().join("\n");
-                    nb_lines += doc[prev_offset..offset].lines().count();
-                    let line = tests.get_line() + (nb_lines - 1);
-                    tests.add_test(text, block_info, line);
-                    prev_offset = offset;
-                } else {
-                    return Err(TestableCodeError(()));
-                }
+
+                let text = test_s
+                    .lines()
+                    .map(|l| map_line(l).for_code())
+                    .collect::<Vec<Cow<'_, str>>>()
+                    .join("\n");
+                nb_lines += doc[prev_offset..offset].lines().count();
+                let line = tests.get_line() + nb_lines;
+                tests.add_test(text, block_info, line);
+                prev_offset = offset;
             }
             Event::Start(Tag::Header(level)) => {
                 register_header = Some(level as u32);
@@ -593,7 +571,6 @@
             _ => {}
         }
     }
-    Ok(())
 }
 
 #[derive(Eq, PartialEq, Clone, Debug)]
@@ -687,10 +664,6 @@
 
         // This is actually common enough to special-case
         if md.is_empty() { return Ok(()) }
-        let mut opts = Options::empty();
-        opts.insert(OPTION_ENABLE_TABLES);
-        opts.insert(OPTION_ENABLE_FOOTNOTES);
-
         let replacer = |_: &str, s: &str| {
             if let Some(&(_, ref replace)) = links.into_iter().find(|link| &*link.0 == s) {
                 Some((replace.clone(), s.to_owned()))
@@ -699,7 +672,7 @@
             }
         };
 
-        let p = Parser::new_with_broken_link_callback(md, opts, Some(&replacer));
+        let p = Parser::new_with_broken_link_callback(md, opts(), Some(&replacer));
 
         let mut s = String::with_capacity(md.len() * 3 / 2);
 
@@ -718,11 +691,7 @@
         let MarkdownWithToc(md, ref ids, codes) = *self;
         let mut ids = ids.borrow_mut();
 
-        let mut opts = Options::empty();
-        opts.insert(OPTION_ENABLE_TABLES);
-        opts.insert(OPTION_ENABLE_FOOTNOTES);
-
-        let p = Parser::new_ext(md, opts);
+        let p = Parser::new_ext(md, opts());
 
         let mut s = String::with_capacity(md.len() * 3 / 2);
 
@@ -748,11 +717,7 @@
 
         // This is actually common enough to special-case
         if md.is_empty() { return Ok(()) }
-        let mut opts = Options::empty();
-        opts.insert(OPTION_ENABLE_TABLES);
-        opts.insert(OPTION_ENABLE_FOOTNOTES);
-
-        let p = Parser::new_ext(md, opts);
+        let p = Parser::new_ext(md, opts());
 
         // Treat inline HTML as plain text.
         let p = p.map(|event| match event {
@@ -868,10 +833,6 @@
         return vec![];
     }
 
-    let mut opts = Options::empty();
-    opts.insert(OPTION_ENABLE_TABLES);
-    opts.insert(OPTION_ENABLE_FOOTNOTES);
-
     let mut links = vec![];
     let shortcut_links = RefCell::new(vec![]);
 
@@ -894,8 +855,7 @@
             shortcut_links.borrow_mut().push((s.to_owned(), locate(s)));
             None
         };
-        let p = Parser::new_with_broken_link_callback(md, opts,
-            Some(&push));
+        let p = Parser::new_with_broken_link_callback(md, opts(), Some(&push));
 
         // There's no need to thread an IdMap through to here because
         // the IDs generated aren't going to be emitted anywhere.
@@ -903,11 +863,11 @@
         let iter = Footnotes::new(HeadingLinks::new(p, None, &mut ids));
 
         for ev in iter {
-            if let Event::Start(Tag::Link(dest, _)) = ev {
+            if let Event::Start(Tag::Link(_, dest, _)) = ev {
                 debug!("found link: {}", dest);
                 links.push(match dest {
-                    Cow::Borrowed(s) => (s.to_owned(), locate(s)),
-                    Cow::Owned(s) => (s, None),
+                    CowStr::Borrowed(s) => (s.to_owned(), locate(s)),
+                    s @ CowStr::Boxed(..) | s @ CowStr::Inlined(..) => (s.into_string(), None),
                 });
             }
         }
@@ -939,10 +899,7 @@
         return code_blocks;
     }
 
-    let mut opts = Options::empty();
-    opts.insert(OPTION_ENABLE_TABLES);
-    opts.insert(OPTION_ENABLE_FOOTNOTES);
-    let mut p = Parser::new_ext(md, opts);
+    let mut p = Parser::new_ext(md, opts());
 
     let mut code_block_start = 0;
     let mut code_start = 0;
@@ -1013,7 +970,7 @@
                         end: code_end,
                     },
                     syntax: if !syntax.is_empty() {
-                        Some(syntax.into_owned())
+                        Some(syntax.into_string())
                     } else {
                         None
                     },
diff --git a/src/librustdoc/markdown.rs b/src/librustdoc/markdown.rs
index a2e2303..c496dde 100644
--- a/src/librustdoc/markdown.rs
+++ b/src/librustdoc/markdown.rs
@@ -143,10 +143,9 @@
                                        options.linker, options.edition, options.persist_doctests);
     collector.set_position(DUMMY_SP);
     let codes = ErrorCodes::from(UnstableFeatures::from_environment().is_nightly_build());
-    let res = find_testable_code(&input_str, &mut collector, codes);
-    if let Err(err) = res {
-        diag.span_warn(DUMMY_SP, &err.to_string());
-    }
+
+    find_testable_code(&input_str, &mut collector, codes);
+
     options.test_args.insert(0, "rustdoctest".to_string());
     testing::test_main(&options.test_args, collector.tests,
                        testing::Options::new().display_output(options.display_warnings));
diff --git a/src/librustdoc/passes/mod.rs b/src/librustdoc/passes/mod.rs
index 3c403d4..99aca06 100644
--- a/src/librustdoc/passes/mod.rs
+++ b/src/librustdoc/passes/mod.rs
@@ -333,24 +333,24 @@
         found_tests: 0,
     };
 
-    if find_testable_code(&dox, &mut tests, ErrorCodes::No).is_ok() {
-        if check_missing_code == true && tests.found_tests == 0 {
-            let mut diag = cx.tcx.struct_span_lint_hir(
-                lint::builtin::MISSING_DOC_CODE_EXAMPLES,
-                hir::CRATE_HIR_ID,
-                span_of_attrs(&item.attrs),
-                "Missing code example in this documentation");
-            diag.emit();
-        } else if check_missing_code == false &&
-                  tests.found_tests > 0 &&
-                  !cx.renderinfo.borrow().access_levels.is_doc_reachable(item.def_id) {
-            let mut diag = cx.tcx.struct_span_lint_hir(
-                lint::builtin::PRIVATE_DOC_TESTS,
-                hir::CRATE_HIR_ID,
-                span_of_attrs(&item.attrs),
-                "Documentation test in private item");
-            diag.emit();
-        }
+    find_testable_code(&dox, &mut tests, ErrorCodes::No);
+
+    if check_missing_code == true && tests.found_tests == 0 {
+        let mut diag = cx.tcx.struct_span_lint_hir(
+            lint::builtin::MISSING_DOC_CODE_EXAMPLES,
+            hir::CRATE_HIR_ID,
+            span_of_attrs(&item.attrs),
+            "Missing code example in this documentation");
+        diag.emit();
+    } else if check_missing_code == false &&
+              tests.found_tests > 0 &&
+              !cx.renderinfo.borrow().access_levels.is_doc_reachable(item.def_id) {
+        let mut diag = cx.tcx.struct_span_lint_hir(
+            lint::builtin::PRIVATE_DOC_TESTS,
+            hir::CRATE_HIR_ID,
+            span_of_attrs(&item.attrs),
+            "Documentation test in private item");
+        diag.emit();
     }
 }
 
diff --git a/src/librustdoc/test.rs b/src/librustdoc/test.rs
index abf7415..8492986 100644
--- a/src/librustdoc/test.rs
+++ b/src/librustdoc/test.rs
@@ -796,11 +796,7 @@
         // anything else, this will combine them for us.
         if let Some(doc) = attrs.collapsed_doc_value() {
             self.collector.set_position(attrs.span.unwrap_or(DUMMY_SP));
-            let res = markdown::find_testable_code(&doc, self.collector, self.codes);
-            if let Err(err) = res {
-                self.sess.diagnostic().span_warn(attrs.span.unwrap_or(DUMMY_SP),
-                    &err.to_string());
-            }
+            markdown::find_testable_code(&doc, self.collector, self.codes);
         }
 
         nested(self);
diff --git a/src/libstd/sys/unix/fs.rs b/src/libstd/sys/unix/fs.rs
index a14db10..761f1d8 100644
--- a/src/libstd/sys/unix/fs.rs
+++ b/src/libstd/sys/unix/fs.rs
@@ -526,8 +526,15 @@
     }
 
     pub fn fsync(&self) -> io::Result<()> {
-        cvt_r(|| unsafe { libc::fsync(self.0.raw()) })?;
-        Ok(())
+        cvt_r(|| unsafe { os_fsync(self.0.raw()) })?;
+        return Ok(());
+
+        #[cfg(any(target_os = "macos", target_os = "ios"))]
+        unsafe fn os_fsync(fd: c_int) -> c_int {
+            libc::fcntl(fd, libc::F_FULLFSYNC)
+        }
+        #[cfg(not(any(target_os = "macos", target_os = "ios")))]
+        unsafe fn os_fsync(fd: c_int) -> c_int { libc::fsync(fd) }
     }
 
     pub fn datasync(&self) -> io::Result<()> {
diff --git a/src/rustc/rustc.rs b/src/rustc/rustc.rs
index 626fceb..4a1786f 100644
--- a/src/rustc/rustc.rs
+++ b/src/rustc/rustc.rs
@@ -1,4 +1,3 @@
-
 fn main() {
     // Pull in jemalloc when enabled.
     //
diff --git a/src/test/incremental/change_name_of_static_in_fn.rs b/src/test/incremental/change_name_of_static_in_fn.rs
index 5b27b68..fd16ad2 100644
--- a/src/test/incremental/change_name_of_static_in_fn.rs
+++ b/src/test/incremental/change_name_of_static_in_fn.rs
@@ -1,4 +1,3 @@
-
 // revisions:rpass1 rpass2 rpass3
 
 // See issue #57692.
diff --git a/src/test/run-make-fulldeps/lto-dylib-dep/a_dylib.rs b/src/test/run-make-fulldeps/lto-dylib-dep/a_dylib.rs
index c5a3529..e63457e 100644
--- a/src/test/run-make-fulldeps/lto-dylib-dep/a_dylib.rs
+++ b/src/test/run-make-fulldeps/lto-dylib-dep/a_dylib.rs
@@ -1,4 +1,3 @@
-
 pub fn foo() {
     println!("bar");
 }
diff --git a/src/test/run-make-fulldeps/lto-dylib-dep/main.rs b/src/test/run-make-fulldeps/lto-dylib-dep/main.rs
index af0955e..4fb3c47 100644
--- a/src/test/run-make-fulldeps/lto-dylib-dep/main.rs
+++ b/src/test/run-make-fulldeps/lto-dylib-dep/main.rs
@@ -1,4 +1,3 @@
-
 extern crate a_dylib;
 
 fn main() {
diff --git a/src/test/run-make-fulldeps/rustdoc-error-lines/Makefile b/src/test/run-make-fulldeps/rustdoc-error-lines/Makefile
index e09343a..c9d41f0 100644
--- a/src/test/run-make-fulldeps/rustdoc-error-lines/Makefile
+++ b/src/test/run-make-fulldeps/rustdoc-error-lines/Makefile
@@ -5,4 +5,9 @@
 
 all:
 	$(RUSTDOC) --test input.rs > $(TMPDIR)/output || true
+	$(CGREP) 'input.rs - foo (line 5)' < $(TMPDIR)/output
 	$(CGREP) 'input.rs:7:15' < $(TMPDIR)/output
+	$(CGREP) 'input.rs - bar (line 15)' < $(TMPDIR)/output
+	$(CGREP) 'input.rs:17:15' < $(TMPDIR)/output
+	$(CGREP) 'input.rs - bar (line 24)' < $(TMPDIR)/output
+	$(CGREP) 'input.rs:26:15' < $(TMPDIR)/output
diff --git a/src/test/run-make-fulldeps/rustdoc-error-lines/input.rs b/src/test/run-make-fulldeps/rustdoc-error-lines/input.rs
index 7b07f38..2d29fa8 100644
--- a/src/test/run-make-fulldeps/rustdoc-error-lines/input.rs
+++ b/src/test/run-make-fulldeps/rustdoc-error-lines/input.rs
@@ -9,3 +9,20 @@
 pub fn foo() {
 
 }
+
+/// Add some text around the test...
+///
+/// ```rust
+/// #![feature(nll)]
+/// let x: char = 1;
+/// ```
+///
+/// ...to make sure that the line number is still correct.
+///
+/// Let's also add a second test in the same doc comment.
+///
+/// ```rust
+/// #![feature(nll)]
+/// let x: char = 1;
+/// ```
+pub fn bar() {}
diff --git a/src/test/run-pass/coherence/auxiliary/re_rebalance_coherence_lib.rs b/src/test/run-pass/coherence/auxiliary/re_rebalance_coherence_lib.rs
index c8d027b..41b9d64 100644
--- a/src/test/run-pass/coherence/auxiliary/re_rebalance_coherence_lib.rs
+++ b/src/test/run-pass/coherence/auxiliary/re_rebalance_coherence_lib.rs
@@ -1,5 +1,4 @@
-
-pub trait Backend{}
+pub trait Backend {}
 pub trait SupportsDefaultKeyword {}
 
 impl SupportsDefaultKeyword for Postgres {}
diff --git a/src/test/ui/c-variadic/variadic-ffi-1.rs b/src/test/ui/c-variadic/variadic-ffi-1.rs
index 61b2ad4..6a3ff24 100644
--- a/src/test/ui/c-variadic/variadic-ffi-1.rs
+++ b/src/test/ui/c-variadic/variadic-ffi-1.rs
@@ -12,20 +12,18 @@
 extern "C" fn bar(f: isize, x: u8) {}
 
 fn main() {
-    // errors below are no longer checked because error above aborts
-    // compilation; see variadic-ffi-3.rs for corresponding test.
     unsafe {
-        foo();
-        foo(1);
+        foo();  //~ ERROR this function takes at least 2 parameters but 0 parameters were supplied
+        foo(1); //~ ERROR this function takes at least 2 parameters but 1 parameter was supplied
 
-        let x: unsafe extern "C" fn(f: isize, x: u8) = foo;
-        let y: extern "C" fn(f: isize, x: u8, ...) = bar;
+        let x: unsafe extern "C" fn(f: isize, x: u8) = foo; //~ ERROR mismatched types
+        let y: extern "C" fn(f: isize, x: u8, ...) = bar; //~ ERROR mismatched types
 
-        foo(1, 2, 3f32);
-        foo(1, 2, true);
-        foo(1, 2, 1i8);
-        foo(1, 2, 1u8);
-        foo(1, 2, 1i16);
-        foo(1, 2, 1u16);
+        foo(1, 2, 3f32); //~ ERROR can't pass
+        foo(1, 2, true); //~ ERROR can't pass
+        foo(1, 2, 1i8);  //~ ERROR can't pass
+        foo(1, 2, 1u8);  //~ ERROR can't pass
+        foo(1, 2, 1i16); //~ ERROR can't pass
+        foo(1, 2, 1u16); //~ ERROR can't pass
     }
 }
diff --git a/src/test/ui/c-variadic/variadic-ffi-1.stderr b/src/test/ui/c-variadic/variadic-ffi-1.stderr
index 1a2bb44..e16d15a 100644
--- a/src/test/ui/c-variadic/variadic-ffi-1.stderr
+++ b/src/test/ui/c-variadic/variadic-ffi-1.stderr
@@ -4,6 +4,79 @@
 LL |     fn printf(_: *const u8, ...);
    |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ C-variadics require C or cdecl calling convention
 
-error: aborting due to previous error
+error[E0060]: this function takes at least 2 parameters but 0 parameters were supplied
+  --> $DIR/variadic-ffi-1.rs:16:9
+   |
+LL |     fn foo(f: isize, x: u8, ...);
+   |     ----------------------------- defined here
+...
+LL |         foo();
+   |         ^^^^^ expected at least 2 parameters
 
-For more information about this error, try `rustc --explain E0045`.
+error[E0060]: this function takes at least 2 parameters but 1 parameter was supplied
+  --> $DIR/variadic-ffi-1.rs:17:9
+   |
+LL |     fn foo(f: isize, x: u8, ...);
+   |     ----------------------------- defined here
+...
+LL |         foo(1);
+   |         ^^^^^^ expected at least 2 parameters
+
+error[E0308]: mismatched types
+  --> $DIR/variadic-ffi-1.rs:19:56
+   |
+LL |         let x: unsafe extern "C" fn(f: isize, x: u8) = foo;
+   |                                                        ^^^ expected non-variadic fn, found variadic function
+   |
+   = note: expected type `unsafe extern "C" fn(isize, u8)`
+              found type `for<'r> unsafe extern "C" fn(isize, u8, std::ffi::VaList<'r>, ...) {foo}`
+
+error[E0308]: mismatched types
+  --> $DIR/variadic-ffi-1.rs:20:54
+   |
+LL |         let y: extern "C" fn(f: isize, x: u8, ...) = bar;
+   |                                                      ^^^ expected variadic fn, found non-variadic function
+   |
+   = note: expected type `for<'r> extern "C" fn(isize, u8, std::ffi::VaList<'r>, ...)`
+              found type `extern "C" fn(isize, u8) {bar}`
+
+error[E0617]: can't pass `f32` to variadic function
+  --> $DIR/variadic-ffi-1.rs:22:19
+   |
+LL |         foo(1, 2, 3f32);
+   |                   ^^^^ help: cast the value to `c_double`: `3f32 as c_double`
+
+error[E0617]: can't pass `bool` to variadic function
+  --> $DIR/variadic-ffi-1.rs:23:19
+   |
+LL |         foo(1, 2, true);
+   |                   ^^^^ help: cast the value to `c_int`: `true as c_int`
+
+error[E0617]: can't pass `i8` to variadic function
+  --> $DIR/variadic-ffi-1.rs:24:19
+   |
+LL |         foo(1, 2, 1i8);
+   |                   ^^^ help: cast the value to `c_int`: `1i8 as c_int`
+
+error[E0617]: can't pass `u8` to variadic function
+  --> $DIR/variadic-ffi-1.rs:25:19
+   |
+LL |         foo(1, 2, 1u8);
+   |                   ^^^ help: cast the value to `c_uint`: `1u8 as c_uint`
+
+error[E0617]: can't pass `i16` to variadic function
+  --> $DIR/variadic-ffi-1.rs:26:19
+   |
+LL |         foo(1, 2, 1i16);
+   |                   ^^^^ help: cast the value to `c_int`: `1i16 as c_int`
+
+error[E0617]: can't pass `u16` to variadic function
+  --> $DIR/variadic-ffi-1.rs:27:19
+   |
+LL |         foo(1, 2, 1u16);
+   |                   ^^^^ help: cast the value to `c_uint`: `1u16 as c_uint`
+
+error: aborting due to 11 previous errors
+
+Some errors have detailed explanations: E0045, E0060, E0308, E0617.
+For more information about an error, try `rustc --explain E0045`.
diff --git a/src/test/ui/c-variadic/variadic-ffi-3.rs b/src/test/ui/c-variadic/variadic-ffi-3.rs
deleted file mode 100644
index c02d1f5..0000000
--- a/src/test/ui/c-variadic/variadic-ffi-3.rs
+++ /dev/null
@@ -1,29 +0,0 @@
-extern {
-    fn foo(f: isize, x: u8, ...);
-    //~^ defined here
-    //~| defined here
-}
-
-extern "C" fn bar(f: isize, x: u8) {}
-
-fn main() {
-    unsafe {
-        foo(); //~ ERROR: this function takes at least 2 parameters but 0 parameters were supplied
-        foo(1); //~ ERROR: this function takes at least 2 parameters but 1 parameter was supplied
-
-        let x: unsafe extern "C" fn(f: isize, x: u8) = foo;
-        //~^ ERROR: mismatched types
-        //~| expected type `unsafe extern "C" fn(isize, u8)`
-
-        let y: extern "C" fn(f: isize, x: u8, ...) = bar;
-        //~^ ERROR: mismatched types
-        //~| expected type `for<'r> extern "C" fn(isize, u8, std::ffi::VaList<'r>, ...)`
-
-        foo(1, 2, 3f32); //~ ERROR can't pass `f32` to variadic function
-        foo(1, 2, true); //~ ERROR can't pass `bool` to variadic function
-        foo(1, 2, 1i8); //~ ERROR can't pass `i8` to variadic function
-        foo(1, 2, 1u8); //~ ERROR can't pass `u8` to variadic function
-        foo(1, 2, 1i16); //~ ERROR can't pass `i16` to variadic function
-        foo(1, 2, 1u16); //~ ERROR can't pass `u16` to variadic function
-    }
-}
diff --git a/src/test/ui/c-variadic/variadic-ffi-3.stderr b/src/test/ui/c-variadic/variadic-ffi-3.stderr
deleted file mode 100644
index 2876225..0000000
--- a/src/test/ui/c-variadic/variadic-ffi-3.stderr
+++ /dev/null
@@ -1,76 +0,0 @@
-error[E0060]: this function takes at least 2 parameters but 0 parameters were supplied
-  --> $DIR/variadic-ffi-3.rs:11:9
-   |
-LL |     fn foo(f: isize, x: u8, ...);
-   |     ----------------------------- defined here
-...
-LL |         foo();
-   |         ^^^^^ expected at least 2 parameters
-
-error[E0060]: this function takes at least 2 parameters but 1 parameter was supplied
-  --> $DIR/variadic-ffi-3.rs:12:9
-   |
-LL |     fn foo(f: isize, x: u8, ...);
-   |     ----------------------------- defined here
-...
-LL |         foo(1);
-   |         ^^^^^^ expected at least 2 parameters
-
-error[E0308]: mismatched types
-  --> $DIR/variadic-ffi-3.rs:14:56
-   |
-LL |         let x: unsafe extern "C" fn(f: isize, x: u8) = foo;
-   |                                                        ^^^ expected non-variadic fn, found variadic function
-   |
-   = note: expected type `unsafe extern "C" fn(isize, u8)`
-              found type `for<'r> unsafe extern "C" fn(isize, u8, std::ffi::VaList<'r>, ...) {foo}`
-
-error[E0308]: mismatched types
-  --> $DIR/variadic-ffi-3.rs:18:54
-   |
-LL |         let y: extern "C" fn(f: isize, x: u8, ...) = bar;
-   |                                                      ^^^ expected variadic fn, found non-variadic function
-   |
-   = note: expected type `for<'r> extern "C" fn(isize, u8, std::ffi::VaList<'r>, ...)`
-              found type `extern "C" fn(isize, u8) {bar}`
-
-error[E0617]: can't pass `f32` to variadic function
-  --> $DIR/variadic-ffi-3.rs:22:19
-   |
-LL |         foo(1, 2, 3f32);
-   |                   ^^^^ help: cast the value to `c_double`: `3f32 as c_double`
-
-error[E0617]: can't pass `bool` to variadic function
-  --> $DIR/variadic-ffi-3.rs:23:19
-   |
-LL |         foo(1, 2, true);
-   |                   ^^^^ help: cast the value to `c_int`: `true as c_int`
-
-error[E0617]: can't pass `i8` to variadic function
-  --> $DIR/variadic-ffi-3.rs:24:19
-   |
-LL |         foo(1, 2, 1i8);
-   |                   ^^^ help: cast the value to `c_int`: `1i8 as c_int`
-
-error[E0617]: can't pass `u8` to variadic function
-  --> $DIR/variadic-ffi-3.rs:25:19
-   |
-LL |         foo(1, 2, 1u8);
-   |                   ^^^ help: cast the value to `c_uint`: `1u8 as c_uint`
-
-error[E0617]: can't pass `i16` to variadic function
-  --> $DIR/variadic-ffi-3.rs:26:19
-   |
-LL |         foo(1, 2, 1i16);
-   |                   ^^^^ help: cast the value to `c_int`: `1i16 as c_int`
-
-error[E0617]: can't pass `u16` to variadic function
-  --> $DIR/variadic-ffi-3.rs:27:19
-   |
-LL |         foo(1, 2, 1u16);
-   |                   ^^^^ help: cast the value to `c_uint`: `1u16 as c_uint`
-
-error: aborting due to 10 previous errors
-
-Some errors have detailed explanations: E0060, E0308, E0617.
-For more information about an error, try `rustc --explain E0060`.
diff --git a/src/test/ui/coherence/auxiliary/re_rebalance_coherence_lib.rs b/src/test/ui/coherence/auxiliary/re_rebalance_coherence_lib.rs
index c8d027b..41b9d64 100644
--- a/src/test/ui/coherence/auxiliary/re_rebalance_coherence_lib.rs
+++ b/src/test/ui/coherence/auxiliary/re_rebalance_coherence_lib.rs
@@ -1,5 +1,4 @@
-
-pub trait Backend{}
+pub trait Backend {}
 pub trait SupportsDefaultKeyword {}
 
 impl SupportsDefaultKeyword for Postgres {}
diff --git a/src/test/ui/e0119/conflict-with-std.rs b/src/test/ui/e0119/conflict-with-std.rs
index 6dc81f3..c9db2ba 100644
--- a/src/test/ui/e0119/conflict-with-std.rs
+++ b/src/test/ui/e0119/conflict-with-std.rs
@@ -1,4 +1,3 @@
-
 use std::marker::PhantomData;
 use std::convert::{TryFrom, AsRef};
 
diff --git a/src/test/ui/e0119/conflict-with-std.stderr b/src/test/ui/e0119/conflict-with-std.stderr
index 8c12b3d..3e0c71e 100644
--- a/src/test/ui/e0119/conflict-with-std.stderr
+++ b/src/test/ui/e0119/conflict-with-std.stderr
@@ -1,5 +1,5 @@
 error[E0119]: conflicting implementations of trait `std::convert::AsRef<Q>` for type `std::boxed::Box<Q>`:
-  --> $DIR/conflict-with-std.rs:6:1
+  --> $DIR/conflict-with-std.rs:5:1
    |
 LL | impl AsRef<Q> for Box<Q> {
    | ^^^^^^^^^^^^^^^^^^^^^^^^
@@ -9,7 +9,7 @@
              where T: ?Sized;
 
 error[E0119]: conflicting implementations of trait `std::convert::From<S>` for type `S`:
-  --> $DIR/conflict-with-std.rs:13:1
+  --> $DIR/conflict-with-std.rs:12:1
    |
 LL | impl From<S> for S {
    | ^^^^^^^^^^^^^^^^^^
@@ -18,7 +18,7 @@
            - impl<T> std::convert::From<T> for T;
 
 error[E0119]: conflicting implementations of trait `std::convert::TryFrom<X>` for type `X`:
-  --> $DIR/conflict-with-std.rs:20:1
+  --> $DIR/conflict-with-std.rs:19:1
    |
 LL | impl TryFrom<X> for X {
    | ^^^^^^^^^^^^^^^^^^^^^
diff --git a/src/test/ui/feature-gates/auxiliary/re_rebalance_coherence_lib.rs b/src/test/ui/feature-gates/auxiliary/re_rebalance_coherence_lib.rs
index c8d027b..41b9d64 100644
--- a/src/test/ui/feature-gates/auxiliary/re_rebalance_coherence_lib.rs
+++ b/src/test/ui/feature-gates/auxiliary/re_rebalance_coherence_lib.rs
@@ -1,5 +1,4 @@
-
-pub trait Backend{}
+pub trait Backend {}
 pub trait SupportsDefaultKeyword {}
 
 impl SupportsDefaultKeyword for Postgres {}
diff --git a/src/test/ui/in-band-lifetimes/mismatched_trait_impl.rs b/src/test/ui/in-band-lifetimes/mismatched_trait_impl.rs
index 654d2bd..f2ba81a 100644
--- a/src/test/ui/in-band-lifetimes/mismatched_trait_impl.rs
+++ b/src/test/ui/in-band-lifetimes/mismatched_trait_impl.rs
@@ -7,7 +7,7 @@
 
 impl Get for i32 {
     fn foo(&self, x: &u32, y: &'a u32) -> &'a u32 { //~ ERROR cannot infer
-        x
+        x //~ ERROR lifetime mismatch
     }
 }
 
diff --git a/src/test/ui/in-band-lifetimes/mismatched_trait_impl.stderr b/src/test/ui/in-band-lifetimes/mismatched_trait_impl.stderr
index cd65bab..80f15b7 100644
--- a/src/test/ui/in-band-lifetimes/mismatched_trait_impl.stderr
+++ b/src/test/ui/in-band-lifetimes/mismatched_trait_impl.stderr
@@ -20,5 +20,15 @@
            expected fn(&i32, &'a u32, &u32) -> &'a u32
               found fn(&i32, &u32, &u32) -> &u32
 
-error: aborting due to previous error
+error[E0623]: lifetime mismatch
+  --> $DIR/mismatched_trait_impl.rs:10:9
+   |
+LL |     fn foo(&self, x: &u32, y: &'a u32) -> &'a u32 {
+   |                      ----                 -------
+   |                      |
+   |                      this parameter and the return type are declared with different lifetimes...
+LL |         x
+   |         ^ ...but data from `x` is returned here
+
+error: aborting due to 2 previous errors
 
diff --git a/src/test/ui/infinite/infinite-tag-type-recursion.rs b/src/test/ui/infinite/infinite-tag-type-recursion.rs
index 87a9e08..bbfaaa6 100644
--- a/src/test/ui/infinite/infinite-tag-type-recursion.rs
+++ b/src/test/ui/infinite/infinite-tag-type-recursion.rs
@@ -1,4 +1,5 @@
 enum MList { Cons(isize, MList), Nil }
 //~^ ERROR recursive type `MList` has infinite size
+//~| ERROR cycle detected when processing `MList`
 
 fn main() { let a = MList::Cons(10, MList::Cons(11, MList::Nil)); }
diff --git a/src/test/ui/infinite/infinite-tag-type-recursion.stderr b/src/test/ui/infinite/infinite-tag-type-recursion.stderr
index 88dad00..8f6529d 100644
--- a/src/test/ui/infinite/infinite-tag-type-recursion.stderr
+++ b/src/test/ui/infinite/infinite-tag-type-recursion.stderr
@@ -8,6 +8,16 @@
    |
    = help: insert indirection (e.g., a `Box`, `Rc`, or `&`) at some point to make `MList` representable
 
-error: aborting due to previous error
+error[E0391]: cycle detected when processing `MList`
+  --> $DIR/infinite-tag-type-recursion.rs:1:1
+   |
+LL | enum MList { Cons(isize, MList), Nil }
+   | ^^^^^^^^^^
+   |
+   = note: ...which again requires processing `MList`, completing the cycle
+   = note: cycle used when computing dropck types for `Canonical { max_universe: U0, variables: [], value: ParamEnvAnd { param_env: ParamEnv { caller_bounds: [], reveal: UserFacing, def_id: None }, value: MList } }`
 
-For more information about this error, try `rustc --explain E0072`.
+error: aborting due to 2 previous errors
+
+Some errors have detailed explanations: E0072, E0391.
+For more information about an error, try `rustc --explain E0072`.
diff --git a/src/test/ui/issues/issue-16048.rs b/src/test/ui/issues/issue-16048.rs
index 5910481..7d24f3a 100644
--- a/src/test/ui/issues/issue-16048.rs
+++ b/src/test/ui/issues/issue-16048.rs
@@ -22,6 +22,8 @@
     //~^ ERROR E0195
     //~| NOTE lifetimes do not match method in trait
         return *self as T;
+        //~^ ERROR non-primitive cast: `Foo<'a>` as `T`
+        //~| NOTE an `as` expression can only be used to convert between primitive types.
     }
 }
 
diff --git a/src/test/ui/issues/issue-16048.stderr b/src/test/ui/issues/issue-16048.stderr
index 18e59bd..a137bcd 100644
--- a/src/test/ui/issues/issue-16048.stderr
+++ b/src/test/ui/issues/issue-16048.stderr
@@ -7,6 +7,15 @@
 LL |     fn get<'p, T : Test<'a>>(&self) -> T {
    |           ^^^^^^^^^^^^^^^^^^ lifetimes do not match method in trait
 
-error: aborting due to previous error
+error[E0605]: non-primitive cast: `Foo<'a>` as `T`
+  --> $DIR/issue-16048.rs:24:16
+   |
+LL |         return *self as T;
+   |                ^^^^^^^^^^
+   |
+   = note: an `as` expression can only be used to convert between primitive types. Consider using the `From` trait
 
-For more information about this error, try `rustc --explain E0195`.
+error: aborting due to 2 previous errors
+
+Some errors have detailed explanations: E0195, E0605.
+For more information about an error, try `rustc --explain E0195`.
diff --git a/src/test/ui/mod-subitem-as-enum-variant.rs b/src/test/ui/mod-subitem-as-enum-variant.rs
index cd4459a..9328d1a 100644
--- a/src/test/ui/mod-subitem-as-enum-variant.rs
+++ b/src/test/ui/mod-subitem-as-enum-variant.rs
@@ -1,4 +1,3 @@
-
 mod Mod {
     pub struct FakeVariant<T>(pub T);
 }
diff --git a/src/test/ui/mod-subitem-as-enum-variant.stderr b/src/test/ui/mod-subitem-as-enum-variant.stderr
index 72eca58..d6815c9 100644
--- a/src/test/ui/mod-subitem-as-enum-variant.stderr
+++ b/src/test/ui/mod-subitem-as-enum-variant.stderr
@@ -1,5 +1,5 @@
 error[E0109]: type arguments are not allowed for this type
-  --> $DIR/mod-subitem-as-enum-variant.rs:8:11
+  --> $DIR/mod-subitem-as-enum-variant.rs:7:11
    |
 LL |     Mod::<i32>::FakeVariant(0);
    |           ^^^ type argument not allowed
diff --git a/src/test/ui/rfc-1937-termination-trait/termination-trait-test-wrong-type.rs b/src/test/ui/rfc-1937-termination-trait/termination-trait-test-wrong-type.rs
index c648f542..193a523 100644
--- a/src/test/ui/rfc-1937-termination-trait/termination-trait-test-wrong-type.rs
+++ b/src/test/ui/rfc-1937-termination-trait/termination-trait-test-wrong-type.rs
@@ -1,8 +1,8 @@
 // compile-flags: --test
 
-use std::num::ParseIntError;
+use std::num::ParseFloatError;
 
 #[test]
-fn can_parse_zero_as_f32() -> Result<f32, ParseIntError> { //~ ERROR
+fn can_parse_zero_as_f32() -> Result<f32, ParseFloatError> { //~ ERROR
     "0".parse()
 }
diff --git a/src/test/ui/rfc-1937-termination-trait/termination-trait-test-wrong-type.stderr b/src/test/ui/rfc-1937-termination-trait/termination-trait-test-wrong-type.stderr
index 1811554..f253b67 100644
--- a/src/test/ui/rfc-1937-termination-trait/termination-trait-test-wrong-type.stderr
+++ b/src/test/ui/rfc-1937-termination-trait/termination-trait-test-wrong-type.stderr
@@ -1,12 +1,12 @@
-error[E0277]: `main` has invalid return type `std::result::Result<f32, std::num::ParseIntError>`
+error[E0277]: `main` has invalid return type `std::result::Result<f32, std::num::ParseFloatError>`
   --> $DIR/termination-trait-test-wrong-type.rs:6:1
    |
-LL | / fn can_parse_zero_as_f32() -> Result<f32, ParseIntError> {
+LL | / fn can_parse_zero_as_f32() -> Result<f32, ParseFloatError> {
 LL | |     "0".parse()
 LL | | }
    | |_^ `main` can only return types that implement `std::process::Termination`
    |
-   = help: the trait `std::process::Termination` is not implemented for `std::result::Result<f32, std::num::ParseIntError>`
+   = help: the trait `std::process::Termination` is not implemented for `std::result::Result<f32, std::num::ParseFloatError>`
    = note: required by `test::assert_test_result`
 
 error: aborting due to previous error
diff --git a/src/test/ui/structs/struct-base-wrong-type-2.rs b/src/test/ui/structs/struct-base-wrong-type-2.rs
deleted file mode 100644
index 562f75b..0000000
--- a/src/test/ui/structs/struct-base-wrong-type-2.rs
+++ /dev/null
@@ -1,19 +0,0 @@
-// Check that `base` in `Fru { field: expr, ..base }` must have right type.
-//
-// See also struct-base-wrong-type.rs, which tests same condition
-// within a const expression.
-
-struct Foo { a: isize, b: isize }
-struct Bar { x: isize }
-
-fn main() {
-    let b = Bar { x: 5 };
-    let f = Foo { a: 2, ..b }; //~  ERROR mismatched types
-                               //~| expected type `Foo`
-                               //~| found type `Bar`
-                               //~| expected struct `Foo`, found struct `Bar`
-    let f__isize = Foo { a: 2, ..4 }; //~  ERROR mismatched types
-                                 //~| expected type `Foo`
-                                 //~| found type `{integer}`
-                                 //~| expected struct `Foo`, found integer
-}
diff --git a/src/test/ui/structs/struct-base-wrong-type-2.stderr b/src/test/ui/structs/struct-base-wrong-type-2.stderr
deleted file mode 100644
index d02ed20..0000000
--- a/src/test/ui/structs/struct-base-wrong-type-2.stderr
+++ /dev/null
@@ -1,21 +0,0 @@
-error[E0308]: mismatched types
-  --> $DIR/struct-base-wrong-type-2.rs:11:27
-   |
-LL |     let f = Foo { a: 2, ..b };
-   |                           ^ expected struct `Foo`, found struct `Bar`
-   |
-   = note: expected type `Foo`
-              found type `Bar`
-
-error[E0308]: mismatched types
-  --> $DIR/struct-base-wrong-type-2.rs:15:34
-   |
-LL |     let f__isize = Foo { a: 2, ..4 };
-   |                                  ^ expected struct `Foo`, found integer
-   |
-   = note: expected type `Foo`
-              found type `{integer}`
-
-error: aborting due to 2 previous errors
-
-For more information about this error, try `rustc --explain E0308`.
diff --git a/src/test/ui/structs/struct-base-wrong-type.rs b/src/test/ui/structs/struct-base-wrong-type.rs
index 6252673..b64c6b4 100644
--- a/src/test/ui/structs/struct-base-wrong-type.rs
+++ b/src/test/ui/structs/struct-base-wrong-type.rs
@@ -1,27 +1,14 @@
 // Check that `base` in `Fru { field: expr, ..base }` must have right type.
-//
-// See also struct-base-wrong-type-2.rs, which tests same condition
-// within a function body.
 
 struct Foo { a: isize, b: isize }
 struct Bar { x: isize }
 
 static bar: Bar = Bar { x: 5 };
 static foo: Foo = Foo { a: 2, ..bar }; //~  ERROR mismatched types
-                                       //~| expected type `Foo`
-                                       //~| found type `Bar`
-                                       //~| expected struct `Foo`, found struct `Bar`
 static foo_i: Foo = Foo { a: 2, ..4 }; //~  ERROR mismatched types
-                                       //~| expected type `Foo`
-                                       //~| found type `{integer}`
-                                       //~| expected struct `Foo`, found integer
 
 fn main() {
     let b = Bar { x: 5 };
-    // errors below are no longer caught since error above causes
-    // compilation to abort before we bother checking function bodies.
-    // See also struct-base-wrong-type-2.rs, which checks that we
-    // would catch these errors eventually.
-    let f = Foo { a: 2, ..b };
-    let f__isize = Foo { a: 2, ..4 };
+    let f = Foo { a: 2, ..b };        //~ ERROR mismatched types
+    let f__isize = Foo { a: 2, ..4 }; //~ ERROR mismatched types
 }
diff --git a/src/test/ui/structs/struct-base-wrong-type.stderr b/src/test/ui/structs/struct-base-wrong-type.stderr
index 2491296..a021630 100644
--- a/src/test/ui/structs/struct-base-wrong-type.stderr
+++ b/src/test/ui/structs/struct-base-wrong-type.stderr
@@ -1,5 +1,5 @@
 error[E0308]: mismatched types
-  --> $DIR/struct-base-wrong-type.rs:10:33
+  --> $DIR/struct-base-wrong-type.rs:7:33
    |
 LL | static foo: Foo = Foo { a: 2, ..bar };
    |                                 ^^^ expected struct `Foo`, found struct `Bar`
@@ -8,7 +8,7 @@
               found type `Bar`
 
 error[E0308]: mismatched types
-  --> $DIR/struct-base-wrong-type.rs:14:35
+  --> $DIR/struct-base-wrong-type.rs:8:35
    |
 LL | static foo_i: Foo = Foo { a: 2, ..4 };
    |                                   ^ expected struct `Foo`, found integer
@@ -16,6 +16,24 @@
    = note: expected type `Foo`
               found type `{integer}`
 
-error: aborting due to 2 previous errors
+error[E0308]: mismatched types
+  --> $DIR/struct-base-wrong-type.rs:12:27
+   |
+LL |     let f = Foo { a: 2, ..b };
+   |                           ^ expected struct `Foo`, found struct `Bar`
+   |
+   = note: expected type `Foo`
+              found type `Bar`
+
+error[E0308]: mismatched types
+  --> $DIR/struct-base-wrong-type.rs:13:34
+   |
+LL |     let f__isize = Foo { a: 2, ..4 };
+   |                                  ^ expected struct `Foo`, found integer
+   |
+   = note: expected type `Foo`
+              found type `{integer}`
+
+error: aborting due to 4 previous errors
 
 For more information about this error, try `rustc --explain E0308`.
diff --git a/src/test/ui/wrong-mul-method-signature.rs b/src/test/ui/wrong-mul-method-signature.rs
index 54e2af5..1c2f865 100644
--- a/src/test/ui/wrong-mul-method-signature.rs
+++ b/src/test/ui/wrong-mul-method-signature.rs
@@ -61,9 +61,8 @@
     let x: Vec1 = Vec1 { x: 1.0 } * 2.0; // this is OK
 
     let x: Vec2 = Vec2 { x: 1.0, y: 2.0 } * 2.0; // trait had reversed order
-    // (we no longer signal a compile error here, since the
-    //  error in the trait signature will cause compilation to
-    //  abort before we bother looking at function bodies.)
+    //~^ ERROR mismatched types
+    //~| ERROR mismatched types
 
     let x: i32 = Vec3 { x: 1.0, y: 2.0, z: 3.0 } * 2.0;
 }
diff --git a/src/test/ui/wrong-mul-method-signature.stderr b/src/test/ui/wrong-mul-method-signature.stderr
index 8630ebc..2317bf8 100644
--- a/src/test/ui/wrong-mul-method-signature.stderr
+++ b/src/test/ui/wrong-mul-method-signature.stderr
@@ -25,6 +25,25 @@
    = note: expected type `fn(Vec3, f64) -> i32`
               found type `fn(Vec3, f64) -> f64`
 
-error: aborting due to 3 previous errors
+error[E0308]: mismatched types
+  --> $DIR/wrong-mul-method-signature.rs:63:45
+   |
+LL |     let x: Vec2 = Vec2 { x: 1.0, y: 2.0 } * 2.0; // trait had reversed order
+   |                                             ^^^ expected struct `Vec2`, found floating-point number
+   |
+   = note: expected type `Vec2`
+              found type `{float}`
 
-For more information about this error, try `rustc --explain E0053`.
+error[E0308]: mismatched types
+  --> $DIR/wrong-mul-method-signature.rs:63:19
+   |
+LL |     let x: Vec2 = Vec2 { x: 1.0, y: 2.0 } * 2.0; // trait had reversed order
+   |                   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected struct `Vec2`, found f64
+   |
+   = note: expected type `Vec2`
+              found type `f64`
+
+error: aborting due to 5 previous errors
+
+Some errors have detailed explanations: E0053, E0308.
+For more information about an error, try `rustc --explain E0053`.
diff --git a/src/tools/tidy/src/style.rs b/src/tools/tidy/src/style.rs
index eeddddf..fb2bfb1 100644
--- a/src/tools/tidy/src/style.rs
+++ b/src/tools/tidy/src/style.rs
@@ -112,6 +112,7 @@
         let skip_length = contents.contains("ignore-tidy-linelength");
         let skip_end_whitespace = contents.contains("ignore-tidy-end-whitespace");
         let skip_copyright = contents.contains("ignore-tidy-copyright");
+        let mut leading_new_lines = false;
         let mut trailing_new_lines = 0;
         for (i, line) in contents.split('\n').enumerate() {
             let mut err = |msg: &str| {
@@ -152,11 +153,17 @@
                 err(LLVM_UNREACHABLE_INFO);
             }
             if line.is_empty() {
+                if i == 0 {
+                    leading_new_lines = true;
+                }
                 trailing_new_lines += 1;
             } else {
                 trailing_new_lines = 0;
             }
         }
+        if leading_new_lines {
+            tidy_error!(bad, "{}: leading newline", file.display());
+        }
         match trailing_new_lines {
             0 => tidy_error!(bad, "{}: missing trailing newline", file.display()),
             1 => {}