From 3b686d5c251be3354d53c08c5a0c1f46894627a6 Mon Sep 17 00:00:00 2001
From: Andy Russell <arussell123@gmail.com>
Date: Thu, 4 Apr 2019 00:43:58 -0400
Subject: [PATCH 01/13] tweak unresolved label suggestion

Only suggest label names in the same hygiene context, and use a
structured suggestion.
---
 src/librustc_resolve/lib.rs                   | 15 +++++++++++++--
 src/test/ui/hygiene/hygienic-label-1.stderr   |  2 +-
 src/test/ui/hygiene/hygienic-label-2.stderr   |  2 +-
 src/test/ui/hygiene/hygienic-label-3.stderr   |  2 +-
 src/test/ui/hygiene/hygienic-label-4.stderr   |  2 +-
 src/test/ui/suggestions/suggest-labels.stderr | 18 +++++++++++++++---
 6 files changed, 32 insertions(+), 9 deletions(-)

diff --git a/src/librustc_resolve/lib.rs b/src/librustc_resolve/lib.rs
index 1934f800af757..0c37296d2411b 100644
--- a/src/librustc_resolve/lib.rs
+++ b/src/librustc_resolve/lib.rs
@@ -357,7 +357,12 @@ fn resolve_struct_error<'sess, 'a>(resolver: &'sess Resolver<'_>,
                                            "use of undeclared label `{}`",
                                            name);
             if let Some(lev_candidate) = lev_candidate {
-                err.span_label(span, format!("did you mean `{}`?", lev_candidate));
+                err.span_suggestion(
+                    span,
+                    "a label with a similar name exists in this scope",
+                    lev_candidate.to_string(),
+                    Applicability::MaybeIncorrect,
+                );
             } else {
                 err.span_label(span, format!("undeclared label `{}`", name));
             }
@@ -4218,7 +4223,13 @@ impl<'a> Resolver<'a> {
                         // Picks the first label that is "close enough", which is not necessarily
                         // the closest match
                         let close_match = self.search_label(label.ident, |rib, ident| {
-                            let names = rib.bindings.iter().map(|(id, _)| &id.name);
+                            let names = rib.bindings.iter().filter_map(|(id, _)| {
+                                if id.span.ctxt() == label.ident.span.ctxt() {
+                                    Some(&id.name)
+                                } else {
+                                    None
+                                }
+                            });
                             find_best_match_for_name(names, &*ident.as_str(), None)
                         });
                         self.record_def(expr.id, err_path_resolution());
diff --git a/src/test/ui/hygiene/hygienic-label-1.stderr b/src/test/ui/hygiene/hygienic-label-1.stderr
index 80cd1547b45e7..d61c0687c1665 100644
--- a/src/test/ui/hygiene/hygienic-label-1.stderr
+++ b/src/test/ui/hygiene/hygienic-label-1.stderr
@@ -2,7 +2,7 @@ error[E0426]: use of undeclared label `'x`
   --> $DIR/hygienic-label-1.rs:2:19
    |
 LL |     () => { break 'x; }
-   |                   ^^ did you mean `'x`?
+   |                   ^^ undeclared label `'x`
 ...
 LL |     'x: loop { foo!() }
    |                ------ in this macro invocation
diff --git a/src/test/ui/hygiene/hygienic-label-2.stderr b/src/test/ui/hygiene/hygienic-label-2.stderr
index c20cbd9f68791..f23e741debe9d 100644
--- a/src/test/ui/hygiene/hygienic-label-2.stderr
+++ b/src/test/ui/hygiene/hygienic-label-2.stderr
@@ -2,7 +2,7 @@ error[E0426]: use of undeclared label `'x`
   --> $DIR/hygienic-label-2.rs:6:16
    |
 LL |     foo!(break 'x);
-   |                ^^ did you mean `'x`?
+   |                ^^ undeclared label `'x`
 
 error: aborting due to previous error
 
diff --git a/src/test/ui/hygiene/hygienic-label-3.stderr b/src/test/ui/hygiene/hygienic-label-3.stderr
index b5839fe5c3d23..0c4173a61aac4 100644
--- a/src/test/ui/hygiene/hygienic-label-3.stderr
+++ b/src/test/ui/hygiene/hygienic-label-3.stderr
@@ -2,7 +2,7 @@ error[E0426]: use of undeclared label `'x`
   --> $DIR/hygienic-label-3.rs:2:19
    |
 LL |     () => { break 'x; }
-   |                   ^^ did you mean `'x`?
+   |                   ^^ undeclared label `'x`
 ...
 LL |         foo!()
    |         ------ in this macro invocation
diff --git a/src/test/ui/hygiene/hygienic-label-4.stderr b/src/test/ui/hygiene/hygienic-label-4.stderr
index 1dd7489574622..1c93da02f6142 100644
--- a/src/test/ui/hygiene/hygienic-label-4.stderr
+++ b/src/test/ui/hygiene/hygienic-label-4.stderr
@@ -2,7 +2,7 @@ error[E0426]: use of undeclared label `'x`
   --> $DIR/hygienic-label-4.rs:6:16
    |
 LL |     foo!(break 'x);
-   |                ^^ did you mean `'x`?
+   |                ^^ undeclared label `'x`
 
 error: aborting due to previous error
 
diff --git a/src/test/ui/suggestions/suggest-labels.stderr b/src/test/ui/suggestions/suggest-labels.stderr
index ead8f94209bdc..02d46a3f59607 100644
--- a/src/test/ui/suggestions/suggest-labels.stderr
+++ b/src/test/ui/suggestions/suggest-labels.stderr
@@ -2,19 +2,31 @@ error[E0426]: use of undeclared label `'fo`
   --> $DIR/suggest-labels.rs:4:15
    |
 LL |         break 'fo;
-   |               ^^^ did you mean `'foo`?
+   |               ^^^
+help: a label with a similar name exists in this scope
+   |
+LL |         break 'foo;
+   |               ^^^^
 
 error[E0426]: use of undeclared label `'bor`
   --> $DIR/suggest-labels.rs:8:18
    |
 LL |         continue 'bor;
-   |                  ^^^^ did you mean `'bar`?
+   |                  ^^^^
+help: a label with a similar name exists in this scope
+   |
+LL |         continue 'bar;
+   |                  ^^^^
 
 error[E0426]: use of undeclared label `'longlable`
   --> $DIR/suggest-labels.rs:13:19
    |
 LL |             break 'longlable;
-   |                   ^^^^^^^^^^ did you mean `'longlabel1`?
+   |                   ^^^^^^^^^^
+help: a label with a similar name exists in this scope
+   |
+LL |             break 'longlabel1;
+   |                   ^^^^^^^^^^^
 
 error: aborting due to 3 previous errors
 

From 553ec5d3eb8af66f86599b0abb0efda74393921e Mon Sep 17 00:00:00 2001
From: Michael Woerister <michaelwoerister@posteo>
Date: Wed, 17 Apr 2019 12:53:02 +0200
Subject: [PATCH 02/13] Update run-make PGO test to new commandline syntax.

---
 src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile b/src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile
index dc52e91317a5a..e22fac25cf7a4 100644
--- a/src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile
+++ b/src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile
@@ -2,7 +2,7 @@
 
 all:
 ifeq ($(PROFILER_SUPPORT),1)
-	$(RUSTC) -O -Ccodegen-units=1 -Z pgo-gen="$(TMPDIR)/test.profraw" --emit=llvm-ir test.rs
+	$(RUSTC) -O -Ccodegen-units=1 -Z pgo-gen="$(TMPDIR)" --emit=llvm-ir test.rs
 	# We expect symbols starting with "__llvm_profile_".
 	$(CGREP) "__llvm_profile_" < $(TMPDIR)/test.ll
 	# We do NOT expect the "__imp_" version of these symbols.

From 4269be382fdf1ac92665234502bab33ef9c0d8fa Mon Sep 17 00:00:00 2001
From: Michael Woerister <michaelwoerister@posteo>
Date: Thu, 18 Apr 2019 15:21:05 +0200
Subject: [PATCH 03/13] Prefix PROFILER_SUPPORT and SANITIZER_SUPPORT test env
 vars with RUSTC_ to make things clearer.

---
 src/bootstrap/test.rs                                         | 4 ++--
 src/test/run-make-fulldeps/pgo-gen-lto/Makefile               | 2 +-
 src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile    | 2 +-
 src/test/run-make-fulldeps/pgo-gen/Makefile                   | 2 +-
 src/test/run-make-fulldeps/profile/Makefile                   | 2 +-
 src/test/run-make-fulldeps/sanitizer-address/Makefile         | 4 ++--
 src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile     | 2 +-
 src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile      | 2 +-
 .../run-make-fulldeps/sanitizer-invalid-cratetype/Makefile    | 4 ++--
 src/test/run-make-fulldeps/sanitizer-leak/Makefile            | 2 +-
 src/test/run-make-fulldeps/sanitizer-memory/Makefile          | 2 +-
 src/test/run-make-fulldeps/sanitizer-staticlib-link/Makefile  | 4 ++--
 12 files changed, 16 insertions(+), 16 deletions(-)

diff --git a/src/bootstrap/test.rs b/src/bootstrap/test.rs
index c552f607960b4..a443b7b5863e5 100644
--- a/src/bootstrap/test.rs
+++ b/src/bootstrap/test.rs
@@ -1268,11 +1268,11 @@ impl Step for Compiletest {
         builder.add_rust_test_threads(&mut cmd);
 
         if builder.config.sanitizers {
-            cmd.env("SANITIZER_SUPPORT", "1");
+            cmd.env("RUSTC_SANITIZER_SUPPORT", "1");
         }
 
         if builder.config.profiler {
-            cmd.env("PROFILER_SUPPORT", "1");
+            cmd.env("RUSTC_PROFILER_SUPPORT", "1");
         }
 
         cmd.env("RUST_TEST_TMPDIR", builder.out.join("tmp"));
diff --git a/src/test/run-make-fulldeps/pgo-gen-lto/Makefile b/src/test/run-make-fulldeps/pgo-gen-lto/Makefile
index 7c19961b1e420..d6e45d838535f 100644
--- a/src/test/run-make-fulldeps/pgo-gen-lto/Makefile
+++ b/src/test/run-make-fulldeps/pgo-gen-lto/Makefile
@@ -1,7 +1,7 @@
 -include ../tools.mk
 
 all:
-ifeq ($(PROFILER_SUPPORT),1)
+ifeq ($(RUSTC_PROFILER_SUPPORT),1)
 	$(RUSTC) -Copt-level=3 -Clto=fat -Z pgo-gen="$(TMPDIR)" test.rs
 	$(call RUN,test) || exit 1
 	[ -e "$(TMPDIR)"/default_*.profraw ] || (echo "No .profraw file"; exit 1)
diff --git a/src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile b/src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile
index e22fac25cf7a4..bfb57bfeefe5c 100644
--- a/src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile
+++ b/src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile
@@ -1,7 +1,7 @@
 -include ../tools.mk
 
 all:
-ifeq ($(PROFILER_SUPPORT),1)
+ifeq ($(RUSTC_PROFILER_SUPPORT),1)
 	$(RUSTC) -O -Ccodegen-units=1 -Z pgo-gen="$(TMPDIR)" --emit=llvm-ir test.rs
 	# We expect symbols starting with "__llvm_profile_".
 	$(CGREP) "__llvm_profile_" < $(TMPDIR)/test.ll
diff --git a/src/test/run-make-fulldeps/pgo-gen/Makefile b/src/test/run-make-fulldeps/pgo-gen/Makefile
index 0469c4443d85a..28294f6e1d82d 100644
--- a/src/test/run-make-fulldeps/pgo-gen/Makefile
+++ b/src/test/run-make-fulldeps/pgo-gen/Makefile
@@ -1,7 +1,7 @@
 -include ../tools.mk
 
 all:
-ifeq ($(PROFILER_SUPPORT),1)
+ifeq ($(RUSTC_PROFILER_SUPPORT),1)
 	$(RUSTC) -g -Z pgo-gen="$(TMPDIR)" test.rs
 	$(call RUN,test) || exit 1
 	[ -e "$(TMPDIR)"/default_*.profraw ] || (echo "No .profraw file"; exit 1)
diff --git a/src/test/run-make-fulldeps/profile/Makefile b/src/test/run-make-fulldeps/profile/Makefile
index 7300bfc955363..880bc38f408e6 100644
--- a/src/test/run-make-fulldeps/profile/Makefile
+++ b/src/test/run-make-fulldeps/profile/Makefile
@@ -1,7 +1,7 @@
 -include ../tools.mk
 
 all:
-ifeq ($(PROFILER_SUPPORT),1)
+ifeq ($(RUSTC_PROFILER_SUPPORT),1)
 	$(RUSTC) -g -Z profile test.rs
 	$(call RUN,test) || exit 1
 	[ -e "$(TMPDIR)/test.gcno" ] || (echo "No .gcno file"; exit 1)
diff --git a/src/test/run-make-fulldeps/sanitizer-address/Makefile b/src/test/run-make-fulldeps/sanitizer-address/Makefile
index 207615bfbd5c6..5f3486a495be2 100644
--- a/src/test/run-make-fulldeps/sanitizer-address/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-address/Makefile
@@ -5,11 +5,11 @@ LOG := $(TMPDIR)/log.txt
 # NOTE the address sanitizer only supports x86_64 linux and macOS
 
 ifeq ($(TARGET),x86_64-apple-darwin)
-ASAN_SUPPORT=$(SANITIZER_SUPPORT)
+ASAN_SUPPORT=$(RUSTC_SANITIZER_SUPPORT)
 EXTRA_RUSTFLAG=-C rpath
 else
 ifeq ($(TARGET),x86_64-unknown-linux-gnu)
-ASAN_SUPPORT=$(SANITIZER_SUPPORT)
+ASAN_SUPPORT=$(RUSTC_SANITIZER_SUPPORT)
 
 # Apparently there are very specific Linux kernels, notably the one that's
 # currently on Travis CI, which contain a buggy commit that triggers failures in
diff --git a/src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile b/src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile
index 4b7fece36d92a..bb323d2a6341a 100644
--- a/src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile
@@ -8,7 +8,7 @@ LOG := $(TMPDIR)/log.txt
 # is correctly detected.
 
 ifeq ($(TARGET),x86_64-unknown-linux-gnu)
-ASAN_SUPPORT=$(SANITIZER_SUPPORT)
+ASAN_SUPPORT=$(RUSTC_SANITIZER_SUPPORT)
 
 # See comment in sanitizer-address/Makefile for why this is here
 EXTRA_RUSTFLAG=-C relocation-model=dynamic-no-pic
diff --git a/src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile b/src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile
index 97f6172142224..77f119d889967 100644
--- a/src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile
@@ -8,7 +8,7 @@ LOG := $(TMPDIR)/log.txt
 # is correctly detected.
 
 ifeq ($(TARGET),x86_64-unknown-linux-gnu)
-ASAN_SUPPORT=$(SANITIZER_SUPPORT)
+ASAN_SUPPORT=$(RUSTC_SANITIZER_SUPPORT)
 
 # See comment in sanitizer-address/Makefile for why this is here
 EXTRA_RUSTFLAG=-C relocation-model=dynamic-no-pic
diff --git a/src/test/run-make-fulldeps/sanitizer-invalid-cratetype/Makefile b/src/test/run-make-fulldeps/sanitizer-invalid-cratetype/Makefile
index dc37c0d0bc946..ac49e519c7b96 100644
--- a/src/test/run-make-fulldeps/sanitizer-invalid-cratetype/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-invalid-cratetype/Makefile
@@ -3,11 +3,11 @@
 # NOTE the address sanitizer only supports x86_64 linux and macOS
 
 ifeq ($(TARGET),x86_64-apple-darwin)
-ASAN_SUPPORT=$(SANITIZER_SUPPORT)
+ASAN_SUPPORT=$(RUSTC_SANITIZER_SUPPORT)
 EXTRA_RUSTFLAG=-C rpath
 else
 ifeq ($(TARGET),x86_64-unknown-linux-gnu)
-ASAN_SUPPORT=$(SANITIZER_SUPPORT)
+ASAN_SUPPORT=$(RUSTC_SANITIZER_SUPPORT)
 EXTRA_RUSTFLAG=
 endif
 endif
diff --git a/src/test/run-make-fulldeps/sanitizer-leak/Makefile b/src/test/run-make-fulldeps/sanitizer-leak/Makefile
index 0f3c18f9293f5..e84e1cbd2b61b 100644
--- a/src/test/run-make-fulldeps/sanitizer-leak/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-leak/Makefile
@@ -6,7 +6,7 @@
 # FIXME(#46126) ThinLTO for libstd broke this test
 
 all:
-ifdef SANITIZER_SUPPORT
+ifdef RUSTC_SANITIZER_SUPPORT
 	$(RUSTC) -C opt-level=1 -g -Z sanitizer=leak -Z print-link-args leak.rs | $(CGREP) librustc_lsan
 	$(TMPDIR)/leak 2>&1 | $(CGREP) 'detected memory leaks'
 endif
diff --git a/src/test/run-make-fulldeps/sanitizer-memory/Makefile b/src/test/run-make-fulldeps/sanitizer-memory/Makefile
index 718d9637ea06d..aca3591555cfd 100644
--- a/src/test/run-make-fulldeps/sanitizer-memory/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-memory/Makefile
@@ -4,7 +4,7 @@
 # only-x86_64
 
 all:
-ifdef SANITIZER_SUPPORT
+ifdef RUSTC_SANITIZER_SUPPORT
 	$(RUSTC) -g -Z sanitizer=memory -Z print-link-args uninit.rs | $(CGREP) librustc_msan
 	$(TMPDIR)/uninit 2>&1 | $(CGREP) use-of-uninitialized-value
 endif
diff --git a/src/test/run-make-fulldeps/sanitizer-staticlib-link/Makefile b/src/test/run-make-fulldeps/sanitizer-staticlib-link/Makefile
index 2b444d667bfa3..7a1b9509f4f98 100644
--- a/src/test/run-make-fulldeps/sanitizer-staticlib-link/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-staticlib-link/Makefile
@@ -1,11 +1,11 @@
 -include ../tools.mk
 
 # This test builds a staticlib, then an executable that links to it.
-# The staticlib and executable both  are compiled with address sanitizer, 
+# The staticlib and executable both  are compiled with address sanitizer,
 # and we assert that a fault in the staticlib is correctly detected.
 
 ifeq ($(TARGET),x86_64-unknown-linux-gnu)
-ASAN_SUPPORT=$(SANITIZER_SUPPORT)
+ASAN_SUPPORT=$(RUSTC_SANITIZER_SUPPORT)
 EXTRA_RUSTFLAG=
 endif
 

From 227be657cdeee2259199b24fb9691f7f8994c5e6 Mon Sep 17 00:00:00 2001
From: Michael Woerister <michaelwoerister@posteo>
Date: Thu, 18 Apr 2019 15:31:46 +0200
Subject: [PATCH 04/13] compiletest: Allow for tests requiring profiler-rt or
 sanitizer-rt support.

---
 src/tools/compiletest/src/header.rs | 21 +++++++++++++++++++++
 1 file changed, 21 insertions(+)

diff --git a/src/tools/compiletest/src/header.rs b/src/tools/compiletest/src/header.rs
index 64882c603bad3..fb6ada89171ab 100644
--- a/src/tools/compiletest/src/header.rs
+++ b/src/tools/compiletest/src/header.rs
@@ -88,6 +88,9 @@ impl EarlyProps {
             }
         }
 
+        let rustc_has_profiler_support = env::var_os("RUSTC_PROFILER_SUPPORT").is_some();
+        let rustc_has_sanitizer_support = env::var_os("RUSTC_SANITIZER_SUPPORT").is_some();
+
         iter_header(testfile, None, &mut |ln| {
             // we should check if any only-<platform> exists and if it exists
             // and does not matches the current platform, skip the test
@@ -116,6 +119,16 @@ impl EarlyProps {
                    config.parse_needs_matching_clang(ln) {
                     props.ignore = Ignore::Ignore;
                 }
+
+                if !rustc_has_profiler_support &&
+                   config.parse_needs_profiler_support(ln) {
+                    props.ignore = Ignore::Ignore;
+                }
+
+                if !rustc_has_sanitizer_support &&
+                   config.parse_needs_sanitizer_support(ln) {
+                    props.ignore = Ignore::Ignore;
+                }
             }
 
             if (config.mode == common::DebugInfoGdb || config.mode == common::DebugInfoBoth) &&
@@ -748,6 +761,14 @@ impl Config {
         self.parse_name_directive(line, "needs-matching-clang")
     }
 
+    fn parse_needs_profiler_support(&self, line: &str) -> bool {
+        self.parse_name_directive(line, "needs-profiler-support")
+    }
+
+    fn parse_needs_sanitizer_support(&self, line: &str) -> bool {
+        self.parse_name_directive(line, "needs-sanitizer-support")
+    }
+
     /// Parses a name-value directive which contains config-specific information, e.g., `ignore-x86`
     /// or `normalize-stderr-32bit`.
     fn parse_cfg_name_directive(&self, line: &str, prefix: &str) -> ParsedNameDirective {

From e2acaee8bb364197af2ab197f0f641e8f988ae04 Mon Sep 17 00:00:00 2001
From: Michael Woerister <michaelwoerister@posteo>
Date: Tue, 16 Apr 2019 13:54:01 +0200
Subject: [PATCH 05/13] Add codegen test that makes sure PGO instrumentation is
 emitted as expected.

---
 src/test/codegen/pgo-instrumentation.rs | 20 ++++++++++++++++++++
 1 file changed, 20 insertions(+)
 create mode 100644 src/test/codegen/pgo-instrumentation.rs

diff --git a/src/test/codegen/pgo-instrumentation.rs b/src/test/codegen/pgo-instrumentation.rs
new file mode 100644
index 0000000000000..8493ef565d888
--- /dev/null
+++ b/src/test/codegen/pgo-instrumentation.rs
@@ -0,0 +1,20 @@
+// Test that `-Zpgo-gen` creates expected instrumentation artifacts in LLVM IR.
+
+// needs-profiler-support
+// compile-flags: -Z pgo-gen -Ccodegen-units=1
+
+// CHECK: @__llvm_profile_raw_version =
+// CHECK: @__profc_{{.*}}pgo_instrumentation{{.*}}some_function{{.*}} = private global
+// CHECK: @__profd_{{.*}}pgo_instrumentation{{.*}}some_function{{.*}} = private global
+// CHECK: @__profc_{{.*}}pgo_instrumentation{{.*}}main{{.*}} = private global
+// CHECK: @__profd_{{.*}}pgo_instrumentation{{.*}}main{{.*}} = private global
+// CHECK: @__llvm_profile_filename = {{.*}}"default_%m.profraw\00"{{.*}}
+
+#[inline(never)]
+fn some_function() {
+
+}
+
+fn main() {
+    some_function();
+}

From cc77087d6f6143927d9fe98a07ca3d12b26ce474 Mon Sep 17 00:00:00 2001
From: Michael Woerister <michaelwoerister@posteo>
Date: Thu, 18 Apr 2019 15:49:41 +0200
Subject: [PATCH 06/13] Use new `needs-(profiler|sanitizer)-support`
 compiletest directive to clean up some run-make tests.

---
 src/test/run-make-fulldeps/pgo-gen-lto/Makefile             | 4 ++--
 src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile  | 4 ++--
 src/test/run-make-fulldeps/pgo-gen/Makefile                 | 4 ++--
 src/test/run-make-fulldeps/profile/Makefile                 | 4 ++--
 src/test/run-make-fulldeps/sanitizer-address/Makefile       | 6 ++----
 src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile   | 5 ++---
 src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile    | 6 ++----
 .../run-make-fulldeps/sanitizer-invalid-cratetype/Makefile  | 6 ++----
 src/test/run-make-fulldeps/sanitizer-leak/Makefile          | 3 +--
 src/test/run-make-fulldeps/sanitizer-memory/Makefile        | 3 +--
 .../run-make-fulldeps/sanitizer-staticlib-link/Makefile     | 5 ++---
 11 files changed, 20 insertions(+), 30 deletions(-)

diff --git a/src/test/run-make-fulldeps/pgo-gen-lto/Makefile b/src/test/run-make-fulldeps/pgo-gen-lto/Makefile
index d6e45d838535f..48181bcbdc6d3 100644
--- a/src/test/run-make-fulldeps/pgo-gen-lto/Makefile
+++ b/src/test/run-make-fulldeps/pgo-gen-lto/Makefile
@@ -1,8 +1,8 @@
+# needs-profiler-support
+
 -include ../tools.mk
 
 all:
-ifeq ($(RUSTC_PROFILER_SUPPORT),1)
 	$(RUSTC) -Copt-level=3 -Clto=fat -Z pgo-gen="$(TMPDIR)" test.rs
 	$(call RUN,test) || exit 1
 	[ -e "$(TMPDIR)"/default_*.profraw ] || (echo "No .profraw file"; exit 1)
-endif
diff --git a/src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile b/src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile
index bfb57bfeefe5c..20977edb88e87 100644
--- a/src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile
+++ b/src/test/run-make-fulldeps/pgo-gen-no-imp-symbols/Makefile
@@ -1,11 +1,11 @@
+# needs-profiler-support
+
 -include ../tools.mk
 
 all:
-ifeq ($(RUSTC_PROFILER_SUPPORT),1)
 	$(RUSTC) -O -Ccodegen-units=1 -Z pgo-gen="$(TMPDIR)" --emit=llvm-ir test.rs
 	# We expect symbols starting with "__llvm_profile_".
 	$(CGREP) "__llvm_profile_" < $(TMPDIR)/test.ll
 	# We do NOT expect the "__imp_" version of these symbols.
 	$(CGREP) -v "__imp___llvm_profile_" < $(TMPDIR)/test.ll # 64 bit
 	$(CGREP) -v "__imp____llvm_profile_" < $(TMPDIR)/test.ll # 32 bit
-endif
diff --git a/src/test/run-make-fulldeps/pgo-gen/Makefile b/src/test/run-make-fulldeps/pgo-gen/Makefile
index 28294f6e1d82d..ce44c10a7c2d2 100644
--- a/src/test/run-make-fulldeps/pgo-gen/Makefile
+++ b/src/test/run-make-fulldeps/pgo-gen/Makefile
@@ -1,8 +1,8 @@
+# needs-profiler-support
+
 -include ../tools.mk
 
 all:
-ifeq ($(RUSTC_PROFILER_SUPPORT),1)
 	$(RUSTC) -g -Z pgo-gen="$(TMPDIR)" test.rs
 	$(call RUN,test) || exit 1
 	[ -e "$(TMPDIR)"/default_*.profraw ] || (echo "No .profraw file"; exit 1)
-endif
diff --git a/src/test/run-make-fulldeps/profile/Makefile b/src/test/run-make-fulldeps/profile/Makefile
index 880bc38f408e6..c12712590e48f 100644
--- a/src/test/run-make-fulldeps/profile/Makefile
+++ b/src/test/run-make-fulldeps/profile/Makefile
@@ -1,9 +1,9 @@
+# needs-profiler-support
+
 -include ../tools.mk
 
 all:
-ifeq ($(RUSTC_PROFILER_SUPPORT),1)
 	$(RUSTC) -g -Z profile test.rs
 	$(call RUN,test) || exit 1
 	[ -e "$(TMPDIR)/test.gcno" ] || (echo "No .gcno file"; exit 1)
 	[ -e "$(TMPDIR)/test.gcda" ] || (echo "No .gcda file"; exit 1)
-endif
diff --git a/src/test/run-make-fulldeps/sanitizer-address/Makefile b/src/test/run-make-fulldeps/sanitizer-address/Makefile
index 5f3486a495be2..51d8a4a947adc 100644
--- a/src/test/run-make-fulldeps/sanitizer-address/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-address/Makefile
@@ -1,3 +1,5 @@
+# needs-sanitizer-support
+
 -include ../tools.mk
 
 LOG := $(TMPDIR)/log.txt
@@ -5,11 +7,9 @@ LOG := $(TMPDIR)/log.txt
 # NOTE the address sanitizer only supports x86_64 linux and macOS
 
 ifeq ($(TARGET),x86_64-apple-darwin)
-ASAN_SUPPORT=$(RUSTC_SANITIZER_SUPPORT)
 EXTRA_RUSTFLAG=-C rpath
 else
 ifeq ($(TARGET),x86_64-unknown-linux-gnu)
-ASAN_SUPPORT=$(RUSTC_SANITIZER_SUPPORT)
 
 # Apparently there are very specific Linux kernels, notably the one that's
 # currently on Travis CI, which contain a buggy commit that triggers failures in
@@ -23,7 +23,5 @@ endif
 endif
 
 all:
-ifeq ($(ASAN_SUPPORT),1)
 	$(RUSTC) -g -Z sanitizer=address -Z print-link-args $(EXTRA_RUSTFLAG) overflow.rs | $(CGREP) librustc_asan
 	$(TMPDIR)/overflow 2>&1 | $(CGREP) stack-buffer-overflow
-endif
diff --git a/src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile b/src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile
index bb323d2a6341a..36cde355468be 100644
--- a/src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile
@@ -1,3 +1,5 @@
+# needs-sanitizer-support
+
 -include ../tools.mk
 
 LOG := $(TMPDIR)/log.txt
@@ -8,15 +10,12 @@ LOG := $(TMPDIR)/log.txt
 # is correctly detected.
 
 ifeq ($(TARGET),x86_64-unknown-linux-gnu)
-ASAN_SUPPORT=$(RUSTC_SANITIZER_SUPPORT)
 
 # See comment in sanitizer-address/Makefile for why this is here
 EXTRA_RUSTFLAG=-C relocation-model=dynamic-no-pic
 endif
 
 all:
-ifeq ($(ASAN_SUPPORT),1)
 	$(RUSTC) -g -Z sanitizer=address --crate-type cdylib --target $(TARGET) $(EXTRA_RUSTFLAG) library.rs
 	$(RUSTC) -g -Z sanitizer=address --crate-type bin --target $(TARGET) $(EXTRA_RUSTFLAG) -llibrary program.rs
 	LD_LIBRARY_PATH=$(TMPDIR) $(TMPDIR)/program 2>&1 | $(CGREP) stack-buffer-overflow
-endif
diff --git a/src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile b/src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile
index 77f119d889967..b382ff5e7b24f 100644
--- a/src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile
@@ -1,3 +1,5 @@
+# needs-sanitizer-support
+
 -include ../tools.mk
 
 LOG := $(TMPDIR)/log.txt
@@ -8,15 +10,11 @@ LOG := $(TMPDIR)/log.txt
 # is correctly detected.
 
 ifeq ($(TARGET),x86_64-unknown-linux-gnu)
-ASAN_SUPPORT=$(RUSTC_SANITIZER_SUPPORT)
-
 # See comment in sanitizer-address/Makefile for why this is here
 EXTRA_RUSTFLAG=-C relocation-model=dynamic-no-pic
 endif
 
 all:
-ifeq ($(ASAN_SUPPORT),1)
 	$(RUSTC) -g -Z sanitizer=address --crate-type dylib --target $(TARGET) $(EXTRA_RUSTFLAG) library.rs
 	$(RUSTC) -g -Z sanitizer=address --crate-type bin --target $(TARGET) $(EXTRA_RUSTFLAG) -llibrary program.rs
 	LD_LIBRARY_PATH=$(TMPDIR) $(TMPDIR)/program 2>&1 | $(CGREP) stack-buffer-overflow
-endif
diff --git a/src/test/run-make-fulldeps/sanitizer-invalid-cratetype/Makefile b/src/test/run-make-fulldeps/sanitizer-invalid-cratetype/Makefile
index ac49e519c7b96..9581ac565ea02 100644
--- a/src/test/run-make-fulldeps/sanitizer-invalid-cratetype/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-invalid-cratetype/Makefile
@@ -1,18 +1,16 @@
+# needs-sanitizer-support
+
 -include ../tools.mk
 
 # NOTE the address sanitizer only supports x86_64 linux and macOS
 
 ifeq ($(TARGET),x86_64-apple-darwin)
-ASAN_SUPPORT=$(RUSTC_SANITIZER_SUPPORT)
 EXTRA_RUSTFLAG=-C rpath
 else
 ifeq ($(TARGET),x86_64-unknown-linux-gnu)
-ASAN_SUPPORT=$(RUSTC_SANITIZER_SUPPORT)
 EXTRA_RUSTFLAG=
 endif
 endif
 
 all:
-ifeq ($(ASAN_SUPPORT),1)
 	$(RUSTC) -Z sanitizer=address --crate-type proc-macro --target $(TARGET) hello.rs 2>&1 | $(CGREP) '-Z sanitizer'
-endif
diff --git a/src/test/run-make-fulldeps/sanitizer-leak/Makefile b/src/test/run-make-fulldeps/sanitizer-leak/Makefile
index e84e1cbd2b61b..101e8272ab91e 100644
--- a/src/test/run-make-fulldeps/sanitizer-leak/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-leak/Makefile
@@ -1,12 +1,11 @@
 -include ../tools.mk
 
+# needs-sanitizer-support
 # only-linux
 # only-x86_64
 # ignore-test
 # FIXME(#46126) ThinLTO for libstd broke this test
 
 all:
-ifdef RUSTC_SANITIZER_SUPPORT
 	$(RUSTC) -C opt-level=1 -g -Z sanitizer=leak -Z print-link-args leak.rs | $(CGREP) librustc_lsan
 	$(TMPDIR)/leak 2>&1 | $(CGREP) 'detected memory leaks'
-endif
diff --git a/src/test/run-make-fulldeps/sanitizer-memory/Makefile b/src/test/run-make-fulldeps/sanitizer-memory/Makefile
index aca3591555cfd..b3376f8a72358 100644
--- a/src/test/run-make-fulldeps/sanitizer-memory/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-memory/Makefile
@@ -1,10 +1,9 @@
 -include ../tools.mk
 
+# needs-sanitizer-support
 # only-linux
 # only-x86_64
 
 all:
-ifdef RUSTC_SANITIZER_SUPPORT
 	$(RUSTC) -g -Z sanitizer=memory -Z print-link-args uninit.rs | $(CGREP) librustc_msan
 	$(TMPDIR)/uninit 2>&1 | $(CGREP) use-of-uninitialized-value
-endif
diff --git a/src/test/run-make-fulldeps/sanitizer-staticlib-link/Makefile b/src/test/run-make-fulldeps/sanitizer-staticlib-link/Makefile
index 7a1b9509f4f98..8fa08688fdd71 100644
--- a/src/test/run-make-fulldeps/sanitizer-staticlib-link/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-staticlib-link/Makefile
@@ -1,3 +1,5 @@
+# needs-sanitizer-support
+
 -include ../tools.mk
 
 # This test builds a staticlib, then an executable that links to it.
@@ -5,14 +7,11 @@
 # and we assert that a fault in the staticlib is correctly detected.
 
 ifeq ($(TARGET),x86_64-unknown-linux-gnu)
-ASAN_SUPPORT=$(RUSTC_SANITIZER_SUPPORT)
 EXTRA_RUSTFLAG=
 endif
 
 all:
-ifeq ($(ASAN_SUPPORT),1)
 	$(RUSTC) -g -Z sanitizer=address --crate-type staticlib --target $(TARGET) library.rs
 	$(CC) program.c $(call STATICLIB,library) $(call OUT_EXE,program) $(EXTRACFLAGS) $(EXTRACXXFLAGS)
 	LD_LIBRARY_PATH=$(TMPDIR) $(TMPDIR)/program 2>&1 | $(CGREP) stack-buffer-overflow
-endif
 

From 7af0fccc88127619ec7e0fa695437525678db0b2 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Jakub=20K=C4=85dzio=C5=82ka?= <kuba@kadziolka.net>
Date: Tue, 23 Apr 2019 00:15:43 +0200
Subject: [PATCH 07/13] Reexport IntErrorKind in std

---
 src/libstd/lib.rs | 1 +
 src/libstd/num.rs | 6 ++++++
 2 files changed, 7 insertions(+)

diff --git a/src/libstd/lib.rs b/src/libstd/lib.rs
index 62bc1991cc93c..167c1f944d025 100644
--- a/src/libstd/lib.rs
+++ b/src/libstd/lib.rs
@@ -268,6 +268,7 @@
 #![feature(hash_raw_entry)]
 #![feature(hashmap_internals)]
 #![feature(int_error_internals)]
+#![feature(int_error_matching)]
 #![feature(integer_atomics)]
 #![feature(lang_items)]
 #![feature(libc)]
diff --git a/src/libstd/num.rs b/src/libstd/num.rs
index d67d0b55a799d..2a2ca0b5237ee 100644
--- a/src/libstd/num.rs
+++ b/src/libstd/num.rs
@@ -16,6 +16,12 @@ pub use core::num::{NonZeroU8, NonZeroU16, NonZeroU32, NonZeroU64, NonZeroU128,
 #[stable(feature = "signed_nonzero", since = "1.34.0")]
 pub use core::num::{NonZeroI8, NonZeroI16, NonZeroI32, NonZeroI64, NonZeroI128, NonZeroIsize};
 
+#[unstable(feature = "int_error_matching",
+           reason = "it can be useful to match errors when making error messages \
+                     for integer parsing",
+           issue = "22639")]
+pub use core::num::IntErrorKind;
+
 #[cfg(test)] use crate::fmt;
 #[cfg(test)] use crate::ops::{Add, Sub, Mul, Div, Rem};
 

From 4a073dda936b2bc594056dca43c3ea51479435fe Mon Sep 17 00:00:00 2001
From: Xavier Denis <xldenis@gmail.com>
Date: Tue, 16 Apr 2019 19:26:41 -0300
Subject: [PATCH 08/13] Fix #58270, fix off-by-one error in error diagnostics.

---
 src/librustc_errors/emitter.rs                         | 10 ++++++++++
 src/test/ui/issue-60075.stderr                         |  4 +---
 src/test/ui/issues/issue-58856-1.stderr                |  5 ++---
 .../ex3-both-anon-regions-both-are-structs-3.stderr    |  4 +---
 src/test/ui/parser/issue-10636-2.stderr                |  5 ++---
 ...ntravariant-use-covariant-in-second-position.stderr |  4 +---
 src/test/ui/resolve/token-error-correct-3.stderr       |  5 ++---
 7 files changed, 19 insertions(+), 18 deletions(-)

diff --git a/src/librustc_errors/emitter.rs b/src/librustc_errors/emitter.rs
index a1472479afa89..c3d594204f413 100644
--- a/src/librustc_errors/emitter.rs
+++ b/src/librustc_errors/emitter.rs
@@ -268,6 +268,7 @@ impl EmitterWriter {
                 // 6..7. This is degenerate input, but it's best to degrade
                 // gracefully -- and the parser likes to supply a span like
                 // that for EOF, in particular.
+
                 if lo.col_display == hi.col_display && lo.line == hi.line {
                     hi.col_display += 1;
                 }
@@ -547,6 +548,15 @@ impl EmitterWriter {
                     && j > i                      // multiline lines).
                     && p == 0  // We're currently on the first line, move the label one line down
                 {
+                    // If we're overlapping with an un-labelled annotation with the same span
+                    // we can just merge them in the output
+                    if next.start_col == annotation.start_col
+                    && next.end_col == annotation.end_col
+                    && !next.has_label()
+                    {
+                        continue;
+                    }
+
                     // This annotation needs a new line in the output.
                     p += 1;
                     break;
diff --git a/src/test/ui/issue-60075.stderr b/src/test/ui/issue-60075.stderr
index 244aef2d1f0f5..ac97d32a6e15b 100644
--- a/src/test/ui/issue-60075.stderr
+++ b/src/test/ui/issue-60075.stderr
@@ -11,9 +11,7 @@ LL |     fn qux() -> Option<usize> {
    |                               - unclosed delimiter
 LL |         let _ = if true {
 LL |         });
-   |           ^
-   |           |
-   |           help: `}` may belong here
+   |           ^ help: `}` may belong here
 
 error: expected identifier, found `;`
   --> $DIR/issue-60075.rs:6:11
diff --git a/src/test/ui/issues/issue-58856-1.stderr b/src/test/ui/issues/issue-58856-1.stderr
index 20cdf55365fc7..58ab0a142d6f1 100644
--- a/src/test/ui/issues/issue-58856-1.stderr
+++ b/src/test/ui/issues/issue-58856-1.stderr
@@ -2,9 +2,8 @@ error: expected one of `)`, `,`, or `:`, found `>`
   --> $DIR/issue-58856-1.rs:2:14
    |
 LL |     fn b(self>
-   |         -    ^
-   |         |    |
-   |         |    help: `)` may belong here
+   |         -    ^ help: `)` may belong here
+   |         |
    |         unclosed delimiter
 
 error: aborting due to previous error
diff --git a/src/test/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs-3.stderr b/src/test/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs-3.stderr
index 6484e63223eff..b49ee0cfc7033 100644
--- a/src/test/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs-3.stderr
+++ b/src/test/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs-3.stderr
@@ -2,9 +2,7 @@ error[E0623]: lifetime mismatch
   --> $DIR/ex3-both-anon-regions-both-are-structs-3.rs:7:11
    |
 LL | fn foo(mut x: Ref) {
-   |               ---
-   |               |
-   |               this type is declared with multiple lifetimes...
+   |               --- this type is declared with multiple lifetimes...
 LL |     x.a = x.b;
    |           ^^^ ...but data with one lifetime flows into the other here
 
diff --git a/src/test/ui/parser/issue-10636-2.stderr b/src/test/ui/parser/issue-10636-2.stderr
index 38d57ce572365..5b9a9b7f06c39 100644
--- a/src/test/ui/parser/issue-10636-2.stderr
+++ b/src/test/ui/parser/issue-10636-2.stderr
@@ -2,9 +2,8 @@ error: expected one of `)`, `,`, `.`, `?`, or an operator, found `;`
   --> $DIR/issue-10636-2.rs:5:25
    |
 LL |     option.map(|some| 42;
-   |               -         ^
-   |               |         |
-   |               |         help: `)` may belong here
+   |               -         ^ help: `)` may belong here
+   |               |
    |               unclosed delimiter
 
 error: expected expression, found `)`
diff --git a/src/test/ui/regions/regions-variance-contravariant-use-covariant-in-second-position.stderr b/src/test/ui/regions/regions-variance-contravariant-use-covariant-in-second-position.stderr
index 309106e856a98..6b3a488805f97 100644
--- a/src/test/ui/regions/regions-variance-contravariant-use-covariant-in-second-position.stderr
+++ b/src/test/ui/regions/regions-variance-contravariant-use-covariant-in-second-position.stderr
@@ -2,9 +2,7 @@ error[E0623]: lifetime mismatch
   --> $DIR/regions-variance-contravariant-use-covariant-in-second-position.rs:25:30
    |
 LL | fn use_<'short,'long>(c: S<'long, 'short>,
-   |                          ----------------
-   |                          |
-   |                          this type is declared with multiple lifetimes...
+   |                          ---------------- this type is declared with multiple lifetimes...
 ...
 LL |     let _: S<'long, 'long> = c;
    |                              ^ ...but data with one lifetime flows into the other here
diff --git a/src/test/ui/resolve/token-error-correct-3.stderr b/src/test/ui/resolve/token-error-correct-3.stderr
index 5e965e0952c53..607573f27698b 100644
--- a/src/test/ui/resolve/token-error-correct-3.stderr
+++ b/src/test/ui/resolve/token-error-correct-3.stderr
@@ -2,9 +2,8 @@ error: expected one of `)`, `,`, `.`, `?`, or an operator, found `;`
   --> $DIR/token-error-correct-3.rs:15:35
    |
 LL |             callback(path.as_ref();
-   |                     -             ^
-   |                     |             |
-   |                     |             help: `)` may belong here
+   |                     -             ^ help: `)` may belong here
+   |                     |
    |                     unclosed delimiter
 
 error: expected one of `.`, `;`, `?`, `}`, or an operator, found `)`

From ff976fe0f13491f0e6d3f7cbd52ab409fd93165a Mon Sep 17 00:00:00 2001
From: Michael Woerister <michaelwoerister@posteo>
Date: Wed, 24 Apr 2019 11:14:24 +0200
Subject: [PATCH 09/13] Fix ignore-logic for sanitizer run-make tests.

---
 src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile   | 5 ++---
 src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile    | 4 ++--
 .../run-make-fulldeps/sanitizer-staticlib-link/Makefile     | 6 ++----
 3 files changed, 6 insertions(+), 9 deletions(-)

diff --git a/src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile b/src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile
index 36cde355468be..35317dca1e824 100644
--- a/src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-cdylib-link/Makefile
@@ -1,4 +1,6 @@
 # needs-sanitizer-support
+# only-x86_64
+# only-linux
 
 -include ../tools.mk
 
@@ -9,11 +11,8 @@ LOG := $(TMPDIR)/log.txt
 # are compiled with address sanitizer, and we assert that a fault in the cdylib
 # is correctly detected.
 
-ifeq ($(TARGET),x86_64-unknown-linux-gnu)
-
 # See comment in sanitizer-address/Makefile for why this is here
 EXTRA_RUSTFLAG=-C relocation-model=dynamic-no-pic
-endif
 
 all:
 	$(RUSTC) -g -Z sanitizer=address --crate-type cdylib --target $(TARGET) $(EXTRA_RUSTFLAG) library.rs
diff --git a/src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile b/src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile
index b382ff5e7b24f..24d2ebd8f48aa 100644
--- a/src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-dylib-link/Makefile
@@ -1,4 +1,6 @@
 # needs-sanitizer-support
+# only-x86_64
+# only-linux
 
 -include ../tools.mk
 
@@ -9,10 +11,8 @@ LOG := $(TMPDIR)/log.txt
 # are compiled with address sanitizer, and we assert that a fault in the dylib
 # is correctly detected.
 
-ifeq ($(TARGET),x86_64-unknown-linux-gnu)
 # See comment in sanitizer-address/Makefile for why this is here
 EXTRA_RUSTFLAG=-C relocation-model=dynamic-no-pic
-endif
 
 all:
 	$(RUSTC) -g -Z sanitizer=address --crate-type dylib --target $(TARGET) $(EXTRA_RUSTFLAG) library.rs
diff --git a/src/test/run-make-fulldeps/sanitizer-staticlib-link/Makefile b/src/test/run-make-fulldeps/sanitizer-staticlib-link/Makefile
index 8fa08688fdd71..200dc1be4dee6 100644
--- a/src/test/run-make-fulldeps/sanitizer-staticlib-link/Makefile
+++ b/src/test/run-make-fulldeps/sanitizer-staticlib-link/Makefile
@@ -1,4 +1,6 @@
 # needs-sanitizer-support
+# only-x86_64
+# only-linux
 
 -include ../tools.mk
 
@@ -6,10 +8,6 @@
 # The staticlib and executable both  are compiled with address sanitizer,
 # and we assert that a fault in the staticlib is correctly detected.
 
-ifeq ($(TARGET),x86_64-unknown-linux-gnu)
-EXTRA_RUSTFLAG=
-endif
-
 all:
 	$(RUSTC) -g -Z sanitizer=address --crate-type staticlib --target $(TARGET) library.rs
 	$(CC) program.c $(call STATICLIB,library) $(call OUT_EXE,program) $(EXTRACFLAGS) $(EXTRACXXFLAGS)

From eb37c648d7c2b5587182c7d654622cf80542bea9 Mon Sep 17 00:00:00 2001
From: Matthew Jasper <mjjasper1@gmail.com>
Date: Sat, 29 Dec 2018 21:10:00 +0000
Subject: [PATCH 10/13] Remove incorrect debug assertion in interpret

Cast type may be a subtype of the destination type. There is a later
assertion that they have the same layout.
---
 src/librustc_mir/interpret/step.rs | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/src/librustc_mir/interpret/step.rs b/src/librustc_mir/interpret/step.rs
index 29a8547035e4a..4ca865cc84499 100644
--- a/src/librustc_mir/interpret/step.rs
+++ b/src/librustc_mir/interpret/step.rs
@@ -259,8 +259,7 @@ impl<'a, 'mir, 'tcx, M: Machine<'a, 'mir, 'tcx>> InterpretCx<'a, 'mir, 'tcx, M>
                 )?;
             }
 
-            Cast(kind, ref operand, cast_ty) => {
-                debug_assert_eq!(self.monomorphize(cast_ty)?, dest.layout.ty);
+            Cast(kind, ref operand, _) => {
                 let src = self.eval_operand(operand, None)?;
                 self.cast(src, kind, dest)?;
             }

From ff4d4b277f40b33b02e529d14c462ac11ab059ab Mon Sep 17 00:00:00 2001
From: Matthew Jasper <mjjasper1@gmail.com>
Date: Sat, 30 Mar 2019 13:00:41 +0000
Subject: [PATCH 11/13] Allow subtyping of the final expression of a constant

Fixes an ICE for the following code:

fn foo(_ : &()) {}
static X: fn(&'static ()) = foo;
---
 src/librustc_mir/build/mod.rs               | 33 +++++++++++++++++----
 src/librustc_typeck/check/mod.rs            |  2 ++
 src/librustc_typeck/check/writeback.rs      |  8 +++++
 src/test/run-pass/mir/mir_static_subtype.rs |  8 +++++
 4 files changed, 46 insertions(+), 5 deletions(-)
 create mode 100644 src/test/run-pass/mir/mir_static_subtype.rs

diff --git a/src/librustc_mir/build/mod.rs b/src/librustc_mir/build/mod.rs
index 79e1d5daae194..16ab233bd2e36 100644
--- a/src/librustc_mir/build/mod.rs
+++ b/src/librustc_mir/build/mod.rs
@@ -147,7 +147,21 @@ pub fn mir_build<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> Mir<'t
             build::construct_fn(cx, id, arguments, safety, abi,
                                 return_ty, yield_ty, return_ty_span, body)
         } else {
-            build::construct_const(cx, body_id, return_ty_span)
+            // Get the revealed type of this const. This is *not* the adjusted
+            // type of its body, which may be a subtype of this type. For
+            // example:
+            //
+            // fn foo(_: &()) {}
+            // static X: fn(&'static ()) = foo;
+            //
+            // The adjusted type of the body of X is `for<'a> fn(&'a ())` which
+            // is not the same as the type of X. We need the type of the return
+            // place to be the type of the constant because NLL typeck will
+            // equate them.
+
+            let return_ty = cx.tables().node_type(id);
+
+            build::construct_const(cx, body_id, return_ty, return_ty_span)
         };
 
         // Convert the Mir to global types.
@@ -730,16 +744,25 @@ fn construct_fn<'a, 'gcx, 'tcx, A>(hir: Cx<'a, 'gcx, 'tcx>,
 fn construct_const<'a, 'gcx, 'tcx>(
     hir: Cx<'a, 'gcx, 'tcx>,
     body_id: hir::BodyId,
-    ty_span: Span,
+    const_ty: Ty<'tcx>,
+    const_ty_span: Span,
 ) -> Mir<'tcx> {
     let tcx = hir.tcx();
-    let ast_expr = &tcx.hir().body(body_id).value;
-    let ty = hir.tables().expr_ty_adjusted(ast_expr);
     let owner_id = tcx.hir().body_owner(body_id);
     let span = tcx.hir().span(owner_id);
-    let mut builder = Builder::new(hir, span, 0, Safety::Safe, ty, ty_span, vec![], vec![]);
+    let mut builder = Builder::new(
+        hir,
+        span,
+        0,
+        Safety::Safe,
+        const_ty,
+        const_ty_span,
+        vec![],
+        vec![],
+    );
 
     let mut block = START_BLOCK;
+    let ast_expr = &tcx.hir().body(body_id).value;
     let expr = builder.hir.mirror(ast_expr);
     unpack!(block = builder.into_expr(&Place::RETURN_PLACE, block, expr));
 
diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs
index 79477b6fea87d..bd715df6e9d1e 100644
--- a/src/librustc_typeck/check/mod.rs
+++ b/src/librustc_typeck/check/mod.rs
@@ -866,6 +866,8 @@ fn typeck_tables_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
 
             fcx.check_expr_coercable_to_type(&body.value, revealed_ty);
 
+            fcx.write_ty(id, revealed_ty);
+
             fcx
         };
 
diff --git a/src/librustc_typeck/check/writeback.rs b/src/librustc_typeck/check/writeback.rs
index efff08f669690..193b17af55eff 100644
--- a/src/librustc_typeck/check/writeback.rs
+++ b/src/librustc_typeck/check/writeback.rs
@@ -42,6 +42,14 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
         for arg in &body.arguments {
             wbcx.visit_node_id(arg.pat.span, arg.hir_id);
         }
+        // Type only exists for constants and statics, not functions.
+        match self.tcx.hir().body_owner_kind(item_id) {
+            hir::BodyOwnerKind::Const | hir::BodyOwnerKind::Static(_) => {
+                let item_hir_id = self.tcx.hir().node_to_hir_id(item_id);
+                wbcx.visit_node_id(body.value.span, item_hir_id);
+            }
+            hir::BodyOwnerKind::Closure | hir::BodyOwnerKind::Fn => (),
+        }
         wbcx.visit_body(body);
         wbcx.visit_upvar_capture_map();
         wbcx.visit_upvar_list_map();
diff --git a/src/test/run-pass/mir/mir_static_subtype.rs b/src/test/run-pass/mir/mir_static_subtype.rs
new file mode 100644
index 0000000000000..5b1ccd7ddf6d9
--- /dev/null
+++ b/src/test/run-pass/mir/mir_static_subtype.rs
@@ -0,0 +1,8 @@
+// Test that subtyping the body of a static doesn't cause an ICE.
+
+fn foo(_ : &()) {}
+static X: fn(&'static ()) = foo;
+
+fn main() {
+    let _ = X;
+}

From e9c687b04a9511f2b93f35b5325d1b6ab5f5bb01 Mon Sep 17 00:00:00 2001
From: Matthew Jasper <mjjasper1@gmail.com>
Date: Sat, 30 Mar 2019 13:05:33 +0000
Subject: [PATCH 12/13] Evaluate hair::ExprKind::Use in into

This avoids some unnecessary moves
---
 src/librustc_mir/build/expr/as_rvalue.rs     |  5 +----
 src/librustc_mir/build/expr/category.rs      |  2 +-
 src/librustc_mir/build/expr/into.rs          |  4 +++-
 src/test/mir-opt/array-index-is-temporary.rs | 21 ++++++++++----------
 src/test/mir-opt/retag.rs                    | 14 ++++++-------
 5 files changed, 22 insertions(+), 24 deletions(-)

diff --git a/src/librustc_mir/build/expr/as_rvalue.rs b/src/librustc_mir/build/expr/as_rvalue.rs
index c58b570d8fc9f..da2de43c09efe 100644
--- a/src/librustc_mir/build/expr/as_rvalue.rs
+++ b/src/librustc_mir/build/expr/as_rvalue.rs
@@ -150,10 +150,6 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
                 let source = unpack!(block = this.as_operand(block, scope, source));
                 block.and(Rvalue::Cast(CastKind::Misc, source, expr.ty))
             }
-            ExprKind::Use { source } => {
-                let source = unpack!(block = this.as_operand(block, scope, source));
-                block.and(Rvalue::Use(source))
-            }
             ExprKind::Pointer { cast, source } => {
                 let source = unpack!(block = this.as_operand(block, scope, source));
                 block.and(Rvalue::Cast(CastKind::Pointer(cast), source, expr.ty))
@@ -363,6 +359,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
             | ExprKind::Match { .. }
             | ExprKind::If { .. }
             | ExprKind::NeverToAny { .. }
+            | ExprKind::Use { .. }
             | ExprKind::Loop { .. }
             | ExprKind::LogicalOp { .. }
             | ExprKind::Call { .. }
diff --git a/src/librustc_mir/build/expr/category.rs b/src/librustc_mir/build/expr/category.rs
index 52f1d0eca5e3c..4e24b6853d6eb 100644
--- a/src/librustc_mir/build/expr/category.rs
+++ b/src/librustc_mir/build/expr/category.rs
@@ -48,6 +48,7 @@ impl Category {
             | ExprKind::If { .. }
             | ExprKind::Match { .. }
             | ExprKind::NeverToAny { .. }
+            | ExprKind::Use { .. }
             | ExprKind::Call { .. } => Some(Category::Rvalue(RvalueFunc::Into)),
 
             ExprKind::Array { .. }
@@ -58,7 +59,6 @@ impl Category {
             | ExprKind::Binary { .. }
             | ExprKind::Box { .. }
             | ExprKind::Cast { .. }
-            | ExprKind::Use { .. }
             | ExprKind::Pointer { .. }
             | ExprKind::Repeat { .. }
             | ExprKind::Borrow { .. }
diff --git a/src/librustc_mir/build/expr/into.rs b/src/librustc_mir/build/expr/into.rs
index 8967572ea8f64..30ed9cef36f7b 100644
--- a/src/librustc_mir/build/expr/into.rs
+++ b/src/librustc_mir/build/expr/into.rs
@@ -327,6 +327,9 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
                     success.unit()
                 }
             }
+            ExprKind::Use { source } => {
+                this.into(destination, block, source)
+            }
 
             // These cases don't actually need a destination
             ExprKind::Assign { .. }
@@ -379,7 +382,6 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
             | ExprKind::Binary { .. }
             | ExprKind::Box { .. }
             | ExprKind::Cast { .. }
-            | ExprKind::Use { .. }
             | ExprKind::Pointer { .. }
             | ExprKind::Repeat { .. }
             | ExprKind::Borrow { .. }
diff --git a/src/test/mir-opt/array-index-is-temporary.rs b/src/test/mir-opt/array-index-is-temporary.rs
index 856e1063f6001..00a6b26d0cf22 100644
--- a/src/test/mir-opt/array-index-is-temporary.rs
+++ b/src/test/mir-opt/array-index-is-temporary.rs
@@ -18,25 +18,24 @@ fn main() {
 // START rustc.main.EraseRegions.after.mir
 //     bb0: {
 //         ...
-//         _6 = &mut _2;
-//         _5 = &mut (*_6);
-//         _4 = move _5 as *mut usize (Misc);
-//         _3 = move _4;
+//         _5 = &mut _2;
+//         _4 = &mut (*_5);
+//         _3 = move _4 as *mut usize (Misc);
 //         ...
-//         _8 = _3;
-//         _7 = const foo(move _8) -> bb1;
+//         _7 = _3;
+//         _6 = const foo(move _7) -> bb1;
 //     }
 //
 //     bb1: {
 //         ...
-//         _9 = _2;
-//         _10 = Len(_1);
-//         _11 = Lt(_9, _10);
-//         assert(move _11, "index out of bounds: the len is move _10 but the index is _9") -> bb2;
+//         _8 = _2;
+//         _9 = Len(_1);
+//         _10 = Lt(_8, _9);
+//         assert(move _10, "index out of bounds: the len is move _9 but the index is _8") -> bb2;
 //     }
 //
 //     bb2: {
-//         _1[_9] = move _7;
+//         _1[_8] = move _6;
 //         ...
 //         return;
 //     }
diff --git a/src/test/mir-opt/retag.rs b/src/test/mir-opt/retag.rs
index 1f8abf10fa549..6b7c863fcd43f 100644
--- a/src/test/mir-opt/retag.rs
+++ b/src/test/mir-opt/retag.rs
@@ -75,18 +75,18 @@ fn main() {
 //         _10 = move _8;
 //         Retag(_10);
 //         ...
-//         _15 = &mut (*_10);
-//         Retag(_15);
-//         _14 = move _15 as *mut i32 (Misc);
-//         Retag([raw] _14);
+//         _13 = &mut (*_10);
+//         Retag(_13);
+//         _12 = move _13 as *mut i32 (Misc);
+//         Retag([raw] _12);
 //         ...
-//         _18 = move _19(move _20) -> bb2;
+//         _16 = move _17(move _18) -> bb2;
 //     }
 //
 //     bb2: {
-//         Retag(_18);
+//         Retag(_16);
 //         ...
-//         _22 = const Test::foo_shr(move _23, move _25) -> bb3;
+//         _20 = const Test::foo_shr(move _21, move _23) -> bb3;
 //     }
 //
 //     bb3: {

From 04023dc22da3f3329ba1eadc8ceb132a70a333d9 Mon Sep 17 00:00:00 2001
From: David Wood <david@davidtw.co>
Date: Wed, 24 Apr 2019 19:11:10 +0100
Subject: [PATCH 13/13] Add regression test for #53249.

---
 src/test/ui/issue-53249.rs | 47 ++++++++++++++++++++++++++++++++++++++
 1 file changed, 47 insertions(+)
 create mode 100644 src/test/ui/issue-53249.rs

diff --git a/src/test/ui/issue-53249.rs b/src/test/ui/issue-53249.rs
new file mode 100644
index 0000000000000..9e4ff43ecd112
--- /dev/null
+++ b/src/test/ui/issue-53249.rs
@@ -0,0 +1,47 @@
+// compile-pass
+// edition:2018
+
+#![feature(arbitrary_self_types, async_await, await_macro)]
+
+use std::task::{self, Poll};
+use std::future::Future;
+use std::marker::Unpin;
+use std::pin::Pin;
+
+// This is a regression test for a ICE/unbounded recursion issue relating to async-await.
+
+#[derive(Debug)]
+#[must_use = "futures do nothing unless polled"]
+pub struct Lazy<F> {
+    f: Option<F>
+}
+
+impl<F> Unpin for Lazy<F> {}
+
+pub fn lazy<F, R>(f: F) -> Lazy<F>
+    where F: FnOnce(&mut task::Context) -> R,
+{
+    Lazy { f: Some(f) }
+}
+
+impl<R, F> Future for Lazy<F>
+    where F: FnOnce(&mut task::Context) -> R,
+{
+    type Output = R;
+
+    fn poll(mut self: Pin<&mut Self>, cx: &mut task::Context) -> Poll<R> {
+        Poll::Ready((self.f.take().unwrap())(cx))
+    }
+}
+
+async fn __receive<WantFn, Fut>(want: WantFn) -> ()
+    where Fut: Future<Output = ()>, WantFn: Fn(&Box<Send + 'static>) -> Fut,
+{
+    await!(lazy(|_| ()));
+}
+
+pub fn basic_spawn_receive() {
+    async { await!(__receive(|_| async { () })) };
+}
+
+fn main() {}