summaryrefslogtreecommitdiffstats
path: root/src/test/ui/coherence
diff options
context:
space:
mode:
authorDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-17 12:02:58 +0000
committerDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-17 12:02:58 +0000
commit698f8c2f01ea549d77d7dc3338a12e04c11057b9 (patch)
tree173a775858bd501c378080a10dca74132f05bc50 /src/test/ui/coherence
parentInitial commit. (diff)
downloadrustc-698f8c2f01ea549d77d7dc3338a12e04c11057b9.tar.xz
rustc-698f8c2f01ea549d77d7dc3338a12e04c11057b9.zip
Adding upstream version 1.64.0+dfsg1.upstream/1.64.0+dfsg1
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'src/test/ui/coherence')
-rw-r--r--src/test/ui/coherence/auxiliary/coherence_copy_like_lib.rs10
-rw-r--r--src/test/ui/coherence/auxiliary/coherence_fundamental_trait_lib.rs7
-rw-r--r--src/test/ui/coherence/auxiliary/coherence_inherent_cc_lib.rs11
-rw-r--r--src/test/ui/coherence/auxiliary/coherence_lib.rs15
-rw-r--r--src/test/ui/coherence/auxiliary/coherence_orphan_lib.rs3
-rw-r--r--src/test/ui/coherence/auxiliary/error_lib.rs6
-rw-r--r--src/test/ui/coherence/auxiliary/go_trait.rs43
-rw-r--r--src/test/ui/coherence/auxiliary/option_future.rs8
-rw-r--r--src/test/ui/coherence/auxiliary/re_rebalance_coherence_lib-rpass.rs31
-rw-r--r--src/test/ui/coherence/auxiliary/re_rebalance_coherence_lib.rs22
-rw-r--r--src/test/ui/coherence/auxiliary/trait_impl_conflict.rs6
-rw-r--r--src/test/ui/coherence/coherence-all-remote.rs9
-rw-r--r--src/test/ui/coherence/coherence-all-remote.stderr12
-rw-r--r--src/test/ui/coherence/coherence-bigint-int.rs13
-rw-r--r--src/test/ui/coherence/coherence-bigint-param.rs11
-rw-r--r--src/test/ui/coherence/coherence-bigint-param.stderr12
-rw-r--r--src/test/ui/coherence/coherence-bigint-vecint.rs13
-rw-r--r--src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-implemented.rs30
-rw-r--r--src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-implemented.stderr12
-rw-r--r--src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-unimplemented.rs25
-rw-r--r--src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-unimplemented.stderr12
-rw-r--r--src/test/ui/coherence/coherence-blanket-conflicts-with-specific-cross-crate.rs20
-rw-r--r--src/test/ui/coherence/coherence-blanket-conflicts-with-specific-cross-crate.stderr13
-rw-r--r--src/test/ui/coherence/coherence-blanket-conflicts-with-specific-multidispatch.rs27
-rw-r--r--src/test/ui/coherence/coherence-blanket-conflicts-with-specific-multidispatch.stderr12
-rw-r--r--src/test/ui/coherence/coherence-blanket-conflicts-with-specific-trait.rs29
-rw-r--r--src/test/ui/coherence/coherence-blanket-conflicts-with-specific-trait.stderr12
-rw-r--r--src/test/ui/coherence/coherence-blanket-conflicts-with-specific.rs24
-rw-r--r--src/test/ui/coherence/coherence-blanket-conflicts-with-specific.stderr12
-rw-r--r--src/test/ui/coherence/coherence-blanket.rs16
-rw-r--r--src/test/ui/coherence/coherence-conflicting-negative-trait-impl.rs17
-rw-r--r--src/test/ui/coherence/coherence-conflicting-negative-trait-impl.stderr22
-rw-r--r--src/test/ui/coherence/coherence-covered-type-parameter.rs14
-rw-r--r--src/test/ui/coherence/coherence-cow.re_a.stderr14
-rw-r--r--src/test/ui/coherence/coherence-cow.re_b.stderr14
-rw-r--r--src/test/ui/coherence/coherence-cow.re_c.stderr14
-rw-r--r--src/test/ui/coherence/coherence-cow.rs29
-rw-r--r--src/test/ui/coherence/coherence-cross-crate-conflict.rs13
-rw-r--r--src/test/ui/coherence/coherence-cross-crate-conflict.stderr12
-rw-r--r--src/test/ui/coherence/coherence-default-trait-impl.rs16
-rw-r--r--src/test/ui/coherence/coherence-default-trait-impl.stderr16
-rw-r--r--src/test/ui/coherence/coherence-error-suppression.rs16
-rw-r--r--src/test/ui/coherence/coherence-error-suppression.stderr9
-rw-r--r--src/test/ui/coherence/coherence-fn-covariant-bound-vs-static.rs26
-rw-r--r--src/test/ui/coherence/coherence-fn-covariant-bound-vs-static.stderr13
-rw-r--r--src/test/ui/coherence/coherence-fn-implied-bounds.rs26
-rw-r--r--src/test/ui/coherence/coherence-fn-implied-bounds.stderr20
-rw-r--r--src/test/ui/coherence/coherence-fn-inputs.rs25
-rw-r--r--src/test/ui/coherence/coherence-fn-inputs.stderr13
-rw-r--r--src/test/ui/coherence/coherence-free-vs-bound-region.rs21
-rw-r--r--src/test/ui/coherence/coherence-free-vs-bound-region.stderr20
-rw-r--r--src/test/ui/coherence/coherence-fundamental-trait-objects.rs15
-rw-r--r--src/test/ui/coherence/coherence-fundamental-trait-objects.stderr14
-rw-r--r--src/test/ui/coherence/coherence-impl-in-fn.rs14
-rw-r--r--src/test/ui/coherence/coherence-impl-trait-for-marker-trait-negative.rs30
-rw-r--r--src/test/ui/coherence/coherence-impl-trait-for-marker-trait-negative.stderr39
-rw-r--r--src/test/ui/coherence/coherence-impl-trait-for-marker-trait-positive.rs30
-rw-r--r--src/test/ui/coherence/coherence-impl-trait-for-marker-trait-positive.stderr39
-rw-r--r--src/test/ui/coherence/coherence-impl-trait-for-trait-object-safe.rs10
-rw-r--r--src/test/ui/coherence/coherence-impl-trait-for-trait-object-safe.stderr18
-rw-r--r--src/test/ui/coherence/coherence-impl-trait-for-trait.rs20
-rw-r--r--src/test/ui/coherence/coherence-impl-trait-for-trait.stderr21
-rw-r--r--src/test/ui/coherence/coherence-impls-copy.rs36
-rw-r--r--src/test/ui/coherence/coherence-impls-copy.stderr76
-rw-r--r--src/test/ui/coherence/coherence-impls-send.rs28
-rw-r--r--src/test/ui/coherence/coherence-impls-send.stderr43
-rw-r--r--src/test/ui/coherence/coherence-impls-sized.rs36
-rw-r--r--src/test/ui/coherence/coherence-impls-sized.stderr73
-rw-r--r--src/test/ui/coherence/coherence-inherited-assoc-ty-cycle-err.rs24
-rw-r--r--src/test/ui/coherence/coherence-inherited-assoc-ty-cycle-err.stderr26
-rw-r--r--src/test/ui/coherence/coherence-inherited-subtyping.old.stderr14
-rw-r--r--src/test/ui/coherence/coherence-inherited-subtyping.re.stderr14
-rw-r--r--src/test/ui/coherence/coherence-inherited-subtyping.rs21
-rw-r--r--src/test/ui/coherence/coherence-iterator-vec-any-elem.rs14
-rw-r--r--src/test/ui/coherence/coherence-iterator-vec.rs14
-rw-r--r--src/test/ui/coherence/coherence-lone-type-parameter.rs10
-rw-r--r--src/test/ui/coherence/coherence-lone-type-parameter.stderr12
-rw-r--r--src/test/ui/coherence/coherence-multidispatch-tuple.rs24
-rw-r--r--src/test/ui/coherence/coherence-negative-impls-safe-rpass.rs13
-rw-r--r--src/test/ui/coherence/coherence-negative-impls-safe.rs10
-rw-r--r--src/test/ui/coherence/coherence-negative-impls-safe.stderr12
-rw-r--r--src/test/ui/coherence/coherence-negative-inherent-where-bounds.rs25
-rw-r--r--src/test/ui/coherence/coherence-negative-inherent.rs22
-rw-r--r--src/test/ui/coherence/coherence-negative-outlives-lifetimes.rs12
-rw-r--r--src/test/ui/coherence/coherence-negative-outlives-lifetimes.stderr11
-rw-r--r--src/test/ui/coherence/coherence-no-direct-lifetime-dispatch.rs9
-rw-r--r--src/test/ui/coherence/coherence-no-direct-lifetime-dispatch.stderr11
-rw-r--r--src/test/ui/coherence/coherence-orphan.rs20
-rw-r--r--src/test/ui/coherence/coherence-orphan.stderr26
-rw-r--r--src/test/ui/coherence/coherence-overlap-all-t-and-tuple.rs20
-rw-r--r--src/test/ui/coherence/coherence-overlap-all-t-and-tuple.stderr12
-rw-r--r--src/test/ui/coherence/coherence-overlap-double-negative.rs12
-rw-r--r--src/test/ui/coherence/coherence-overlap-downstream-inherent.rs17
-rw-r--r--src/test/ui/coherence/coherence-overlap-downstream-inherent.stderr23
-rw-r--r--src/test/ui/coherence/coherence-overlap-downstream.rs17
-rw-r--r--src/test/ui/coherence/coherence-overlap-downstream.stderr21
-rw-r--r--src/test/ui/coherence/coherence-overlap-issue-23516-inherent.rs13
-rw-r--r--src/test/ui/coherence/coherence-overlap-issue-23516-inherent.stderr14
-rw-r--r--src/test/ui/coherence/coherence-overlap-issue-23516.rs11
-rw-r--r--src/test/ui/coherence/coherence-overlap-issue-23516.stderr13
-rw-r--r--src/test/ui/coherence/coherence-overlap-messages.rs28
-rw-r--r--src/test/ui/coherence/coherence-overlap-messages.stderr44
-rw-r--r--src/test/ui/coherence/coherence-overlap-negate-alias-strict.rs19
-rw-r--r--src/test/ui/coherence/coherence-overlap-negate-not-use-feature-gate.rs8
-rw-r--r--src/test/ui/coherence/coherence-overlap-negate-not-use-feature-gate.stderr11
-rw-r--r--src/test/ui/coherence/coherence-overlap-negate-strict.rs18
-rw-r--r--src/test/ui/coherence/coherence-overlap-negate-use-feature-gate.rs11
-rw-r--r--src/test/ui/coherence/coherence-overlap-negative-trait.rs16
-rw-r--r--src/test/ui/coherence/coherence-overlap-negative-trait2.rs17
-rw-r--r--src/test/ui/coherence/coherence-overlap-super-negative.rs18
-rw-r--r--src/test/ui/coherence/coherence-overlap-trait-alias.rs20
-rw-r--r--src/test/ui/coherence/coherence-overlap-trait-alias.stderr17
-rw-r--r--src/test/ui/coherence/coherence-overlap-upstream-inherent.rs16
-rw-r--r--src/test/ui/coherence/coherence-overlap-upstream-inherent.stderr14
-rw-r--r--src/test/ui/coherence/coherence-overlap-upstream.rs16
-rw-r--r--src/test/ui/coherence/coherence-overlap-upstream.stderr13
-rw-r--r--src/test/ui/coherence/coherence-overlap-with-regions.rs16
-rw-r--r--src/test/ui/coherence/coherence-overlapping-pairs.rs11
-rw-r--r--src/test/ui/coherence/coherence-overlapping-pairs.stderr14
-rw-r--r--src/test/ui/coherence/coherence-pair-covered-uncovered-1.rs15
-rw-r--r--src/test/ui/coherence/coherence-pair-covered-uncovered-1.stderr15
-rw-r--r--src/test/ui/coherence/coherence-pair-covered-uncovered.rs11
-rw-r--r--src/test/ui/coherence/coherence-pair-covered-uncovered.stderr14
-rw-r--r--src/test/ui/coherence/coherence-projection-conflict-orphan.rs19
-rw-r--r--src/test/ui/coherence/coherence-projection-conflict-orphan.stderr14
-rw-r--r--src/test/ui/coherence/coherence-projection-conflict-ty-param.rs13
-rw-r--r--src/test/ui/coherence/coherence-projection-conflict-ty-param.stderr12
-rw-r--r--src/test/ui/coherence/coherence-projection-conflict.rs18
-rw-r--r--src/test/ui/coherence/coherence-projection-conflict.stderr12
-rw-r--r--src/test/ui/coherence/coherence-projection-ok-orphan.rs17
-rw-r--r--src/test/ui/coherence/coherence-projection-ok.rs17
-rw-r--r--src/test/ui/coherence/coherence-rfc447-constrained.rs22
-rw-r--r--src/test/ui/coherence/coherence-subtyping.rs20
-rw-r--r--src/test/ui/coherence/coherence-subtyping.stderr16
-rw-r--r--src/test/ui/coherence/coherence-tuple-conflict.rs20
-rw-r--r--src/test/ui/coherence/coherence-tuple-conflict.stderr12
-rw-r--r--src/test/ui/coherence/coherence-unsafe-trait-object-impl.rs18
-rw-r--r--src/test/ui/coherence/coherence-unsafe-trait-object-impl.stderr17
-rw-r--r--src/test/ui/coherence/coherence-vec-local-2.rs14
-rw-r--r--src/test/ui/coherence/coherence-vec-local-2.stderr14
-rw-r--r--src/test/ui/coherence/coherence-vec-local.rs14
-rw-r--r--src/test/ui/coherence/coherence-vec-local.stderr14
-rw-r--r--src/test/ui/coherence/coherence-wasm-bindgen.rs37
-rw-r--r--src/test/ui/coherence/coherence-wasm-bindgen.stderr21
-rw-r--r--src/test/ui/coherence/coherence-where-clause.rs38
-rw-r--r--src/test/ui/coherence/coherence-with-closure.rs15
-rw-r--r--src/test/ui/coherence/coherence-with-closure.stderr24
-rw-r--r--src/test/ui/coherence/coherence-with-generator.rs19
-rw-r--r--src/test/ui/coherence/coherence-with-generator.stderr24
-rw-r--r--src/test/ui/coherence/coherence_copy_like.rs19
-rw-r--r--src/test/ui/coherence/coherence_copy_like_err_fundamental_struct.rs24
-rw-r--r--src/test/ui/coherence/coherence_copy_like_err_fundamental_struct_ref.rs21
-rw-r--r--src/test/ui/coherence/coherence_copy_like_err_fundamental_struct_tuple.rs20
-rw-r--r--src/test/ui/coherence/coherence_copy_like_err_fundamental_struct_tuple.stderr14
-rw-r--r--src/test/ui/coherence/coherence_copy_like_err_struct.rs22
-rw-r--r--src/test/ui/coherence/coherence_copy_like_err_struct.stderr14
-rw-r--r--src/test/ui/coherence/coherence_copy_like_err_tuple.rs21
-rw-r--r--src/test/ui/coherence/coherence_copy_like_err_tuple.stderr14
-rw-r--r--src/test/ui/coherence/coherence_inherent.rs36
-rw-r--r--src/test/ui/coherence/coherence_inherent.stderr15
-rw-r--r--src/test/ui/coherence/coherence_inherent_cc.rs28
-rw-r--r--src/test/ui/coherence/coherence_inherent_cc.stderr15
-rw-r--r--src/test/ui/coherence/coherence_local.rs20
-rw-r--r--src/test/ui/coherence/coherence_local_err_struct.rs18
-rw-r--r--src/test/ui/coherence/coherence_local_err_struct.stderr14
-rw-r--r--src/test/ui/coherence/coherence_local_err_tuple.rs18
-rw-r--r--src/test/ui/coherence/coherence_local_err_tuple.stderr14
-rw-r--r--src/test/ui/coherence/coherence_local_ref.rs14
-rw-r--r--src/test/ui/coherence/conflicting-impl-with-err.rs16
-rw-r--r--src/test/ui/coherence/conflicting-impl-with-err.stderr15
-rw-r--r--src/test/ui/coherence/deep-bad-copy-reason.rs40
-rw-r--r--src/test/ui/coherence/deep-bad-copy-reason.stderr18
-rw-r--r--src/test/ui/coherence/impl-foreign-for-foreign.rs15
-rw-r--r--src/test/ui/coherence/impl-foreign-for-foreign.stderr14
-rw-r--r--src/test/ui/coherence/impl-foreign-for-foreign[foreign].rs23
-rw-r--r--src/test/ui/coherence/impl-foreign-for-foreign[foreign].stderr39
-rw-r--r--src/test/ui/coherence/impl-foreign-for-foreign[local].rs14
-rw-r--r--src/test/ui/coherence/impl-foreign-for-fundamental[foreign].rs19
-rw-r--r--src/test/ui/coherence/impl-foreign-for-fundamental[foreign].stderr27
-rw-r--r--src/test/ui/coherence/impl-foreign-for-fundamental[local].rs15
-rw-r--r--src/test/ui/coherence/impl-foreign-for-local.rs13
-rw-r--r--src/test/ui/coherence/impl-foreign-for-locally-defined-fundamental.rs15
-rw-r--r--src/test/ui/coherence/impl-foreign-for-locally-defined-fundamental[foreign].rs15
-rw-r--r--src/test/ui/coherence/impl-foreign[foreign]-for-foreign.rs15
-rw-r--r--src/test/ui/coherence/impl-foreign[foreign]-for-foreign.stderr15
-rw-r--r--src/test/ui/coherence/impl-foreign[foreign]-for-local.rs14
-rw-r--r--src/test/ui/coherence/impl-foreign[fundemental[foreign]]-for-foreign.rs24
-rw-r--r--src/test/ui/coherence/impl-foreign[fundemental[foreign]]-for-foreign.stderr42
-rw-r--r--src/test/ui/coherence/impl-foreign[fundemental[local]]-for-foreign.rs16
-rw-r--r--src/test/ui/coherence/impl[t]-foreign-for-foreign[t].rs21
-rw-r--r--src/test/ui/coherence/impl[t]-foreign-for-foreign[t].stderr25
-rw-r--r--src/test/ui/coherence/impl[t]-foreign-for-fundamental[t].rs15
-rw-r--r--src/test/ui/coherence/impl[t]-foreign-for-fundamental[t].stderr12
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[foreign[t]_local]-for-foreign.rs12
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[foreign]-for-fundamental[t].rs18
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[foreign]-for-fundamental[t].stderr21
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[foreign]-for-t.rs14
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[foreign]-for-t.stderr12
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-foreign.rs18
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-foreign.stderr21
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-fundamental[t].rs17
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-fundamental[t].stderr21
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-local.rs15
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-t.rs17
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-t.stderr21
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[fundamental[t]_local]-for-foreign.rs18
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[fundamental[t]_local]-for-foreign.stderr21
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[fundemental[local]]-for-foreign[t].rs15
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[local]-for-foreign.rs14
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[local]-for-foreign[t].rs15
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[local]-for-fundamental[foreign[t]].rs17
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[local]-for-fundamental[t].rs18
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[local]-for-fundamental[t].stderr21
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[local]-for-local.rs13
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[local]-for-t.rs14
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[local]-for-t.stderr12
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[local_fundamental[t]]-for-foreign.rs17
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[t]-for-foreign.rs14
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[t]-for-foreign.stderr12
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[t]-for-fundamental.rs18
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[t]-for-fundamental.stderr21
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[t]-for-local.rs13
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[t]-for-t.rs14
-rw-r--r--src/test/ui/coherence/impl[t]-foreign[t]-for-t.stderr12
-rw-r--r--src/test/ui/coherence/inter-crate-ambiguity-causes-notes.rs19
-rw-r--r--src/test/ui/coherence/inter-crate-ambiguity-causes-notes.stderr14
-rw-r--r--src/test/ui/coherence/issue-85026.rs10
-rw-r--r--src/test/ui/coherence/issue-85026.stderr19
-rw-r--r--src/test/ui/coherence/issue-99663-2.rs22
-rw-r--r--src/test/ui/coherence/issue-99663.rs22
-rw-r--r--src/test/ui/coherence/re-rebalance-coherence-default-generic-associated-type.rs26
-rw-r--r--src/test/ui/coherence/re-rebalance-coherence.rs11
232 files changed, 4275 insertions, 0 deletions
diff --git a/src/test/ui/coherence/auxiliary/coherence_copy_like_lib.rs b/src/test/ui/coherence/auxiliary/coherence_copy_like_lib.rs
new file mode 100644
index 000000000..b5b4802c1
--- /dev/null
+++ b/src/test/ui/coherence/auxiliary/coherence_copy_like_lib.rs
@@ -0,0 +1,10 @@
+#![crate_type = "rlib"]
+#![feature(fundamental)]
+
+pub trait MyCopy { }
+impl MyCopy for i32 { }
+
+pub struct MyStruct<T>(T);
+
+#[fundamental]
+pub struct MyFundamentalStruct<T>(T);
diff --git a/src/test/ui/coherence/auxiliary/coherence_fundamental_trait_lib.rs b/src/test/ui/coherence/auxiliary/coherence_fundamental_trait_lib.rs
new file mode 100644
index 000000000..21aaea479
--- /dev/null
+++ b/src/test/ui/coherence/auxiliary/coherence_fundamental_trait_lib.rs
@@ -0,0 +1,7 @@
+#![crate_type = "rlib"]
+#![feature(fundamental)]
+
+pub trait Misc {}
+
+#[fundamental]
+pub trait Fundamental<T> {}
diff --git a/src/test/ui/coherence/auxiliary/coherence_inherent_cc_lib.rs b/src/test/ui/coherence/auxiliary/coherence_inherent_cc_lib.rs
new file mode 100644
index 000000000..08d22fbed
--- /dev/null
+++ b/src/test/ui/coherence/auxiliary/coherence_inherent_cc_lib.rs
@@ -0,0 +1,11 @@
+// See coherence_inherent_cc.rs
+
+pub trait TheTrait {
+ fn the_fn(&self);
+}
+
+pub struct TheStruct;
+
+impl TheTrait for TheStruct {
+ fn the_fn(&self) {}
+}
diff --git a/src/test/ui/coherence/auxiliary/coherence_lib.rs b/src/test/ui/coherence/auxiliary/coherence_lib.rs
new file mode 100644
index 000000000..c22819831
--- /dev/null
+++ b/src/test/ui/coherence/auxiliary/coherence_lib.rs
@@ -0,0 +1,15 @@
+#![crate_type="lib"]
+
+pub trait Remote {
+ fn foo(&self) { }
+}
+
+pub trait Remote1<T> {
+ fn foo(&self, _t: T) { }
+}
+
+pub trait Remote2<T, U> {
+ fn foo(&self, _t: T, _u: U) { }
+}
+
+pub struct Pair<T,U>(T,U);
diff --git a/src/test/ui/coherence/auxiliary/coherence_orphan_lib.rs b/src/test/ui/coherence/auxiliary/coherence_orphan_lib.rs
new file mode 100644
index 000000000..2664ef550
--- /dev/null
+++ b/src/test/ui/coherence/auxiliary/coherence_orphan_lib.rs
@@ -0,0 +1,3 @@
+pub trait TheTrait<T> {
+ fn the_fn(&self);
+}
diff --git a/src/test/ui/coherence/auxiliary/error_lib.rs b/src/test/ui/coherence/auxiliary/error_lib.rs
new file mode 100644
index 000000000..19ff9ae62
--- /dev/null
+++ b/src/test/ui/coherence/auxiliary/error_lib.rs
@@ -0,0 +1,6 @@
+#![crate_type = "lib"]
+#![feature(negative_impls)]
+#![feature(with_negative_coherence)]
+
+pub trait Error {}
+impl !Error for &str {}
diff --git a/src/test/ui/coherence/auxiliary/go_trait.rs b/src/test/ui/coherence/auxiliary/go_trait.rs
new file mode 100644
index 000000000..aa0ec2289
--- /dev/null
+++ b/src/test/ui/coherence/auxiliary/go_trait.rs
@@ -0,0 +1,43 @@
+#![feature(specialization)]
+
+// Common code used for tests that model the Fn/FnMut/FnOnce hierarchy.
+
+pub trait Go {
+ fn go(&self, arg: isize);
+}
+
+pub fn go<G:Go>(this: &G, arg: isize) {
+ this.go(arg)
+}
+
+pub trait GoMut {
+ fn go_mut(&mut self, arg: isize);
+}
+
+pub fn go_mut<G:GoMut>(this: &mut G, arg: isize) {
+ this.go_mut(arg)
+}
+
+pub trait GoOnce {
+ fn go_once(self, arg: isize);
+}
+
+pub fn go_once<G:GoOnce>(this: G, arg: isize) {
+ this.go_once(arg)
+}
+
+impl<G> GoMut for G
+ where G : Go
+{
+ default fn go_mut(&mut self, arg: isize) {
+ go(&*self, arg)
+ }
+}
+
+impl<G> GoOnce for G
+ where G : GoMut
+{
+ default fn go_once(mut self, arg: isize) {
+ go_mut(&mut self, arg)
+ }
+}
diff --git a/src/test/ui/coherence/auxiliary/option_future.rs b/src/test/ui/coherence/auxiliary/option_future.rs
new file mode 100644
index 000000000..067de1cd8
--- /dev/null
+++ b/src/test/ui/coherence/auxiliary/option_future.rs
@@ -0,0 +1,8 @@
+#![crate_type = "lib"]
+#![feature(negative_impls)]
+#![feature(rustc_attrs)]
+#![feature(with_negative_coherence)]
+
+pub trait Future {}
+
+impl<E> !Future for Option<E> where E: Sized {}
diff --git a/src/test/ui/coherence/auxiliary/re_rebalance_coherence_lib-rpass.rs b/src/test/ui/coherence/auxiliary/re_rebalance_coherence_lib-rpass.rs
new file mode 100644
index 000000000..9a191bad8
--- /dev/null
+++ b/src/test/ui/coherence/auxiliary/re_rebalance_coherence_lib-rpass.rs
@@ -0,0 +1,31 @@
+pub trait Backend {}
+pub trait SupportsDefaultKeyword {}
+
+impl SupportsDefaultKeyword for Postgres {}
+
+pub struct Postgres;
+
+impl Backend for Postgres {}
+
+pub struct AstPass<DB>(::std::marker::PhantomData<DB>);
+
+pub trait QueryFragment<DB: Backend> {}
+
+
+#[derive(Debug, Clone, Copy)]
+pub struct BatchInsert<'a, T: 'a, Tab> {
+ _marker: ::std::marker::PhantomData<(&'a T, Tab)>,
+}
+
+impl<'a, T:'a, Tab, DB> QueryFragment<DB> for BatchInsert<'a, T, Tab>
+where DB: SupportsDefaultKeyword + Backend,
+{}
+
+pub trait LibToOwned {
+ type Owned;
+}
+
+pub struct LibCow<T: LibToOwned, Owned = <T as LibToOwned>::Owned> {
+ pub t: T,
+ pub o: Owned,
+}
diff --git a/src/test/ui/coherence/auxiliary/re_rebalance_coherence_lib.rs b/src/test/ui/coherence/auxiliary/re_rebalance_coherence_lib.rs
new file mode 100644
index 000000000..41b9d64d5
--- /dev/null
+++ b/src/test/ui/coherence/auxiliary/re_rebalance_coherence_lib.rs
@@ -0,0 +1,22 @@
+pub trait Backend {}
+pub trait SupportsDefaultKeyword {}
+
+impl SupportsDefaultKeyword for Postgres {}
+
+pub struct Postgres;
+
+impl Backend for Postgres {}
+
+pub struct AstPass<DB>(::std::marker::PhantomData<DB>);
+
+pub trait QueryFragment<DB: Backend> {}
+
+
+#[derive(Debug, Clone, Copy)]
+pub struct BatchInsert<'a, T: 'a, Tab> {
+ _marker: ::std::marker::PhantomData<(&'a T, Tab)>,
+}
+
+impl<'a, T:'a, Tab, DB> QueryFragment<DB> for BatchInsert<'a, T, Tab>
+where DB: SupportsDefaultKeyword + Backend,
+{}
diff --git a/src/test/ui/coherence/auxiliary/trait_impl_conflict.rs b/src/test/ui/coherence/auxiliary/trait_impl_conflict.rs
new file mode 100644
index 000000000..5e5f017ed
--- /dev/null
+++ b/src/test/ui/coherence/auxiliary/trait_impl_conflict.rs
@@ -0,0 +1,6 @@
+pub trait Foo {
+ fn foo() {}
+}
+
+impl Foo for isize {
+}
diff --git a/src/test/ui/coherence/coherence-all-remote.rs b/src/test/ui/coherence/coherence-all-remote.rs
new file mode 100644
index 000000000..5c3bfee82
--- /dev/null
+++ b/src/test/ui/coherence/coherence-all-remote.rs
@@ -0,0 +1,9 @@
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::Remote1;
+
+impl<T> Remote1<T> for isize { }
+//~^ ERROR E0210
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-all-remote.stderr b/src/test/ui/coherence/coherence-all-remote.stderr
new file mode 100644
index 000000000..7eca41753
--- /dev/null
+++ b/src/test/ui/coherence/coherence-all-remote.stderr
@@ -0,0 +1,12 @@
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/coherence-all-remote.rs:6:6
+ |
+LL | impl<T> Remote1<T> for isize { }
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/coherence-bigint-int.rs b/src/test/ui/coherence/coherence-bigint-int.rs
new file mode 100644
index 000000000..02945e9da
--- /dev/null
+++ b/src/test/ui/coherence/coherence-bigint-int.rs
@@ -0,0 +1,13 @@
+// run-pass
+// aux-build:coherence_lib.rs
+
+// pretty-expanded FIXME #23616
+
+extern crate coherence_lib as lib;
+use lib::Remote1;
+
+pub struct BigInt;
+
+impl Remote1<BigInt> for isize { }
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-bigint-param.rs b/src/test/ui/coherence/coherence-bigint-param.rs
new file mode 100644
index 000000000..c6543aaf6
--- /dev/null
+++ b/src/test/ui/coherence/coherence-bigint-param.rs
@@ -0,0 +1,11 @@
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::Remote1;
+
+pub struct BigInt;
+
+impl<T> Remote1<BigInt> for T { }
+//~^ ERROR E0210
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-bigint-param.stderr b/src/test/ui/coherence/coherence-bigint-param.stderr
new file mode 100644
index 000000000..e8d74c917
--- /dev/null
+++ b/src/test/ui/coherence/coherence-bigint-param.stderr
@@ -0,0 +1,12 @@
+error[E0210]: type parameter `T` must be covered by another type when it appears before the first local type (`BigInt`)
+ --> $DIR/coherence-bigint-param.rs:8:6
+ |
+LL | impl<T> Remote1<BigInt> for T { }
+ | ^ type parameter `T` must be covered by another type when it appears before the first local type (`BigInt`)
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local, and no uncovered type parameters appear before that first local type
+ = note: in this case, 'before' refers to the following order: `impl<..> ForeignTrait<T1, ..., Tn> for T0`, where `T0` is the first and `Tn` is the last
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/coherence-bigint-vecint.rs b/src/test/ui/coherence/coherence-bigint-vecint.rs
new file mode 100644
index 000000000..a5dba90be
--- /dev/null
+++ b/src/test/ui/coherence/coherence-bigint-vecint.rs
@@ -0,0 +1,13 @@
+// run-pass
+// aux-build:coherence_lib.rs
+
+// pretty-expanded FIXME #23616
+
+extern crate coherence_lib as lib;
+use lib::Remote1;
+
+pub struct BigInt;
+
+impl Remote1<BigInt> for Vec<isize> { }
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-implemented.rs b/src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-implemented.rs
new file mode 100644
index 000000000..93a4bc5fe
--- /dev/null
+++ b/src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-implemented.rs
@@ -0,0 +1,30 @@
+use std::fmt::Debug;
+use std::default::Default;
+
+// Test that two blanket impls conflict (at least without negative
+// bounds). After all, some other crate could implement Even or Odd
+// for the same type (though this crate doesn't).
+
+trait MyTrait {
+ fn get(&self) -> usize;
+}
+
+trait Even { }
+
+trait Odd { }
+
+impl Even for isize { }
+
+impl Odd for usize { }
+
+impl<T:Even> MyTrait for T {
+ fn get(&self) -> usize { 0 }
+}
+
+impl<T:Odd> MyTrait for T {
+//~^ ERROR E0119
+
+ fn get(&self) -> usize { 0 }
+}
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-implemented.stderr b/src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-implemented.stderr
new file mode 100644
index 000000000..9156972a1
--- /dev/null
+++ b/src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-implemented.stderr
@@ -0,0 +1,12 @@
+error[E0119]: conflicting implementations of trait `MyTrait`
+ --> $DIR/coherence-blanket-conflicts-with-blanket-implemented.rs:24:1
+ |
+LL | impl<T:Even> MyTrait for T {
+ | -------------------------- first implementation here
+...
+LL | impl<T:Odd> MyTrait for T {
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-unimplemented.rs b/src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-unimplemented.rs
new file mode 100644
index 000000000..950a08ff2
--- /dev/null
+++ b/src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-unimplemented.rs
@@ -0,0 +1,25 @@
+use std::fmt::Debug;
+use std::default::Default;
+
+// Test that two blanket impls conflict (at least without negative
+// bounds). After all, some other crate could implement Even or Odd
+// for the same type (though this crate doesn't implement them at all).
+
+trait MyTrait {
+ fn get(&self) -> usize;
+}
+
+trait Even {}
+
+trait Odd {}
+
+impl<T:Even> MyTrait for T {
+ fn get(&self) -> usize { 0 }
+}
+
+impl<T:Odd> MyTrait for T {
+//~^ ERROR E0119
+ fn get(&self) -> usize { 0 }
+}
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-unimplemented.stderr b/src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-unimplemented.stderr
new file mode 100644
index 000000000..8400968e1
--- /dev/null
+++ b/src/test/ui/coherence/coherence-blanket-conflicts-with-blanket-unimplemented.stderr
@@ -0,0 +1,12 @@
+error[E0119]: conflicting implementations of trait `MyTrait`
+ --> $DIR/coherence-blanket-conflicts-with-blanket-unimplemented.rs:20:1
+ |
+LL | impl<T:Even> MyTrait for T {
+ | -------------------------- first implementation here
+...
+LL | impl<T:Odd> MyTrait for T {
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-cross-crate.rs b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-cross-crate.rs
new file mode 100644
index 000000000..bccbac2ff
--- /dev/null
+++ b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-cross-crate.rs
@@ -0,0 +1,20 @@
+// aux-build:go_trait.rs
+
+extern crate go_trait;
+
+use go_trait::{Go,GoMut};
+use std::fmt::Debug;
+use std::default::Default;
+
+struct MyThingy;
+
+impl Go for MyThingy {
+ fn go(&self, arg: isize) { }
+}
+
+impl GoMut for MyThingy {
+//~^ ERROR E0119
+ fn go_mut(&mut self, arg: isize) { }
+}
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-cross-crate.stderr b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-cross-crate.stderr
new file mode 100644
index 000000000..c25c43692
--- /dev/null
+++ b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-cross-crate.stderr
@@ -0,0 +1,13 @@
+error[E0119]: conflicting implementations of trait `go_trait::GoMut` for type `MyThingy`
+ --> $DIR/coherence-blanket-conflicts-with-specific-cross-crate.rs:15:1
+ |
+LL | impl GoMut for MyThingy {
+ | ^^^^^^^^^^^^^^^^^^^^^^^
+ |
+ = note: conflicting implementation in crate `go_trait`:
+ - impl<G> GoMut for G
+ where G: Go;
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-multidispatch.rs b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-multidispatch.rs
new file mode 100644
index 000000000..6a9db2173
--- /dev/null
+++ b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-multidispatch.rs
@@ -0,0 +1,27 @@
+use std::fmt::Debug;
+use std::default::Default;
+
+// Test that a blank impl for all T conflicts with an impl for some
+// specific T, even when there are multiple type parameters involved.
+
+trait MyTrait<T> {
+ fn get(&self) -> T;
+}
+
+impl<T> MyTrait<T> for T {
+ fn get(&self) -> T {
+ panic!()
+ }
+}
+
+#[derive(Clone)]
+struct MyType {
+ dummy: usize
+}
+
+impl MyTrait<MyType> for MyType {
+//~^ ERROR E0119
+ fn get(&self) -> usize { (*self).clone() }
+}
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-multidispatch.stderr b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-multidispatch.stderr
new file mode 100644
index 000000000..c2a925213
--- /dev/null
+++ b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-multidispatch.stderr
@@ -0,0 +1,12 @@
+error[E0119]: conflicting implementations of trait `MyTrait<MyType>` for type `MyType`
+ --> $DIR/coherence-blanket-conflicts-with-specific-multidispatch.rs:22:1
+ |
+LL | impl<T> MyTrait<T> for T {
+ | ------------------------ first implementation here
+...
+LL | impl MyTrait<MyType> for MyType {
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `MyType`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-trait.rs b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-trait.rs
new file mode 100644
index 000000000..02f9217da
--- /dev/null
+++ b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-trait.rs
@@ -0,0 +1,29 @@
+// Test that a blank impl for all T:PartialEq conflicts with an impl for some
+// specific T when T:PartialEq.
+
+trait OtherTrait {
+ fn noop(&self);
+}
+
+trait MyTrait {
+ fn get(&self) -> usize;
+}
+
+impl<T:OtherTrait> MyTrait for T {
+ fn get(&self) -> usize { 0 }
+}
+
+struct MyType {
+ dummy: usize
+}
+
+impl MyTrait for MyType {
+//~^ ERROR E0119
+ fn get(&self) -> usize { self.dummy }
+}
+
+impl OtherTrait for MyType {
+ fn noop(&self) { }
+}
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-trait.stderr b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-trait.stderr
new file mode 100644
index 000000000..e1a5dffeb
--- /dev/null
+++ b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific-trait.stderr
@@ -0,0 +1,12 @@
+error[E0119]: conflicting implementations of trait `MyTrait` for type `MyType`
+ --> $DIR/coherence-blanket-conflicts-with-specific-trait.rs:20:1
+ |
+LL | impl<T:OtherTrait> MyTrait for T {
+ | -------------------------------- first implementation here
+...
+LL | impl MyTrait for MyType {
+ | ^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `MyType`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-blanket-conflicts-with-specific.rs b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific.rs
new file mode 100644
index 000000000..5a562ff6a
--- /dev/null
+++ b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific.rs
@@ -0,0 +1,24 @@
+use std::fmt::Debug;
+use std::default::Default;
+
+// Test that a blank impl for all T conflicts with an impl for some
+// specific T.
+
+trait MyTrait {
+ fn get(&self) -> usize;
+}
+
+impl<T> MyTrait for T {
+ fn get(&self) -> usize { 0 }
+}
+
+struct MyType {
+ dummy: usize
+}
+
+impl MyTrait for MyType {
+//~^ ERROR E0119
+ fn get(&self) -> usize { self.dummy }
+}
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-blanket-conflicts-with-specific.stderr b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific.stderr
new file mode 100644
index 000000000..ba60a2ea9
--- /dev/null
+++ b/src/test/ui/coherence/coherence-blanket-conflicts-with-specific.stderr
@@ -0,0 +1,12 @@
+error[E0119]: conflicting implementations of trait `MyTrait` for type `MyType`
+ --> $DIR/coherence-blanket-conflicts-with-specific.rs:19:1
+ |
+LL | impl<T> MyTrait for T {
+ | --------------------- first implementation here
+...
+LL | impl MyTrait for MyType {
+ | ^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `MyType`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-blanket.rs b/src/test/ui/coherence/coherence-blanket.rs
new file mode 100644
index 000000000..55fa89d75
--- /dev/null
+++ b/src/test/ui/coherence/coherence-blanket.rs
@@ -0,0 +1,16 @@
+// run-pass
+#![allow(unused_imports)]
+// aux-build:coherence_lib.rs
+
+// pretty-expanded FIXME #23616
+
+extern crate coherence_lib as lib;
+use lib::Remote1;
+
+pub trait Local {
+ fn foo(&self) { }
+}
+
+impl<T> Local for T { }
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-conflicting-negative-trait-impl.rs b/src/test/ui/coherence/coherence-conflicting-negative-trait-impl.rs
new file mode 100644
index 000000000..24b878927
--- /dev/null
+++ b/src/test/ui/coherence/coherence-conflicting-negative-trait-impl.rs
@@ -0,0 +1,17 @@
+#![feature(negative_impls)]
+#![feature(marker_trait_attr)]
+
+#[marker]
+trait MyTrait {}
+
+struct TestType<T>(::std::marker::PhantomData<T>);
+
+unsafe impl<T: MyTrait + 'static> Send for TestType<T> {}
+
+impl<T: MyTrait> !Send for TestType<T> {} //~ ERROR found both positive and negative implementation
+
+unsafe impl<T: 'static> Send for TestType<T> {} //~ ERROR conflicting implementations
+
+impl !Send for TestType<i32> {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-conflicting-negative-trait-impl.stderr b/src/test/ui/coherence/coherence-conflicting-negative-trait-impl.stderr
new file mode 100644
index 000000000..111019773
--- /dev/null
+++ b/src/test/ui/coherence/coherence-conflicting-negative-trait-impl.stderr
@@ -0,0 +1,22 @@
+error[E0751]: found both positive and negative implementation of trait `std::marker::Send` for type `TestType<_>`:
+ --> $DIR/coherence-conflicting-negative-trait-impl.rs:11:1
+ |
+LL | unsafe impl<T: MyTrait + 'static> Send for TestType<T> {}
+ | ------------------------------------------------------ positive implementation here
+LL |
+LL | impl<T: MyTrait> !Send for TestType<T> {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ negative implementation here
+
+error[E0119]: conflicting implementations of trait `std::marker::Send` for type `TestType<_>`
+ --> $DIR/coherence-conflicting-negative-trait-impl.rs:13:1
+ |
+LL | unsafe impl<T: MyTrait + 'static> Send for TestType<T> {}
+ | ------------------------------------------------------ first implementation here
+...
+LL | unsafe impl<T: 'static> Send for TestType<T> {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `TestType<_>`
+
+error: aborting due to 2 previous errors
+
+Some errors have detailed explanations: E0119, E0751.
+For more information about an error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-covered-type-parameter.rs b/src/test/ui/coherence/coherence-covered-type-parameter.rs
new file mode 100644
index 000000000..bb95c59d1
--- /dev/null
+++ b/src/test/ui/coherence/coherence-covered-type-parameter.rs
@@ -0,0 +1,14 @@
+// run-pass
+#![allow(dead_code)]
+// aux-build:coherence_lib.rs
+
+// pretty-expanded FIXME #23616
+
+extern crate coherence_lib as lib;
+use lib::Remote;
+
+struct Foo<T>(T);
+
+impl<T> Remote for Foo<T> { }
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-cow.re_a.stderr b/src/test/ui/coherence/coherence-cow.re_a.stderr
new file mode 100644
index 000000000..fe4b5b410
--- /dev/null
+++ b/src/test/ui/coherence/coherence-cow.re_a.stderr
@@ -0,0 +1,14 @@
+error[E0117]: only traits defined in the current crate can be implemented for types defined outside of the crate
+ --> $DIR/coherence-cow.rs:18:1
+ |
+LL | impl<T> Remote for Pair<T,Cover<T>> { }
+ | ^^^^^^^^^^^^^^^^^^^----------------
+ | | |
+ | | `Pair` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-cow.re_b.stderr b/src/test/ui/coherence/coherence-cow.re_b.stderr
new file mode 100644
index 000000000..da4ede325
--- /dev/null
+++ b/src/test/ui/coherence/coherence-cow.re_b.stderr
@@ -0,0 +1,14 @@
+error[E0117]: only traits defined in the current crate can be implemented for types defined outside of the crate
+ --> $DIR/coherence-cow.rs:22:1
+ |
+LL | impl<T> Remote for Pair<Cover<T>,T> { }
+ | ^^^^^^^^^^^^^^^^^^^----------------
+ | | |
+ | | `Pair` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-cow.re_c.stderr b/src/test/ui/coherence/coherence-cow.re_c.stderr
new file mode 100644
index 000000000..d1a20c0ca
--- /dev/null
+++ b/src/test/ui/coherence/coherence-cow.re_c.stderr
@@ -0,0 +1,14 @@
+error[E0117]: only traits defined in the current crate can be implemented for types defined outside of the crate
+ --> $DIR/coherence-cow.rs:26:1
+ |
+LL | impl<T,U> Remote for Pair<Cover<T>,U> { }
+ | ^^^^^^^^^^^^^^^^^^^^^----------------
+ | | |
+ | | `Pair` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-cow.rs b/src/test/ui/coherence/coherence-cow.rs
new file mode 100644
index 000000000..86a8d0963
--- /dev/null
+++ b/src/test/ui/coherence/coherence-cow.rs
@@ -0,0 +1,29 @@
+// revisions: re_a re_b re_c
+
+#![cfg_attr(any(), re_a, re_b, re_c)]
+
+// aux-build:coherence_lib.rs
+
+// Test that the `Pair` type reports an error if it contains type
+// parameters, even when they are covered by local types. This test
+// was originally intended to test the opposite, but the rules changed
+// with RFC 1023 and this became illegal.
+
+extern crate coherence_lib as lib;
+use lib::{Remote,Pair};
+
+pub struct Cover<T>(T);
+
+#[cfg(any(re_a))]
+impl<T> Remote for Pair<T,Cover<T>> { }
+//[re_a]~^ ERROR E0117
+
+#[cfg(any(re_b))]
+impl<T> Remote for Pair<Cover<T>,T> { }
+//[re_b]~^ ERROR E0117
+
+#[cfg(any(re_c))]
+impl<T,U> Remote for Pair<Cover<T>,U> { }
+//[re_c]~^ ERROR E0117
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-cross-crate-conflict.rs b/src/test/ui/coherence/coherence-cross-crate-conflict.rs
new file mode 100644
index 000000000..588630957
--- /dev/null
+++ b/src/test/ui/coherence/coherence-cross-crate-conflict.rs
@@ -0,0 +1,13 @@
+// The error here is strictly due to orphan rules; the impl here
+// generalizes the one upstream
+
+// aux-build:trait_impl_conflict.rs
+
+extern crate trait_impl_conflict;
+use trait_impl_conflict::Foo;
+
+impl<A> Foo for A { //~ ERROR E0210
+}
+
+fn main() {
+}
diff --git a/src/test/ui/coherence/coherence-cross-crate-conflict.stderr b/src/test/ui/coherence/coherence-cross-crate-conflict.stderr
new file mode 100644
index 000000000..3d253d56a
--- /dev/null
+++ b/src/test/ui/coherence/coherence-cross-crate-conflict.stderr
@@ -0,0 +1,12 @@
+error[E0210]: type parameter `A` must be used as the type parameter for some local type (e.g., `MyStruct<A>`)
+ --> $DIR/coherence-cross-crate-conflict.rs:9:6
+ |
+LL | impl<A> Foo for A {
+ | ^ type parameter `A` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/coherence-default-trait-impl.rs b/src/test/ui/coherence/coherence-default-trait-impl.rs
new file mode 100644
index 000000000..d57fb4777
--- /dev/null
+++ b/src/test/ui/coherence/coherence-default-trait-impl.rs
@@ -0,0 +1,16 @@
+#![feature(auto_traits)]
+#![feature(negative_impls)]
+
+auto trait MySafeTrait {}
+
+struct Foo;
+
+unsafe impl MySafeTrait for Foo {}
+//~^ ERROR E0199
+
+unsafe auto trait MyUnsafeTrait {}
+
+impl MyUnsafeTrait for Foo {}
+//~^ ERROR E0200
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-default-trait-impl.stderr b/src/test/ui/coherence/coherence-default-trait-impl.stderr
new file mode 100644
index 000000000..b08ccb087
--- /dev/null
+++ b/src/test/ui/coherence/coherence-default-trait-impl.stderr
@@ -0,0 +1,16 @@
+error[E0199]: implementing the trait `MySafeTrait` is not unsafe
+ --> $DIR/coherence-default-trait-impl.rs:8:1
+ |
+LL | unsafe impl MySafeTrait for Foo {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error[E0200]: the trait `MyUnsafeTrait` requires an `unsafe impl` declaration
+ --> $DIR/coherence-default-trait-impl.rs:13:1
+ |
+LL | impl MyUnsafeTrait for Foo {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: aborting due to 2 previous errors
+
+Some errors have detailed explanations: E0199, E0200.
+For more information about an error, try `rustc --explain E0199`.
diff --git a/src/test/ui/coherence/coherence-error-suppression.rs b/src/test/ui/coherence/coherence-error-suppression.rs
new file mode 100644
index 000000000..909214c1b
--- /dev/null
+++ b/src/test/ui/coherence/coherence-error-suppression.rs
@@ -0,0 +1,16 @@
+// check that error types in coherence do not cause error cascades.
+
+trait Foo {}
+
+impl Foo for i8 {}
+impl Foo for i16 {}
+impl Foo for i32 {}
+impl Foo for i64 {}
+impl Foo for DoesNotExist {}
+//~^ ERROR E0412
+impl Foo for u8 {}
+impl Foo for u16 {}
+impl Foo for u32 {}
+impl Foo for u64 {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-error-suppression.stderr b/src/test/ui/coherence/coherence-error-suppression.stderr
new file mode 100644
index 000000000..aadc80cb1
--- /dev/null
+++ b/src/test/ui/coherence/coherence-error-suppression.stderr
@@ -0,0 +1,9 @@
+error[E0412]: cannot find type `DoesNotExist` in this scope
+ --> $DIR/coherence-error-suppression.rs:9:14
+ |
+LL | impl Foo for DoesNotExist {}
+ | ^^^^^^^^^^^^ not found in this scope
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0412`.
diff --git a/src/test/ui/coherence/coherence-fn-covariant-bound-vs-static.rs b/src/test/ui/coherence/coherence-fn-covariant-bound-vs-static.rs
new file mode 100644
index 000000000..99f805f7f
--- /dev/null
+++ b/src/test/ui/coherence/coherence-fn-covariant-bound-vs-static.rs
@@ -0,0 +1,26 @@
+// Test that impls for these two types are considered ovelapping:
+//
+// * `for<'r> fn(fn(&'r u32))`
+// * `fn(fn(&'a u32)` where `'a` is free
+//
+// This is because, for `'a = 'static`, the two types overlap.
+// Effectively for them to be equal to you get:
+//
+// * `for<'r> fn(fn(&'r u32)) <: fn(fn(&'static u32))`
+// * true if `exists<'r> { 'r: 'static }` (obviously true)
+// * `fn(fn(&'static u32)) <: for<'r> fn(fn(&'r u32))`
+// * true if `forall<'r> { 'static: 'r }` (also true)
+
+trait Trait {}
+
+impl Trait for for<'r> fn(fn(&'r ())) {}
+impl<'a> Trait for fn(fn(&'a ())) {}
+//~^ ERROR conflicting implementations
+//
+// Note in particular that we do NOT get a future-compatibility warning
+// here. This is because the new leak-check proposed in [MCP 295] does not
+// "error" when these two types are equated.
+//
+// [MCP 295]: https://github.com/rust-lang/compiler-team/issues/295
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-fn-covariant-bound-vs-static.stderr b/src/test/ui/coherence/coherence-fn-covariant-bound-vs-static.stderr
new file mode 100644
index 000000000..cfcef9699
--- /dev/null
+++ b/src/test/ui/coherence/coherence-fn-covariant-bound-vs-static.stderr
@@ -0,0 +1,13 @@
+error[E0119]: conflicting implementations of trait `Trait` for type `for<'r> fn(for<'r> fn(&'r ()))`
+ --> $DIR/coherence-fn-covariant-bound-vs-static.rs:17:1
+ |
+LL | impl Trait for for<'r> fn(fn(&'r ())) {}
+ | ------------------------------------- first implementation here
+LL | impl<'a> Trait for fn(fn(&'a ())) {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `for<'r> fn(for<'r> fn(&'r ()))`
+ |
+ = note: this behavior recently changed as a result of a bug fix; see rust-lang/rust#56105 for details
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-fn-implied-bounds.rs b/src/test/ui/coherence/coherence-fn-implied-bounds.rs
new file mode 100644
index 000000000..4539af9a3
--- /dev/null
+++ b/src/test/ui/coherence/coherence-fn-implied-bounds.rs
@@ -0,0 +1,26 @@
+// Test that our leak-check is not smart enough to take implied bounds
+// into account (yet). Here we have two types that look like they
+// should not be equivalent, but because of the rules on implied
+// bounds we ought to know that, in fact, `'a = 'b` must always hold,
+// and hence they are.
+//
+// Rustc can't figure this out and hence it accepts the impls but
+// gives a future-compatibility warning (because we'd like to make
+// this an error someday).
+//
+// Note that while we would like to make this a hard error, we also
+// give the same warning for `coherence-wasm-bindgen.rs`, which ought
+// to be accepted.
+
+#![deny(coherence_leak_check)]
+
+trait Trait {}
+
+impl Trait for for<'a, 'b> fn(&'a &'b u32, &'b &'a u32) -> &'b u32 {}
+
+impl Trait for for<'c> fn(&'c &'c u32, &'c &'c u32) -> &'c u32 {
+ //~^ ERROR conflicting implementations
+ //~| WARNING this was previously accepted by the compiler
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-fn-implied-bounds.stderr b/src/test/ui/coherence/coherence-fn-implied-bounds.stderr
new file mode 100644
index 000000000..8612ce60d
--- /dev/null
+++ b/src/test/ui/coherence/coherence-fn-implied-bounds.stderr
@@ -0,0 +1,20 @@
+error: conflicting implementations of trait `Trait` for type `for<'a, 'b> fn(&'a &'b u32, &'b &'a u32) -> &'b u32`
+ --> $DIR/coherence-fn-implied-bounds.rs:21:1
+ |
+LL | impl Trait for for<'a, 'b> fn(&'a &'b u32, &'b &'a u32) -> &'b u32 {}
+ | ------------------------------------------------------------------ first implementation here
+LL |
+LL | impl Trait for for<'c> fn(&'c &'c u32, &'c &'c u32) -> &'c u32 {
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `for<'a, 'b> fn(&'a &'b u32, &'b &'a u32) -> &'b u32`
+ |
+note: the lint level is defined here
+ --> $DIR/coherence-fn-implied-bounds.rs:15:9
+ |
+LL | #![deny(coherence_leak_check)]
+ | ^^^^^^^^^^^^^^^^^^^^
+ = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
+ = note: for more information, see issue #56105 <https://github.com/rust-lang/rust/issues/56105>
+ = note: this behavior recently changed as a result of a bug fix; see rust-lang/rust#56105 for details
+
+error: aborting due to previous error
+
diff --git a/src/test/ui/coherence/coherence-fn-inputs.rs b/src/test/ui/coherence/coherence-fn-inputs.rs
new file mode 100644
index 000000000..3afec5c54
--- /dev/null
+++ b/src/test/ui/coherence/coherence-fn-inputs.rs
@@ -0,0 +1,25 @@
+// Test that we consider these two types completely equal:
+//
+// * `for<'a, 'b> fn(&'a u32, &'b u32)`
+// * `for<'c> fn(&'c u32, &'c u32)`
+//
+// For a long time we considered these to be distinct types. But in fact they
+// are equivalent, if you work through the implications of subtyping -- this is
+// because:
+//
+// * `'c` can be the intersection of `'a` and `'b` (and there is always an intersection)
+// * `'a` and `'b` can both be equal to `'c`
+
+trait Trait {}
+impl Trait for for<'a, 'b> fn(&'a u32, &'b u32) {}
+impl Trait for for<'c> fn(&'c u32, &'c u32) {
+ //~^ ERROR conflicting implementations
+ //
+ // Note in particular that we do NOT get a future-compatibility warning
+ // here. This is because the new leak-check proposed in [MCP 295] does not
+ // "error" when these two types are equated.
+ //
+ // [MCP 295]: https://github.com/rust-lang/compiler-team/issues/295
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-fn-inputs.stderr b/src/test/ui/coherence/coherence-fn-inputs.stderr
new file mode 100644
index 000000000..82bd8a35f
--- /dev/null
+++ b/src/test/ui/coherence/coherence-fn-inputs.stderr
@@ -0,0 +1,13 @@
+error[E0119]: conflicting implementations of trait `Trait` for type `for<'a, 'b> fn(&'a u32, &'b u32)`
+ --> $DIR/coherence-fn-inputs.rs:15:1
+ |
+LL | impl Trait for for<'a, 'b> fn(&'a u32, &'b u32) {}
+ | ----------------------------------------------- first implementation here
+LL | impl Trait for for<'c> fn(&'c u32, &'c u32) {
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `for<'a, 'b> fn(&'a u32, &'b u32)`
+ |
+ = note: this behavior recently changed as a result of a bug fix; see rust-lang/rust#56105 for details
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-free-vs-bound-region.rs b/src/test/ui/coherence/coherence-free-vs-bound-region.rs
new file mode 100644
index 000000000..2f5c49d29
--- /dev/null
+++ b/src/test/ui/coherence/coherence-free-vs-bound-region.rs
@@ -0,0 +1,21 @@
+// Capture a coherence pattern from wasm-bindgen that we discovered as part of
+// future-compatibility warning #56105. This pattern currently receives a lint
+// warning but we probably want to support it long term.
+//
+// Key distinction: we are implementing once for `A` (take ownership) and one
+// for `&A` (borrow).
+//
+// c.f. #56105
+
+#![deny(coherence_leak_check)]
+
+trait TheTrait {}
+
+impl<'a> TheTrait for fn(&'a u8) {}
+
+impl TheTrait for fn(&u8) {
+ //~^ ERROR conflicting implementations of trait
+ //~| WARNING this was previously accepted by the compiler
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-free-vs-bound-region.stderr b/src/test/ui/coherence/coherence-free-vs-bound-region.stderr
new file mode 100644
index 000000000..af18655b0
--- /dev/null
+++ b/src/test/ui/coherence/coherence-free-vs-bound-region.stderr
@@ -0,0 +1,20 @@
+error: conflicting implementations of trait `TheTrait` for type `fn(&u8)`
+ --> $DIR/coherence-free-vs-bound-region.rs:16:1
+ |
+LL | impl<'a> TheTrait for fn(&'a u8) {}
+ | -------------------------------- first implementation here
+LL |
+LL | impl TheTrait for fn(&u8) {
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `fn(&u8)`
+ |
+note: the lint level is defined here
+ --> $DIR/coherence-free-vs-bound-region.rs:10:9
+ |
+LL | #![deny(coherence_leak_check)]
+ | ^^^^^^^^^^^^^^^^^^^^
+ = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
+ = note: for more information, see issue #56105 <https://github.com/rust-lang/rust/issues/56105>
+ = note: this behavior recently changed as a result of a bug fix; see rust-lang/rust#56105 for details
+
+error: aborting due to previous error
+
diff --git a/src/test/ui/coherence/coherence-fundamental-trait-objects.rs b/src/test/ui/coherence/coherence-fundamental-trait-objects.rs
new file mode 100644
index 000000000..dd127bf7f
--- /dev/null
+++ b/src/test/ui/coherence/coherence-fundamental-trait-objects.rs
@@ -0,0 +1,15 @@
+// Check that trait objects from #[fundamental] traits are not
+// treated as #[fundamental] types - the 2 meanings of #[fundamental]
+// are distinct.
+
+// aux-build:coherence_fundamental_trait_lib.rs
+
+extern crate coherence_fundamental_trait_lib;
+
+use coherence_fundamental_trait_lib::{Fundamental, Misc};
+
+pub struct Local;
+impl Misc for dyn Fundamental<Local> {}
+//~^ ERROR E0117
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-fundamental-trait-objects.stderr b/src/test/ui/coherence/coherence-fundamental-trait-objects.stderr
new file mode 100644
index 000000000..a35a95ef4
--- /dev/null
+++ b/src/test/ui/coherence/coherence-fundamental-trait-objects.stderr
@@ -0,0 +1,14 @@
+error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
+ --> $DIR/coherence-fundamental-trait-objects.rs:12:1
+ |
+LL | impl Misc for dyn Fundamental<Local> {}
+ | ^^^^^^^^^^^^^^----------------------
+ | | |
+ | | `dyn Fundamental<Local>` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-impl-in-fn.rs b/src/test/ui/coherence/coherence-impl-in-fn.rs
new file mode 100644
index 000000000..b97197317
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impl-in-fn.rs
@@ -0,0 +1,14 @@
+// run-pass
+#![allow(dead_code)]
+#![allow(non_camel_case_types)]
+
+pub fn main() {
+ #[derive(Copy, Clone)]
+ enum x { foo }
+ impl ::std::cmp::PartialEq for x {
+ fn eq(&self, other: &x) -> bool {
+ (*self) as isize == (*other) as isize
+ }
+ fn ne(&self, other: &x) -> bool { !(*self).eq(other) }
+ }
+}
diff --git a/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-negative.rs b/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-negative.rs
new file mode 100644
index 000000000..50d9a480a
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-negative.rs
@@ -0,0 +1,30 @@
+#![feature(auto_traits)]
+#![feature(negative_impls)]
+
+// Test for issue #56934 - that it is impossible to redundantly
+// implement an auto-trait for a trait object type that contains it.
+
+// Negative impl variant.
+
+auto trait Marker1 {}
+auto trait Marker2 {}
+
+trait Object: Marker1 {}
+
+// A supertrait marker is illegal...
+impl !Marker1 for dyn Object + Marker2 { } //~ ERROR E0371
+// ...and also a direct component.
+impl !Marker2 for dyn Object + Marker2 { } //~ ERROR E0371
+
+// But implementing a marker if it is not present is OK.
+impl !Marker2 for dyn Object {} // OK
+
+// A non-principal trait-object type is orphan even in its crate.
+impl !Send for dyn Marker2 {} //~ ERROR E0117
+
+// And impl'ing a remote marker for a local trait object is forbidden
+// by one of these special orphan-like rules.
+impl !Send for dyn Object {} //~ ERROR E0321
+impl !Send for dyn Object + Marker2 {} //~ ERROR E0321
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-negative.stderr b/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-negative.stderr
new file mode 100644
index 000000000..c364c707f
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-negative.stderr
@@ -0,0 +1,39 @@
+error[E0371]: the object type `(dyn Object + Marker2 + 'static)` automatically implements the trait `Marker1`
+ --> $DIR/coherence-impl-trait-for-marker-trait-negative.rs:15:1
+ |
+LL | impl !Marker1 for dyn Object + Marker2 { }
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Object + Marker2 + 'static)` automatically implements trait `Marker1`
+
+error[E0371]: the object type `(dyn Object + Marker2 + 'static)` automatically implements the trait `Marker2`
+ --> $DIR/coherence-impl-trait-for-marker-trait-negative.rs:17:1
+ |
+LL | impl !Marker2 for dyn Object + Marker2 { }
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Object + Marker2 + 'static)` automatically implements trait `Marker2`
+
+error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
+ --> $DIR/coherence-impl-trait-for-marker-trait-negative.rs:23:1
+ |
+LL | impl !Send for dyn Marker2 {}
+ | ^^^^^^^^^^^^^^^-----------
+ | | |
+ | | `dyn Marker2` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0321]: cross-crate traits with a default impl, like `Send`, can only be implemented for a struct/enum type, not `(dyn Object + 'static)`
+ --> $DIR/coherence-impl-trait-for-marker-trait-negative.rs:27:1
+ |
+LL | impl !Send for dyn Object {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^ can't implement cross-crate trait with a default impl for non-struct/enum type
+
+error[E0321]: cross-crate traits with a default impl, like `Send`, can only be implemented for a struct/enum type, not `(dyn Object + Marker2 + 'static)`
+ --> $DIR/coherence-impl-trait-for-marker-trait-negative.rs:28:1
+ |
+LL | impl !Send for dyn Object + Marker2 {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ can't implement cross-crate trait with a default impl for non-struct/enum type
+
+error: aborting due to 5 previous errors
+
+Some errors have detailed explanations: E0117, E0321, E0371.
+For more information about an error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-positive.rs b/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-positive.rs
new file mode 100644
index 000000000..faac6d983
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-positive.rs
@@ -0,0 +1,30 @@
+#![feature(auto_traits)]
+#![feature(negative_impls)]
+
+// Test for issue #56934 - that it is impossible to redundantly
+// implement an auto-trait for a trait object type that contains it.
+
+// Positive impl variant.
+
+auto trait Marker1 {}
+auto trait Marker2 {}
+
+trait Object: Marker1 {}
+
+// A supertrait marker is illegal...
+impl Marker1 for dyn Object + Marker2 { } //~ ERROR E0371
+// ...and also a direct component.
+impl Marker2 for dyn Object + Marker2 { } //~ ERROR E0371
+
+// But implementing a marker if it is not present is OK.
+impl Marker2 for dyn Object {} // OK
+
+// A non-principal trait-object type is orphan even in its crate.
+unsafe impl Send for dyn Marker2 {} //~ ERROR E0117
+
+// And impl'ing a remote marker for a local trait object is forbidden
+// by one of these special orphan-like rules.
+unsafe impl Send for dyn Object {} //~ ERROR E0321
+unsafe impl Send for dyn Object + Marker2 {} //~ ERROR E0321
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-positive.stderr b/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-positive.stderr
new file mode 100644
index 000000000..b80429794
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impl-trait-for-marker-trait-positive.stderr
@@ -0,0 +1,39 @@
+error[E0371]: the object type `(dyn Object + Marker2 + 'static)` automatically implements the trait `Marker1`
+ --> $DIR/coherence-impl-trait-for-marker-trait-positive.rs:15:1
+ |
+LL | impl Marker1 for dyn Object + Marker2 { }
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Object + Marker2 + 'static)` automatically implements trait `Marker1`
+
+error[E0371]: the object type `(dyn Object + Marker2 + 'static)` automatically implements the trait `Marker2`
+ --> $DIR/coherence-impl-trait-for-marker-trait-positive.rs:17:1
+ |
+LL | impl Marker2 for dyn Object + Marker2 { }
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `(dyn Object + Marker2 + 'static)` automatically implements trait `Marker2`
+
+error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
+ --> $DIR/coherence-impl-trait-for-marker-trait-positive.rs:23:1
+ |
+LL | unsafe impl Send for dyn Marker2 {}
+ | ^^^^^^^^^^^^^^^^^^^^^-----------
+ | | |
+ | | `dyn Marker2` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0321]: cross-crate traits with a default impl, like `Send`, can only be implemented for a struct/enum type, not `(dyn Object + 'static)`
+ --> $DIR/coherence-impl-trait-for-marker-trait-positive.rs:27:1
+ |
+LL | unsafe impl Send for dyn Object {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ can't implement cross-crate trait with a default impl for non-struct/enum type
+
+error[E0321]: cross-crate traits with a default impl, like `Send`, can only be implemented for a struct/enum type, not `(dyn Object + Marker2 + 'static)`
+ --> $DIR/coherence-impl-trait-for-marker-trait-positive.rs:28:1
+ |
+LL | unsafe impl Send for dyn Object + Marker2 {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ can't implement cross-crate trait with a default impl for non-struct/enum type
+
+error: aborting due to 5 previous errors
+
+Some errors have detailed explanations: E0117, E0321, E0371.
+For more information about an error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-impl-trait-for-trait-object-safe.rs b/src/test/ui/coherence/coherence-impl-trait-for-trait-object-safe.rs
new file mode 100644
index 000000000..20ff87549
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impl-trait-for-trait-object-safe.rs
@@ -0,0 +1,10 @@
+// Test that we give suitable error messages when the user attempts to
+// impl a trait `Trait` for its own object type.
+
+// If the trait is not object-safe, we give a more tailored message
+// because we're such schnuckels:
+trait NotObjectSafe { fn eq(&self, other: Self); }
+impl NotObjectSafe for dyn NotObjectSafe { }
+//~^ ERROR E0038
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-impl-trait-for-trait-object-safe.stderr b/src/test/ui/coherence/coherence-impl-trait-for-trait-object-safe.stderr
new file mode 100644
index 000000000..e9090c1b6
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impl-trait-for-trait-object-safe.stderr
@@ -0,0 +1,18 @@
+error[E0038]: the trait `NotObjectSafe` cannot be made into an object
+ --> $DIR/coherence-impl-trait-for-trait-object-safe.rs:7:24
+ |
+LL | impl NotObjectSafe for dyn NotObjectSafe { }
+ | ^^^^^^^^^^^^^^^^^ `NotObjectSafe` cannot be made into an object
+ |
+note: for a trait to be "object safe" it needs to allow building a vtable to allow the call to be resolvable dynamically; for more information visit <https://doc.rust-lang.org/reference/items/traits.html#object-safety>
+ --> $DIR/coherence-impl-trait-for-trait-object-safe.rs:6:43
+ |
+LL | trait NotObjectSafe { fn eq(&self, other: Self); }
+ | ------------- ^^^^ ...because method `eq` references the `Self` type in this parameter
+ | |
+ | this trait cannot be made into an object...
+ = help: consider moving `eq` to another trait
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0038`.
diff --git a/src/test/ui/coherence/coherence-impl-trait-for-trait.rs b/src/test/ui/coherence/coherence-impl-trait-for-trait.rs
new file mode 100644
index 000000000..195a37f15
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impl-trait-for-trait.rs
@@ -0,0 +1,20 @@
+// Test that we give suitable error messages when the user attempts to
+// impl a trait `Trait` for its own object type.
+
+trait Foo { fn dummy(&self) { } }
+trait Bar: Foo { }
+trait Baz: Bar { }
+
+// Supertraits of Baz are not legal:
+impl Foo for dyn Baz { }
+//~^ ERROR E0371
+impl Bar for dyn Baz { }
+//~^ ERROR E0371
+impl Baz for dyn Baz { }
+//~^ ERROR E0371
+
+// But other random traits are:
+trait Other { }
+impl Other for dyn Baz { } // OK, Other not a supertrait of Baz
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-impl-trait-for-trait.stderr b/src/test/ui/coherence/coherence-impl-trait-for-trait.stderr
new file mode 100644
index 000000000..cf0b38c5b
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impl-trait-for-trait.stderr
@@ -0,0 +1,21 @@
+error[E0371]: the object type `(dyn Baz + 'static)` automatically implements the trait `Foo`
+ --> $DIR/coherence-impl-trait-for-trait.rs:9:1
+ |
+LL | impl Foo for dyn Baz { }
+ | ^^^^^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Foo`
+
+error[E0371]: the object type `(dyn Baz + 'static)` automatically implements the trait `Bar`
+ --> $DIR/coherence-impl-trait-for-trait.rs:11:1
+ |
+LL | impl Bar for dyn Baz { }
+ | ^^^^^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Bar`
+
+error[E0371]: the object type `(dyn Baz + 'static)` automatically implements the trait `Baz`
+ --> $DIR/coherence-impl-trait-for-trait.rs:13:1
+ |
+LL | impl Baz for dyn Baz { }
+ | ^^^^^^^^^^^^^^^^^^^^ `(dyn Baz + 'static)` automatically implements trait `Baz`
+
+error: aborting due to 3 previous errors
+
+For more information about this error, try `rustc --explain E0371`.
diff --git a/src/test/ui/coherence/coherence-impls-copy.rs b/src/test/ui/coherence/coherence-impls-copy.rs
new file mode 100644
index 000000000..4204fecc3
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impls-copy.rs
@@ -0,0 +1,36 @@
+#![feature(negative_impls)]
+
+use std::marker::Copy;
+
+impl Copy for i32 {}
+//~^ ERROR E0117
+enum TestE {
+ A
+}
+
+struct MyType;
+
+struct NotSync;
+impl !Sync for NotSync {}
+
+impl Copy for TestE {}
+impl Clone for TestE { fn clone(&self) -> Self { *self } }
+
+impl Copy for MyType {}
+
+impl Copy for &'static mut MyType {}
+//~^ ERROR E0206
+impl Clone for MyType { fn clone(&self) -> Self { *self } }
+
+impl Copy for (MyType, MyType) {}
+//~^ ERROR E0206
+//~| ERROR E0117
+impl Copy for &'static NotSync {}
+//~^ ERROR E0119
+impl Copy for [MyType] {}
+//~^ ERROR E0206
+//~| ERROR E0117
+impl Copy for &'static [NotSync] {}
+//~^ ERROR E0117
+fn main() {
+}
diff --git a/src/test/ui/coherence/coherence-impls-copy.stderr b/src/test/ui/coherence/coherence-impls-copy.stderr
new file mode 100644
index 000000000..86356af25
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impls-copy.stderr
@@ -0,0 +1,76 @@
+error[E0117]: only traits defined in the current crate can be implemented for primitive types
+ --> $DIR/coherence-impls-copy.rs:5:1
+ |
+LL | impl Copy for i32 {}
+ | ^^^^^^^^^^^^^^---
+ | | |
+ | | `i32` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0119]: conflicting implementations of trait `std::marker::Copy` for type `&NotSync`
+ --> $DIR/coherence-impls-copy.rs:28:1
+ |
+LL | impl Copy for &'static NotSync {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+ |
+ = note: conflicting implementation in crate `core`:
+ - impl<T> Copy for &T
+ where T: ?Sized;
+
+error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
+ --> $DIR/coherence-impls-copy.rs:33:1
+ |
+LL | impl Copy for &'static [NotSync] {}
+ | ^^^^^^^^^^^^^^------------------
+ | | |
+ | | this is not defined in the current crate because slices are always foreign
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
+ --> $DIR/coherence-impls-copy.rs:25:1
+ |
+LL | impl Copy for (MyType, MyType) {}
+ | ^^^^^^^^^^^^^^----------------
+ | | |
+ | | this is not defined in the current crate because tuples are always foreign
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
+ --> $DIR/coherence-impls-copy.rs:30:1
+ |
+LL | impl Copy for [MyType] {}
+ | ^^^^^^^^^^^^^^--------
+ | | |
+ | | this is not defined in the current crate because slices are always foreign
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0206]: the trait `Copy` may not be implemented for this type
+ --> $DIR/coherence-impls-copy.rs:21:15
+ |
+LL | impl Copy for &'static mut MyType {}
+ | ^^^^^^^^^^^^^^^^^^^ type is not a structure or enumeration
+
+error[E0206]: the trait `Copy` may not be implemented for this type
+ --> $DIR/coherence-impls-copy.rs:25:15
+ |
+LL | impl Copy for (MyType, MyType) {}
+ | ^^^^^^^^^^^^^^^^ type is not a structure or enumeration
+
+error[E0206]: the trait `Copy` may not be implemented for this type
+ --> $DIR/coherence-impls-copy.rs:30:15
+ |
+LL | impl Copy for [MyType] {}
+ | ^^^^^^^^ type is not a structure or enumeration
+
+error: aborting due to 8 previous errors
+
+Some errors have detailed explanations: E0117, E0119, E0206.
+For more information about an error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-impls-send.rs b/src/test/ui/coherence/coherence-impls-send.rs
new file mode 100644
index 000000000..b7b57c602
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impls-send.rs
@@ -0,0 +1,28 @@
+#![feature(negative_impls)]
+
+use std::marker::Copy;
+
+enum TestE {
+ A,
+}
+
+struct MyType;
+
+struct NotSync;
+impl !Sync for NotSync {}
+
+unsafe impl Send for TestE {}
+unsafe impl Send for MyType {}
+unsafe impl Send for (MyType, MyType) {}
+//~^ ERROR E0117
+
+unsafe impl Send for &'static NotSync {}
+//~^ ERROR E0321
+
+unsafe impl Send for [MyType] {}
+//~^ ERROR E0117
+
+unsafe impl Send for &'static [NotSync] {}
+//~^ ERROR only traits defined in the current crate
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-impls-send.stderr b/src/test/ui/coherence/coherence-impls-send.stderr
new file mode 100644
index 000000000..e1071846e
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impls-send.stderr
@@ -0,0 +1,43 @@
+error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
+ --> $DIR/coherence-impls-send.rs:25:1
+ |
+LL | unsafe impl Send for &'static [NotSync] {}
+ | ^^^^^^^^^^^^^^^^^^^^^------------------
+ | | |
+ | | this is not defined in the current crate because slices are always foreign
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
+ --> $DIR/coherence-impls-send.rs:16:1
+ |
+LL | unsafe impl Send for (MyType, MyType) {}
+ | ^^^^^^^^^^^^^^^^^^^^^----------------
+ | | |
+ | | this is not defined in the current crate because tuples are always foreign
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0321]: cross-crate traits with a default impl, like `Send`, can only be implemented for a struct/enum type, not `&'static NotSync`
+ --> $DIR/coherence-impls-send.rs:19:1
+ |
+LL | unsafe impl Send for &'static NotSync {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ can't implement cross-crate trait with a default impl for non-struct/enum type
+
+error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
+ --> $DIR/coherence-impls-send.rs:22:1
+ |
+LL | unsafe impl Send for [MyType] {}
+ | ^^^^^^^^^^^^^^^^^^^^^--------
+ | | |
+ | | this is not defined in the current crate because slices are always foreign
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to 4 previous errors
+
+Some errors have detailed explanations: E0117, E0321.
+For more information about an error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-impls-sized.rs b/src/test/ui/coherence/coherence-impls-sized.rs
new file mode 100644
index 000000000..231b96ad4
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impls-sized.rs
@@ -0,0 +1,36 @@
+#![feature(negative_impls)]
+
+use std::marker::Copy;
+
+enum TestE {
+ A
+}
+
+struct MyType;
+
+struct NotSync;
+impl !Sync for NotSync {}
+
+impl Sized for TestE {}
+//~^ ERROR E0322
+
+impl Sized for MyType {}
+//~^ ERROR E0322
+
+impl Sized for (MyType, MyType) {}
+//~^ ERROR E0322
+//~| ERROR E0117
+
+impl Sized for &'static NotSync {}
+//~^ ERROR E0322
+
+impl Sized for [MyType] {}
+//~^ ERROR E0322
+//~| ERROR E0117
+
+impl Sized for &'static [NotSync] {}
+//~^ ERROR E0322
+//~| ERROR E0117
+
+fn main() {
+}
diff --git a/src/test/ui/coherence/coherence-impls-sized.stderr b/src/test/ui/coherence/coherence-impls-sized.stderr
new file mode 100644
index 000000000..17a754452
--- /dev/null
+++ b/src/test/ui/coherence/coherence-impls-sized.stderr
@@ -0,0 +1,73 @@
+error[E0322]: explicit impls for the `Sized` trait are not permitted
+ --> $DIR/coherence-impls-sized.rs:14:1
+ |
+LL | impl Sized for TestE {}
+ | ^^^^^^^^^^^^^^^^^^^^ impl of `Sized` not allowed
+
+error[E0322]: explicit impls for the `Sized` trait are not permitted
+ --> $DIR/coherence-impls-sized.rs:17:1
+ |
+LL | impl Sized for MyType {}
+ | ^^^^^^^^^^^^^^^^^^^^^ impl of `Sized` not allowed
+
+error[E0322]: explicit impls for the `Sized` trait are not permitted
+ --> $DIR/coherence-impls-sized.rs:20:1
+ |
+LL | impl Sized for (MyType, MyType) {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ impl of `Sized` not allowed
+
+error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
+ --> $DIR/coherence-impls-sized.rs:20:1
+ |
+LL | impl Sized for (MyType, MyType) {}
+ | ^^^^^^^^^^^^^^^----------------
+ | | |
+ | | this is not defined in the current crate because tuples are always foreign
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0322]: explicit impls for the `Sized` trait are not permitted
+ --> $DIR/coherence-impls-sized.rs:24:1
+ |
+LL | impl Sized for &'static NotSync {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ impl of `Sized` not allowed
+
+error[E0322]: explicit impls for the `Sized` trait are not permitted
+ --> $DIR/coherence-impls-sized.rs:27:1
+ |
+LL | impl Sized for [MyType] {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^ impl of `Sized` not allowed
+
+error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
+ --> $DIR/coherence-impls-sized.rs:27:1
+ |
+LL | impl Sized for [MyType] {}
+ | ^^^^^^^^^^^^^^^--------
+ | | |
+ | | this is not defined in the current crate because slices are always foreign
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0322]: explicit impls for the `Sized` trait are not permitted
+ --> $DIR/coherence-impls-sized.rs:31:1
+ |
+LL | impl Sized for &'static [NotSync] {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ impl of `Sized` not allowed
+
+error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
+ --> $DIR/coherence-impls-sized.rs:31:1
+ |
+LL | impl Sized for &'static [NotSync] {}
+ | ^^^^^^^^^^^^^^^------------------
+ | | |
+ | | this is not defined in the current crate because slices are always foreign
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to 9 previous errors
+
+Some errors have detailed explanations: E0117, E0322.
+For more information about an error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-inherited-assoc-ty-cycle-err.rs b/src/test/ui/coherence/coherence-inherited-assoc-ty-cycle-err.rs
new file mode 100644
index 000000000..d74d3a2a5
--- /dev/null
+++ b/src/test/ui/coherence/coherence-inherited-assoc-ty-cycle-err.rs
@@ -0,0 +1,24 @@
+// Formerly this ICEd with the following message:
+// Tried to project an inherited associated type during coherence checking,
+// which is currently not supported.
+//
+// No we expect to run into a more user-friendly cycle error instead.
+#![feature(specialization)]
+//~^ WARN the feature `specialization` is incomplete
+
+trait Trait<T> { type Assoc; }
+//~^ ERROR E0391
+
+impl<T> Trait<T> for Vec<T> {
+ type Assoc = ();
+}
+
+impl Trait<u8> for Vec<u8> {}
+
+impl<T> Trait<T> for String {
+ type Assoc = ();
+}
+
+impl Trait<<Vec<u8> as Trait<u8>>::Assoc> for String {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-inherited-assoc-ty-cycle-err.stderr b/src/test/ui/coherence/coherence-inherited-assoc-ty-cycle-err.stderr
new file mode 100644
index 000000000..97f3c7593
--- /dev/null
+++ b/src/test/ui/coherence/coherence-inherited-assoc-ty-cycle-err.stderr
@@ -0,0 +1,26 @@
+warning: the feature `specialization` is incomplete and may not be safe to use and/or cause compiler crashes
+ --> $DIR/coherence-inherited-assoc-ty-cycle-err.rs:6:12
+ |
+LL | #![feature(specialization)]
+ | ^^^^^^^^^^^^^^
+ |
+ = note: `#[warn(incomplete_features)]` on by default
+ = note: see issue #31844 <https://github.com/rust-lang/rust/issues/31844> for more information
+ = help: consider using `min_specialization` instead, which is more stable and complete
+
+error[E0391]: cycle detected when building specialization graph of trait `Trait`
+ --> $DIR/coherence-inherited-assoc-ty-cycle-err.rs:9:1
+ |
+LL | trait Trait<T> { type Assoc; }
+ | ^^^^^^^^^^^^^^
+ |
+ = note: ...which immediately requires building specialization graph of trait `Trait` again
+note: cycle used when coherence checking all impls of trait `Trait`
+ --> $DIR/coherence-inherited-assoc-ty-cycle-err.rs:9:1
+ |
+LL | trait Trait<T> { type Assoc; }
+ | ^^^^^^^^^^^^^^
+
+error: aborting due to previous error; 1 warning emitted
+
+For more information about this error, try `rustc --explain E0391`.
diff --git a/src/test/ui/coherence/coherence-inherited-subtyping.old.stderr b/src/test/ui/coherence/coherence-inherited-subtyping.old.stderr
new file mode 100644
index 000000000..4701bc0b1
--- /dev/null
+++ b/src/test/ui/coherence/coherence-inherited-subtyping.old.stderr
@@ -0,0 +1,14 @@
+error[E0592]: duplicate definitions with name `method1`
+ --> $DIR/coherence-inherited-subtyping.rs:14:5
+ |
+LL | fn method1(&self) {}
+ | ^^^^^^^^^^^^^^^^^ duplicate definitions for `method1`
+...
+LL | fn method1(&self) {}
+ | ----------------- other definition for `method1`
+ |
+ = note: this behavior recently changed as a result of a bug fix; see rust-lang/rust#56105 for details
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0592`.
diff --git a/src/test/ui/coherence/coherence-inherited-subtyping.re.stderr b/src/test/ui/coherence/coherence-inherited-subtyping.re.stderr
new file mode 100644
index 000000000..4701bc0b1
--- /dev/null
+++ b/src/test/ui/coherence/coherence-inherited-subtyping.re.stderr
@@ -0,0 +1,14 @@
+error[E0592]: duplicate definitions with name `method1`
+ --> $DIR/coherence-inherited-subtyping.rs:14:5
+ |
+LL | fn method1(&self) {}
+ | ^^^^^^^^^^^^^^^^^ duplicate definitions for `method1`
+...
+LL | fn method1(&self) {}
+ | ----------------- other definition for `method1`
+ |
+ = note: this behavior recently changed as a result of a bug fix; see rust-lang/rust#56105 for details
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0592`.
diff --git a/src/test/ui/coherence/coherence-inherited-subtyping.rs b/src/test/ui/coherence/coherence-inherited-subtyping.rs
new file mode 100644
index 000000000..8587eb779
--- /dev/null
+++ b/src/test/ui/coherence/coherence-inherited-subtyping.rs
@@ -0,0 +1,21 @@
+// Test that two distinct impls which match subtypes of one another
+// yield coherence errors (or not) depending on the variance.
+//
+// Note: This scenario is currently accepted, but as part of the
+// universe transition (#56105) may eventually become an error.
+
+// revisions: old re
+
+struct Foo<T> {
+ t: T,
+}
+
+impl Foo<for<'a, 'b> fn(&'a u8, &'b u8) -> &'a u8> {
+ fn method1(&self) {} //~ ERROR duplicate definitions with name `method1`
+}
+
+impl Foo<for<'a> fn(&'a u8, &'a u8) -> &'a u8> {
+ fn method1(&self) {}
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-iterator-vec-any-elem.rs b/src/test/ui/coherence/coherence-iterator-vec-any-elem.rs
new file mode 100644
index 000000000..43a0a5c42
--- /dev/null
+++ b/src/test/ui/coherence/coherence-iterator-vec-any-elem.rs
@@ -0,0 +1,14 @@
+// run-pass
+#![allow(dead_code)]
+// aux-build:coherence_lib.rs
+
+// pretty-expanded FIXME #23616
+
+extern crate coherence_lib as lib;
+use lib::Remote1;
+
+struct Foo<T>(T);
+
+impl<T,U> Remote1<U> for Foo<T> { }
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-iterator-vec.rs b/src/test/ui/coherence/coherence-iterator-vec.rs
new file mode 100644
index 000000000..386fe40ac
--- /dev/null
+++ b/src/test/ui/coherence/coherence-iterator-vec.rs
@@ -0,0 +1,14 @@
+// run-pass
+#![allow(dead_code)]
+// aux-build:coherence_lib.rs
+
+// pretty-expanded FIXME #23616
+
+extern crate coherence_lib as lib;
+use lib::Remote1;
+
+struct Foo<T>(T);
+
+impl<T> Remote1<T> for Foo<T> { }
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-lone-type-parameter.rs b/src/test/ui/coherence/coherence-lone-type-parameter.rs
new file mode 100644
index 000000000..5368fef76
--- /dev/null
+++ b/src/test/ui/coherence/coherence-lone-type-parameter.rs
@@ -0,0 +1,10 @@
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::Remote;
+
+impl<T> Remote for T { }
+//~^ ERROR E0210
+
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-lone-type-parameter.stderr b/src/test/ui/coherence/coherence-lone-type-parameter.stderr
new file mode 100644
index 000000000..ef5b08836
--- /dev/null
+++ b/src/test/ui/coherence/coherence-lone-type-parameter.stderr
@@ -0,0 +1,12 @@
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/coherence-lone-type-parameter.rs:6:6
+ |
+LL | impl<T> Remote for T { }
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/coherence-multidispatch-tuple.rs b/src/test/ui/coherence/coherence-multidispatch-tuple.rs
new file mode 100644
index 000000000..fa1d4bbb4
--- /dev/null
+++ b/src/test/ui/coherence/coherence-multidispatch-tuple.rs
@@ -0,0 +1,24 @@
+// run-pass
+#![allow(unused_imports)]
+// pretty-expanded FIXME #23616
+
+use std::fmt::Debug;
+use std::default::Default;
+
+// Test that an impl for homogeneous pairs does not conflict with a
+// heterogeneous pair.
+
+trait MyTrait {
+ fn get(&self) -> usize;
+}
+
+impl<T> MyTrait for (T,T) {
+ fn get(&self) -> usize { 0 }
+}
+
+impl MyTrait for (usize,isize) {
+ fn get(&self) -> usize { 0 }
+}
+
+fn main() {
+}
diff --git a/src/test/ui/coherence/coherence-negative-impls-safe-rpass.rs b/src/test/ui/coherence/coherence-negative-impls-safe-rpass.rs
new file mode 100644
index 000000000..b87e162ac
--- /dev/null
+++ b/src/test/ui/coherence/coherence-negative-impls-safe-rpass.rs
@@ -0,0 +1,13 @@
+// run-pass
+#![allow(dead_code)]
+// pretty-expanded FIXME #23616
+
+#![feature(negative_impls)]
+
+use std::marker::Send;
+
+struct TestType;
+
+impl !Send for TestType {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-negative-impls-safe.rs b/src/test/ui/coherence/coherence-negative-impls-safe.rs
new file mode 100644
index 000000000..4821aa6b5
--- /dev/null
+++ b/src/test/ui/coherence/coherence-negative-impls-safe.rs
@@ -0,0 +1,10 @@
+#![feature(negative_impls)]
+
+use std::marker::Send;
+
+struct TestType;
+
+unsafe impl !Send for TestType {}
+//~^ ERROR E0198
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-negative-impls-safe.stderr b/src/test/ui/coherence/coherence-negative-impls-safe.stderr
new file mode 100644
index 000000000..1bd37f395
--- /dev/null
+++ b/src/test/ui/coherence/coherence-negative-impls-safe.stderr
@@ -0,0 +1,12 @@
+error[E0198]: negative impls cannot be unsafe
+ --> $DIR/coherence-negative-impls-safe.rs:7:13
+ |
+LL | unsafe impl !Send for TestType {}
+ | ------ -^^^^
+ | | |
+ | | negative because of this
+ | unsafe because of this
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0198`.
diff --git a/src/test/ui/coherence/coherence-negative-inherent-where-bounds.rs b/src/test/ui/coherence/coherence-negative-inherent-where-bounds.rs
new file mode 100644
index 000000000..39ccaa6ac
--- /dev/null
+++ b/src/test/ui/coherence/coherence-negative-inherent-where-bounds.rs
@@ -0,0 +1,25 @@
+// check-pass
+
+#![feature(negative_impls)]
+#![feature(rustc_attrs)]
+#![feature(with_negative_coherence)]
+
+trait Foo {}
+
+impl !Foo for u32 {}
+
+#[rustc_strict_coherence]
+struct MyStruct<T>(T);
+
+impl MyStruct<u32> {
+ fn method(&self) {}
+}
+
+impl<T> MyStruct<T>
+where
+ T: Foo,
+{
+ fn method(&self) {}
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-negative-inherent.rs b/src/test/ui/coherence/coherence-negative-inherent.rs
new file mode 100644
index 000000000..a9e1acc80
--- /dev/null
+++ b/src/test/ui/coherence/coherence-negative-inherent.rs
@@ -0,0 +1,22 @@
+// check-pass
+
+#![feature(negative_impls)]
+#![feature(rustc_attrs)]
+#![feature(with_negative_coherence)]
+
+#[rustc_strict_coherence]
+trait Foo {}
+
+impl !Foo for u32 {}
+
+struct MyStruct<T>(T);
+
+impl<T: Foo> MyStruct<T> {
+ fn method(&self) {}
+}
+
+impl MyStruct<u32> {
+ fn method(&self) {}
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-negative-outlives-lifetimes.rs b/src/test/ui/coherence/coherence-negative-outlives-lifetimes.rs
new file mode 100644
index 000000000..159788b1b
--- /dev/null
+++ b/src/test/ui/coherence/coherence-negative-outlives-lifetimes.rs
@@ -0,0 +1,12 @@
+#![feature(negative_impls)]
+
+// FIXME: this should compile
+
+trait MyPredicate<'a> {}
+impl<'a, T> !MyPredicate<'a> for &T where T: 'a {}
+trait MyTrait<'a> {}
+impl<'a, T: MyPredicate<'a>> MyTrait<'a> for T {}
+impl<'a, T> MyTrait<'a> for &'a T {}
+//~^ ERROR: conflicting implementations of trait `MyTrait<'_>` for type `&_`
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-negative-outlives-lifetimes.stderr b/src/test/ui/coherence/coherence-negative-outlives-lifetimes.stderr
new file mode 100644
index 000000000..263bd19b4
--- /dev/null
+++ b/src/test/ui/coherence/coherence-negative-outlives-lifetimes.stderr
@@ -0,0 +1,11 @@
+error[E0119]: conflicting implementations of trait `MyTrait<'_>` for type `&_`
+ --> $DIR/coherence-negative-outlives-lifetimes.rs:9:1
+ |
+LL | impl<'a, T: MyPredicate<'a>> MyTrait<'a> for T {}
+ | ---------------------------------------------- first implementation here
+LL | impl<'a, T> MyTrait<'a> for &'a T {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `&_`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-no-direct-lifetime-dispatch.rs b/src/test/ui/coherence/coherence-no-direct-lifetime-dispatch.rs
new file mode 100644
index 000000000..d466dcac1
--- /dev/null
+++ b/src/test/ui/coherence/coherence-no-direct-lifetime-dispatch.rs
@@ -0,0 +1,9 @@
+// Test that you cannot *directly* dispatch on lifetime requirements
+
+trait MyTrait { fn foo() {} }
+
+impl<T> MyTrait for T {}
+impl<T: 'static> MyTrait for T {}
+//~^ ERROR E0119
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-no-direct-lifetime-dispatch.stderr b/src/test/ui/coherence/coherence-no-direct-lifetime-dispatch.stderr
new file mode 100644
index 000000000..8a43ad7b7
--- /dev/null
+++ b/src/test/ui/coherence/coherence-no-direct-lifetime-dispatch.stderr
@@ -0,0 +1,11 @@
+error[E0119]: conflicting implementations of trait `MyTrait`
+ --> $DIR/coherence-no-direct-lifetime-dispatch.rs:6:1
+ |
+LL | impl<T> MyTrait for T {}
+ | --------------------- first implementation here
+LL | impl<T: 'static> MyTrait for T {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-orphan.rs b/src/test/ui/coherence/coherence-orphan.rs
new file mode 100644
index 000000000..3beac04c7
--- /dev/null
+++ b/src/test/ui/coherence/coherence-orphan.rs
@@ -0,0 +1,20 @@
+// aux-build:coherence_orphan_lib.rs
+#![feature(negative_impls)]
+
+extern crate coherence_orphan_lib as lib;
+
+use lib::TheTrait;
+
+struct TheType;
+
+impl TheTrait<usize> for isize { }
+//~^ ERROR E0117
+
+impl TheTrait<TheType> for isize { }
+
+impl TheTrait<isize> for TheType { }
+
+impl !Send for Vec<isize> { }
+//~^ ERROR E0117
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-orphan.stderr b/src/test/ui/coherence/coherence-orphan.stderr
new file mode 100644
index 000000000..01f166a21
--- /dev/null
+++ b/src/test/ui/coherence/coherence-orphan.stderr
@@ -0,0 +1,26 @@
+error[E0117]: only traits defined in the current crate can be implemented for primitive types
+ --> $DIR/coherence-orphan.rs:10:1
+ |
+LL | impl TheTrait<usize> for isize { }
+ | ^^^^^---------------^^^^^-----
+ | | | |
+ | | | `isize` is not defined in the current crate
+ | | `usize` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0117]: only traits defined in the current crate can be implemented for types defined outside of the crate
+ --> $DIR/coherence-orphan.rs:17:1
+ |
+LL | impl !Send for Vec<isize> { }
+ | ^^^^^^^^^^^^^^^----------
+ | | |
+ | | `Vec` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-overlap-all-t-and-tuple.rs b/src/test/ui/coherence/coherence-overlap-all-t-and-tuple.rs
new file mode 100644
index 000000000..574a16a19
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-all-t-and-tuple.rs
@@ -0,0 +1,20 @@
+// Check that we detect an overlap here in the case where:
+//
+// for some type X:
+// T = (X,)
+// T11 = X, U11 = X
+//
+// Seems pretty basic, but then there was issue #24241. :)
+
+trait From<U> {
+ fn foo() {}
+}
+
+impl <T> From<T> for T {
+}
+
+impl <T11, U11> From<(U11,)> for (T11,) {
+//~^ ERROR E0119
+}
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-overlap-all-t-and-tuple.stderr b/src/test/ui/coherence/coherence-overlap-all-t-and-tuple.stderr
new file mode 100644
index 000000000..6a0880334
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-all-t-and-tuple.stderr
@@ -0,0 +1,12 @@
+error[E0119]: conflicting implementations of trait `From<(_,)>` for type `(_,)`
+ --> $DIR/coherence-overlap-all-t-and-tuple.rs:16:1
+ |
+LL | impl <T> From<T> for T {
+ | ---------------------- first implementation here
+...
+LL | impl <T11, U11> From<(U11,)> for (T11,) {
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `(_,)`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-overlap-double-negative.rs b/src/test/ui/coherence/coherence-overlap-double-negative.rs
new file mode 100644
index 000000000..1ea0ddc74
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-double-negative.rs
@@ -0,0 +1,12 @@
+// check-pass
+
+#![feature(negative_impls)]
+#![feature(with_negative_coherence)]
+
+trait A {}
+trait B: A {}
+
+impl !A for u32 {}
+impl !B for u32 {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-overlap-downstream-inherent.rs b/src/test/ui/coherence/coherence-overlap-downstream-inherent.rs
new file mode 100644
index 000000000..5dea33e33
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-downstream-inherent.rs
@@ -0,0 +1,17 @@
+// Tests that we consider `T: Sugar + Fruit` to be ambiguous, even
+// though no impls are found.
+
+struct Sweet<X>(X);
+pub trait Sugar {}
+pub trait Fruit {}
+impl<T:Sugar> Sweet<T> { fn dummy(&self) { } }
+//~^ ERROR E0592
+impl<T:Fruit> Sweet<T> { fn dummy(&self) { } }
+
+trait Bar<X> {}
+struct A<T, X>(T, X);
+impl<X, T> A<T, X> where T: Bar<X> { fn f(&self) {} }
+//~^ ERROR E0592
+impl<X> A<i32, X> { fn f(&self) {} }
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-overlap-downstream-inherent.stderr b/src/test/ui/coherence/coherence-overlap-downstream-inherent.stderr
new file mode 100644
index 000000000..bbce4b530
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-downstream-inherent.stderr
@@ -0,0 +1,23 @@
+error[E0592]: duplicate definitions with name `dummy`
+ --> $DIR/coherence-overlap-downstream-inherent.rs:7:26
+ |
+LL | impl<T:Sugar> Sweet<T> { fn dummy(&self) { } }
+ | ^^^^^^^^^^^^^^^ duplicate definitions for `dummy`
+LL |
+LL | impl<T:Fruit> Sweet<T> { fn dummy(&self) { } }
+ | --------------- other definition for `dummy`
+
+error[E0592]: duplicate definitions with name `f`
+ --> $DIR/coherence-overlap-downstream-inherent.rs:13:38
+ |
+LL | impl<X, T> A<T, X> where T: Bar<X> { fn f(&self) {} }
+ | ^^^^^^^^^^^ duplicate definitions for `f`
+LL |
+LL | impl<X> A<i32, X> { fn f(&self) {} }
+ | ----------- other definition for `f`
+ |
+ = note: downstream crates may implement trait `Bar<_>` for type `i32`
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0592`.
diff --git a/src/test/ui/coherence/coherence-overlap-downstream.rs b/src/test/ui/coherence/coherence-overlap-downstream.rs
new file mode 100644
index 000000000..738ec0e3d
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-downstream.rs
@@ -0,0 +1,17 @@
+// Tests that we consider `T: Sugar + Fruit` to be ambiguous, even
+// though no impls are found.
+
+pub trait Sugar {}
+pub trait Fruit {}
+pub trait Sweet {}
+impl<T:Sugar> Sweet for T { }
+impl<T:Fruit> Sweet for T { }
+//~^ ERROR E0119
+
+pub trait Foo<X> {}
+pub trait Bar<X> {}
+impl<X, T> Foo<X> for T where T: Bar<X> {}
+impl<X> Foo<X> for i32 {}
+//~^ ERROR E0119
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-overlap-downstream.stderr b/src/test/ui/coherence/coherence-overlap-downstream.stderr
new file mode 100644
index 000000000..7f373e595
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-downstream.stderr
@@ -0,0 +1,21 @@
+error[E0119]: conflicting implementations of trait `Sweet`
+ --> $DIR/coherence-overlap-downstream.rs:8:1
+ |
+LL | impl<T:Sugar> Sweet for T { }
+ | ------------------------- first implementation here
+LL | impl<T:Fruit> Sweet for T { }
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation
+
+error[E0119]: conflicting implementations of trait `Foo<_>` for type `i32`
+ --> $DIR/coherence-overlap-downstream.rs:14:1
+ |
+LL | impl<X, T> Foo<X> for T where T: Bar<X> {}
+ | ----------------------- first implementation here
+LL | impl<X> Foo<X> for i32 {}
+ | ^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `i32`
+ |
+ = note: downstream crates may implement trait `Bar<_>` for type `i32`
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-overlap-issue-23516-inherent.rs b/src/test/ui/coherence/coherence-overlap-issue-23516-inherent.rs
new file mode 100644
index 000000000..a272e620f
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-issue-23516-inherent.rs
@@ -0,0 +1,13 @@
+// Tests that we consider `Box<U>: !Sugar` to be ambiguous, even
+// though we see no impl of `Sugar` for `Box`. Therefore, an overlap
+// error is reported for the following pair of impls (#23516).
+
+pub trait Sugar {}
+
+struct Cake<X>(X);
+
+impl<T:Sugar> Cake<T> { fn dummy(&self) { } }
+//~^ ERROR E0592
+impl<U:Sugar> Cake<Box<U>> { fn dummy(&self) { } }
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-overlap-issue-23516-inherent.stderr b/src/test/ui/coherence/coherence-overlap-issue-23516-inherent.stderr
new file mode 100644
index 000000000..3ad818cbc
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-issue-23516-inherent.stderr
@@ -0,0 +1,14 @@
+error[E0592]: duplicate definitions with name `dummy`
+ --> $DIR/coherence-overlap-issue-23516-inherent.rs:9:25
+ |
+LL | impl<T:Sugar> Cake<T> { fn dummy(&self) { } }
+ | ^^^^^^^^^^^^^^^ duplicate definitions for `dummy`
+LL |
+LL | impl<U:Sugar> Cake<Box<U>> { fn dummy(&self) { } }
+ | --------------- other definition for `dummy`
+ |
+ = note: downstream crates may implement trait `Sugar` for type `std::boxed::Box<_>`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0592`.
diff --git a/src/test/ui/coherence/coherence-overlap-issue-23516.rs b/src/test/ui/coherence/coherence-overlap-issue-23516.rs
new file mode 100644
index 000000000..63e42e8f4
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-issue-23516.rs
@@ -0,0 +1,11 @@
+// Tests that we consider `Box<U>: !Sugar` to be ambiguous, even
+// though we see no impl of `Sugar` for `Box`. Therefore, an overlap
+// error is reported for the following pair of impls (#23516).
+
+pub trait Sugar { fn dummy(&self) { } }
+pub trait Sweet { fn dummy(&self) { } }
+impl<T:Sugar> Sweet for T { }
+impl<U:Sugar> Sweet for Box<U> { }
+//~^ ERROR E0119
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-overlap-issue-23516.stderr b/src/test/ui/coherence/coherence-overlap-issue-23516.stderr
new file mode 100644
index 000000000..85eb189e1
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-issue-23516.stderr
@@ -0,0 +1,13 @@
+error[E0119]: conflicting implementations of trait `Sweet` for type `std::boxed::Box<_>`
+ --> $DIR/coherence-overlap-issue-23516.rs:8:1
+ |
+LL | impl<T:Sugar> Sweet for T { }
+ | ------------------------- first implementation here
+LL | impl<U:Sugar> Sweet for Box<U> { }
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `std::boxed::Box<_>`
+ |
+ = note: downstream crates may implement trait `Sugar` for type `std::boxed::Box<_>`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-overlap-messages.rs b/src/test/ui/coherence/coherence-overlap-messages.rs
new file mode 100644
index 000000000..1258a2371
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-messages.rs
@@ -0,0 +1,28 @@
+trait Foo { fn foo() {} }
+
+impl<T> Foo for T {}
+impl<U> Foo for U {}
+//~^ ERROR E0119
+
+
+trait Bar { fn bar() {} }
+
+impl<T> Bar for (T, u8) {}
+impl<T> Bar for (u8, T) {}
+//~^ ERROR E0119
+
+trait Baz<T> { fn baz() {} }
+
+impl<T> Baz<u8> for T {}
+impl<T> Baz<T> for u8 {}
+//~^ ERROR E0119
+
+trait Quux<U, V> { fn quux() {} }
+
+impl<T, U, V> Quux<U, V> for T {}
+impl<T, U> Quux<U, U> for T {}
+//~^ ERROR E0119
+impl<T, V> Quux<T, V> for T {}
+//~^ ERROR E0119
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-overlap-messages.stderr b/src/test/ui/coherence/coherence-overlap-messages.stderr
new file mode 100644
index 000000000..5a97296ee
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-messages.stderr
@@ -0,0 +1,44 @@
+error[E0119]: conflicting implementations of trait `Foo`
+ --> $DIR/coherence-overlap-messages.rs:4:1
+ |
+LL | impl<T> Foo for T {}
+ | ----------------- first implementation here
+LL | impl<U> Foo for U {}
+ | ^^^^^^^^^^^^^^^^^ conflicting implementation
+
+error[E0119]: conflicting implementations of trait `Bar` for type `(u8, u8)`
+ --> $DIR/coherence-overlap-messages.rs:11:1
+ |
+LL | impl<T> Bar for (T, u8) {}
+ | ----------------------- first implementation here
+LL | impl<T> Bar for (u8, T) {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `(u8, u8)`
+
+error[E0119]: conflicting implementations of trait `Baz<u8>` for type `u8`
+ --> $DIR/coherence-overlap-messages.rs:17:1
+ |
+LL | impl<T> Baz<u8> for T {}
+ | --------------------- first implementation here
+LL | impl<T> Baz<T> for u8 {}
+ | ^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `u8`
+
+error[E0119]: conflicting implementations of trait `Quux<_, _>`
+ --> $DIR/coherence-overlap-messages.rs:23:1
+ |
+LL | impl<T, U, V> Quux<U, V> for T {}
+ | ------------------------------ first implementation here
+LL | impl<T, U> Quux<U, U> for T {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation
+
+error[E0119]: conflicting implementations of trait `Quux<_, _>`
+ --> $DIR/coherence-overlap-messages.rs:25:1
+ |
+LL | impl<T, U, V> Quux<U, V> for T {}
+ | ------------------------------ first implementation here
+...
+LL | impl<T, V> Quux<T, V> for T {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation
+
+error: aborting due to 5 previous errors
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-overlap-negate-alias-strict.rs b/src/test/ui/coherence/coherence-overlap-negate-alias-strict.rs
new file mode 100644
index 000000000..48dffc921
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-negate-alias-strict.rs
@@ -0,0 +1,19 @@
+// check-pass
+
+#![feature(negative_impls)]
+#![feature(rustc_attrs)]
+#![feature(trait_alias)]
+#![feature(with_negative_coherence)]
+
+trait A {}
+trait B {}
+trait AB = A + B;
+
+impl !A for u32 {}
+
+#[rustc_strict_coherence]
+trait C {}
+impl<T: AB> C for T {}
+impl C for u32 {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-overlap-negate-not-use-feature-gate.rs b/src/test/ui/coherence/coherence-overlap-negate-not-use-feature-gate.rs
new file mode 100644
index 000000000..a067736f6
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-negate-not-use-feature-gate.rs
@@ -0,0 +1,8 @@
+use std::ops::DerefMut;
+
+trait Foo {}
+impl<T: DerefMut> Foo for T {}
+impl<U> Foo for &U {}
+//~^ ERROR: conflicting implementations of trait `Foo` for type `&_` [E0119]
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-overlap-negate-not-use-feature-gate.stderr b/src/test/ui/coherence/coherence-overlap-negate-not-use-feature-gate.stderr
new file mode 100644
index 000000000..4b55001ec
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-negate-not-use-feature-gate.stderr
@@ -0,0 +1,11 @@
+error[E0119]: conflicting implementations of trait `Foo` for type `&_`
+ --> $DIR/coherence-overlap-negate-not-use-feature-gate.rs:5:1
+ |
+LL | impl<T: DerefMut> Foo for T {}
+ | --------------------------- first implementation here
+LL | impl<U> Foo for &U {}
+ | ^^^^^^^^^^^^^^^^^^ conflicting implementation for `&_`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-overlap-negate-strict.rs b/src/test/ui/coherence/coherence-overlap-negate-strict.rs
new file mode 100644
index 000000000..1021d87ca
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-negate-strict.rs
@@ -0,0 +1,18 @@
+// check-pass
+
+#![feature(negative_impls)]
+#![feature(rustc_attrs)]
+#![feature(trait_alias)]
+#![feature(with_negative_coherence)]
+
+trait A {}
+trait B {}
+
+impl !A for u32 {}
+
+#[rustc_strict_coherence]
+trait C {}
+impl<T: A + B> C for T {}
+impl C for u32 {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-overlap-negate-use-feature-gate.rs b/src/test/ui/coherence/coherence-overlap-negate-use-feature-gate.rs
new file mode 100644
index 000000000..a0dd881d1
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-negate-use-feature-gate.rs
@@ -0,0 +1,11 @@
+// check-pass
+
+#![feature(with_negative_coherence)]
+
+use std::ops::DerefMut;
+
+trait Foo {}
+impl<T: DerefMut> Foo for T {}
+impl<U> Foo for &U {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-overlap-negative-trait.rs b/src/test/ui/coherence/coherence-overlap-negative-trait.rs
new file mode 100644
index 000000000..8059d23ff
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-negative-trait.rs
@@ -0,0 +1,16 @@
+// check-pass
+// aux-build:error_lib.rs
+//
+// Check that if we promise to not impl what would overlap it doesn't actually overlap
+
+#![feature(with_negative_coherence)]
+
+extern crate error_lib as lib;
+use lib::Error;
+
+trait From<T> {}
+
+impl From<&str> for Box<dyn Error> {}
+impl<E> From<E> for Box<dyn Error> where E: Error {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-overlap-negative-trait2.rs b/src/test/ui/coherence/coherence-overlap-negative-trait2.rs
new file mode 100644
index 000000000..cc8c463b8
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-negative-trait2.rs
@@ -0,0 +1,17 @@
+// check-pass
+// aux-build:option_future.rs
+//
+// Check that if we promise to not impl what would overlap it doesn't actually overlap
+
+#![feature(rustc_attrs)]
+#![feature(with_negative_coherence)]
+
+extern crate option_future as lib;
+use lib::Future;
+
+trait Termination {}
+
+impl<E> Termination for Option<E> where E: Sized {}
+impl<F> Termination for F where F: Future + Sized {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-overlap-super-negative.rs b/src/test/ui/coherence/coherence-overlap-super-negative.rs
new file mode 100644
index 000000000..d296a094a
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-super-negative.rs
@@ -0,0 +1,18 @@
+// check-pass
+
+#![feature(negative_impls)]
+#![feature(rustc_attrs)]
+#![feature(with_negative_coherence)]
+
+trait Trait1: Trait2 {}
+trait Trait2 {}
+
+struct MyType {}
+impl !Trait2 for MyType {}
+
+#[rustc_strict_coherence]
+trait Foo {}
+impl<T: Trait1> Foo for T {}
+impl Foo for MyType {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-overlap-trait-alias.rs b/src/test/ui/coherence/coherence-overlap-trait-alias.rs
new file mode 100644
index 000000000..9d9c76af9
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-trait-alias.rs
@@ -0,0 +1,20 @@
+#![feature(rustc_attrs)]
+#![feature(trait_alias)]
+#![feature(with_negative_coherence)]
+
+trait A {}
+trait B {}
+trait AB = A + B;
+
+impl A for u32 {}
+impl B for u32 {}
+
+#[rustc_strict_coherence]
+trait C {}
+impl<T: AB> C for T {}
+impl C for u32 {}
+//~^ ERROR
+// FIXME it's giving an ungreat error but unsure if we care given that it's using an internal rustc
+// attribute and an artificial code path for testing purposes
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-overlap-trait-alias.stderr b/src/test/ui/coherence/coherence-overlap-trait-alias.stderr
new file mode 100644
index 000000000..e324c1e79
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-trait-alias.stderr
@@ -0,0 +1,17 @@
+error[E0283]: type annotations needed: cannot satisfy `u32: C`
+ --> $DIR/coherence-overlap-trait-alias.rs:15:6
+ |
+LL | impl C for u32 {}
+ | ^
+ |
+note: multiple `impl`s satisfying `u32: C` found
+ --> $DIR/coherence-overlap-trait-alias.rs:14:1
+ |
+LL | impl<T: AB> C for T {}
+ | ^^^^^^^^^^^^^^^^^^^
+LL | impl C for u32 {}
+ | ^^^^^^^^^^^^^^
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0283`.
diff --git a/src/test/ui/coherence/coherence-overlap-upstream-inherent.rs b/src/test/ui/coherence/coherence-overlap-upstream-inherent.rs
new file mode 100644
index 000000000..082d753de
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-upstream-inherent.rs
@@ -0,0 +1,16 @@
+// Tests that we consider `i16: Remote` to be ambiguous, even
+// though the upstream crate doesn't implement it for now.
+
+// aux-build:coherence_lib.rs
+
+
+extern crate coherence_lib;
+
+use coherence_lib::Remote;
+
+struct A<X>(X);
+impl<T> A<T> where T: Remote { fn dummy(&self) { } }
+//~^ ERROR E0592
+impl A<i16> { fn dummy(&self) { } }
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-overlap-upstream-inherent.stderr b/src/test/ui/coherence/coherence-overlap-upstream-inherent.stderr
new file mode 100644
index 000000000..f355c6e85
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-upstream-inherent.stderr
@@ -0,0 +1,14 @@
+error[E0592]: duplicate definitions with name `dummy`
+ --> $DIR/coherence-overlap-upstream-inherent.rs:12:32
+ |
+LL | impl<T> A<T> where T: Remote { fn dummy(&self) { } }
+ | ^^^^^^^^^^^^^^^ duplicate definitions for `dummy`
+LL |
+LL | impl A<i16> { fn dummy(&self) { } }
+ | --------------- other definition for `dummy`
+ |
+ = note: upstream crates may add a new impl of trait `coherence_lib::Remote` for type `i16` in future versions
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0592`.
diff --git a/src/test/ui/coherence/coherence-overlap-upstream.rs b/src/test/ui/coherence/coherence-overlap-upstream.rs
new file mode 100644
index 000000000..8f1e6558b
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-upstream.rs
@@ -0,0 +1,16 @@
+// Tests that we consider `i16: Remote` to be ambiguous, even
+// though the upstream crate doesn't implement it for now.
+
+// aux-build:coherence_lib.rs
+
+
+extern crate coherence_lib;
+
+use coherence_lib::Remote;
+
+trait Foo {}
+impl<T> Foo for T where T: Remote {}
+impl Foo for i16 {}
+//~^ ERROR E0119
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-overlap-upstream.stderr b/src/test/ui/coherence/coherence-overlap-upstream.stderr
new file mode 100644
index 000000000..f6145c188
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-upstream.stderr
@@ -0,0 +1,13 @@
+error[E0119]: conflicting implementations of trait `Foo` for type `i16`
+ --> $DIR/coherence-overlap-upstream.rs:13:1
+ |
+LL | impl<T> Foo for T where T: Remote {}
+ | ----------------- first implementation here
+LL | impl Foo for i16 {}
+ | ^^^^^^^^^^^^^^^^ conflicting implementation for `i16`
+ |
+ = note: upstream crates may add a new impl of trait `coherence_lib::Remote` for type `i16` in future versions
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-overlap-with-regions.rs b/src/test/ui/coherence/coherence-overlap-with-regions.rs
new file mode 100644
index 000000000..32f01f418
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlap-with-regions.rs
@@ -0,0 +1,16 @@
+// check-pass
+
+#![feature(negative_impls)]
+#![feature(rustc_attrs)]
+#![feature(with_negative_coherence)]
+
+#[rustc_strict_coherence]
+trait Foo {}
+impl<T> !Foo for &T where T: 'static {}
+
+#[rustc_strict_coherence]
+trait Bar {}
+impl<T: Foo> Bar for T {}
+impl<T> Bar for &T where T: 'static {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-overlapping-pairs.rs b/src/test/ui/coherence/coherence-overlapping-pairs.rs
new file mode 100644
index 000000000..d5d18217b
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlapping-pairs.rs
@@ -0,0 +1,11 @@
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::Remote;
+
+struct Foo;
+
+impl<T> Remote for lib::Pair<T,Foo> { }
+//~^ ERROR E0117
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-overlapping-pairs.stderr b/src/test/ui/coherence/coherence-overlapping-pairs.stderr
new file mode 100644
index 000000000..15c92dfeb
--- /dev/null
+++ b/src/test/ui/coherence/coherence-overlapping-pairs.stderr
@@ -0,0 +1,14 @@
+error[E0117]: only traits defined in the current crate can be implemented for types defined outside of the crate
+ --> $DIR/coherence-overlapping-pairs.rs:8:1
+ |
+LL | impl<T> Remote for lib::Pair<T,Foo> { }
+ | ^^^^^^^^^^^^^^^^^^^----------------
+ | | |
+ | | `Pair` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-pair-covered-uncovered-1.rs b/src/test/ui/coherence/coherence-pair-covered-uncovered-1.rs
new file mode 100644
index 000000000..15868ca86
--- /dev/null
+++ b/src/test/ui/coherence/coherence-pair-covered-uncovered-1.rs
@@ -0,0 +1,15 @@
+// Test that the same coverage rules apply even if the local type appears in the
+// list of type parameters, not the self type.
+
+// aux-build:coherence_lib.rs
+
+
+extern crate coherence_lib as lib;
+use lib::{Remote1, Pair};
+
+pub struct Local<T>(T);
+
+impl<T, U> Remote1<Pair<T, Local<U>>> for i32 { }
+//~^ ERROR E0117
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-pair-covered-uncovered-1.stderr b/src/test/ui/coherence/coherence-pair-covered-uncovered-1.stderr
new file mode 100644
index 000000000..03d787123
--- /dev/null
+++ b/src/test/ui/coherence/coherence-pair-covered-uncovered-1.stderr
@@ -0,0 +1,15 @@
+error[E0117]: only traits defined in the current crate can be implemented for primitive types
+ --> $DIR/coherence-pair-covered-uncovered-1.rs:12:1
+ |
+LL | impl<T, U> Remote1<Pair<T, Local<U>>> for i32 { }
+ | ^^^^^^^^^^^--------------------------^^^^^---
+ | | | |
+ | | | `i32` is not defined in the current crate
+ | | `Pair` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-pair-covered-uncovered.rs b/src/test/ui/coherence/coherence-pair-covered-uncovered.rs
new file mode 100644
index 000000000..da970572f
--- /dev/null
+++ b/src/test/ui/coherence/coherence-pair-covered-uncovered.rs
@@ -0,0 +1,11 @@
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::{Remote, Pair};
+
+struct Local<T>(T);
+
+impl<T,U> Remote for Pair<T,Local<U>> { }
+//~^ ERROR E0117
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-pair-covered-uncovered.stderr b/src/test/ui/coherence/coherence-pair-covered-uncovered.stderr
new file mode 100644
index 000000000..73dfe2f57
--- /dev/null
+++ b/src/test/ui/coherence/coherence-pair-covered-uncovered.stderr
@@ -0,0 +1,14 @@
+error[E0117]: only traits defined in the current crate can be implemented for types defined outside of the crate
+ --> $DIR/coherence-pair-covered-uncovered.rs:8:1
+ |
+LL | impl<T,U> Remote for Pair<T,Local<U>> { }
+ | ^^^^^^^^^^^^^^^^^^^^^----------------
+ | | |
+ | | `Pair` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-projection-conflict-orphan.rs b/src/test/ui/coherence/coherence-projection-conflict-orphan.rs
new file mode 100644
index 000000000..637dd2506
--- /dev/null
+++ b/src/test/ui/coherence/coherence-projection-conflict-orphan.rs
@@ -0,0 +1,19 @@
+#![feature(rustc_attrs)]
+
+// Here we expect a coherence conflict because, even though `i32` does
+// not implement `Iterator`, we cannot rely on that negative reasoning
+// due to the orphan rules. Therefore, `A::Item` may yet turn out to
+// be `i32`.
+
+pub trait Foo<P> { fn foo() {} }
+
+pub trait Bar {
+ type Output: 'static;
+}
+
+impl Foo<i32> for i32 { }
+
+impl<A:Iterator> Foo<A::Item> for A { }
+//~^ ERROR E0119
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-projection-conflict-orphan.stderr b/src/test/ui/coherence/coherence-projection-conflict-orphan.stderr
new file mode 100644
index 000000000..b1ee0795b
--- /dev/null
+++ b/src/test/ui/coherence/coherence-projection-conflict-orphan.stderr
@@ -0,0 +1,14 @@
+error[E0119]: conflicting implementations of trait `Foo<i32>` for type `i32`
+ --> $DIR/coherence-projection-conflict-orphan.rs:16:1
+ |
+LL | impl Foo<i32> for i32 { }
+ | --------------------- first implementation here
+LL |
+LL | impl<A:Iterator> Foo<A::Item> for A { }
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `i32`
+ |
+ = note: upstream crates may add a new impl of trait `std::iter::Iterator` for type `i32` in future versions
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-projection-conflict-ty-param.rs b/src/test/ui/coherence/coherence-projection-conflict-ty-param.rs
new file mode 100644
index 000000000..3e4141fa8
--- /dev/null
+++ b/src/test/ui/coherence/coherence-projection-conflict-ty-param.rs
@@ -0,0 +1,13 @@
+// Coherence error results because we do not know whether `T: Foo<P>` or not
+// for the second impl.
+
+use std::marker::PhantomData;
+
+pub trait Foo<P> { fn foo() {} }
+
+impl <P, T: Foo<P>> Foo<P> for Option<T> {}
+
+impl<T, U> Foo<T> for Option<U> { }
+//~^ ERROR E0119
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-projection-conflict-ty-param.stderr b/src/test/ui/coherence/coherence-projection-conflict-ty-param.stderr
new file mode 100644
index 000000000..6492747bb
--- /dev/null
+++ b/src/test/ui/coherence/coherence-projection-conflict-ty-param.stderr
@@ -0,0 +1,12 @@
+error[E0119]: conflicting implementations of trait `Foo<_>` for type `std::option::Option<_>`
+ --> $DIR/coherence-projection-conflict-ty-param.rs:10:1
+ |
+LL | impl <P, T: Foo<P>> Foo<P> for Option<T> {}
+ | ---------------------------------------- first implementation here
+LL |
+LL | impl<T, U> Foo<T> for Option<U> { }
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `std::option::Option<_>`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-projection-conflict.rs b/src/test/ui/coherence/coherence-projection-conflict.rs
new file mode 100644
index 000000000..daab2a2f8
--- /dev/null
+++ b/src/test/ui/coherence/coherence-projection-conflict.rs
@@ -0,0 +1,18 @@
+use std::marker::PhantomData;
+
+pub trait Foo<P> { fn foo() {} }
+
+pub trait Bar {
+ type Output: 'static;
+}
+
+impl Foo<i32> for i32 { }
+
+impl<A:Bar> Foo<A::Output> for A { }
+//~^ ERROR E0119
+
+impl Bar for i32 {
+ type Output = i32;
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-projection-conflict.stderr b/src/test/ui/coherence/coherence-projection-conflict.stderr
new file mode 100644
index 000000000..7d2c584c3
--- /dev/null
+++ b/src/test/ui/coherence/coherence-projection-conflict.stderr
@@ -0,0 +1,12 @@
+error[E0119]: conflicting implementations of trait `Foo<i32>` for type `i32`
+ --> $DIR/coherence-projection-conflict.rs:11:1
+ |
+LL | impl Foo<i32> for i32 { }
+ | --------------------- first implementation here
+LL |
+LL | impl<A:Bar> Foo<A::Output> for A { }
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `i32`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-projection-ok-orphan.rs b/src/test/ui/coherence/coherence-projection-ok-orphan.rs
new file mode 100644
index 000000000..42b4b1912
--- /dev/null
+++ b/src/test/ui/coherence/coherence-projection-ok-orphan.rs
@@ -0,0 +1,17 @@
+// Here we do not get a coherence conflict because `Baz: Iterator`
+// does not hold and (due to the orphan rules), we can rely on that.
+
+// check-pass
+
+pub trait Foo<P> {}
+
+pub trait Bar {
+ type Output: 'static;
+}
+
+struct Baz;
+impl Foo<i32> for Baz { }
+
+impl<A:Iterator> Foo<A::Item> for A { }
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-projection-ok.rs b/src/test/ui/coherence/coherence-projection-ok.rs
new file mode 100644
index 000000000..44fc02a5c
--- /dev/null
+++ b/src/test/ui/coherence/coherence-projection-ok.rs
@@ -0,0 +1,17 @@
+// check-pass
+
+pub trait Foo<P> {}
+
+pub trait Bar {
+ type Output: 'static;
+}
+
+impl Foo<i32> for i32 { }
+
+impl<A:Bar> Foo<A::Output> for A { }
+
+impl Bar for i32 {
+ type Output = u32;
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-rfc447-constrained.rs b/src/test/ui/coherence/coherence-rfc447-constrained.rs
new file mode 100644
index 000000000..9d1d86883
--- /dev/null
+++ b/src/test/ui/coherence/coherence-rfc447-constrained.rs
@@ -0,0 +1,22 @@
+// run-pass
+// check that trait matching can handle impls whose types are only
+// constrained by a projection.
+
+trait IsU32 {}
+impl IsU32 for u32 {}
+
+trait Mirror { type Image: ?Sized; }
+impl<T: ?Sized> Mirror for T { type Image = T; }
+
+trait Bar {}
+impl<U: Mirror, V: Mirror<Image=L>, L: Mirror<Image=U>> Bar for V
+ where U::Image: IsU32 {}
+
+trait Foo { fn name() -> &'static str; }
+impl Foo for u64 { fn name() -> &'static str { "u64" } }
+impl<T: Bar> Foo for T { fn name() -> &'static str { "Bar" }}
+
+fn main() {
+ assert_eq!(<u64 as Foo>::name(), "u64");
+ assert_eq!(<u32 as Foo>::name(), "Bar");
+}
diff --git a/src/test/ui/coherence/coherence-subtyping.rs b/src/test/ui/coherence/coherence-subtyping.rs
new file mode 100644
index 000000000..b3ed728a8
--- /dev/null
+++ b/src/test/ui/coherence/coherence-subtyping.rs
@@ -0,0 +1,20 @@
+// Test that two distinct impls which match subtypes of one another
+// yield coherence errors (or not) depending on the variance.
+//
+// Note: This scenario is currently accepted, but as part of the
+// universe transition (#56105) may eventually become an error.
+
+// check-pass
+
+trait TheTrait {
+ fn foo(&self) {}
+}
+
+impl TheTrait for for<'a, 'b> fn(&'a u8, &'b u8) -> &'a u8 {}
+
+impl TheTrait for for<'a> fn(&'a u8, &'a u8) -> &'a u8 {
+ //~^ WARNING conflicting implementation
+ //~^^ WARNING this was previously accepted by the compiler but is being phased out
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-subtyping.stderr b/src/test/ui/coherence/coherence-subtyping.stderr
new file mode 100644
index 000000000..25d8c8756
--- /dev/null
+++ b/src/test/ui/coherence/coherence-subtyping.stderr
@@ -0,0 +1,16 @@
+warning: conflicting implementations of trait `TheTrait` for type `for<'a, 'b> fn(&'a u8, &'b u8) -> &'a u8`
+ --> $DIR/coherence-subtyping.rs:15:1
+ |
+LL | impl TheTrait for for<'a, 'b> fn(&'a u8, &'b u8) -> &'a u8 {}
+ | ---------------------------------------------------------- first implementation here
+LL |
+LL | impl TheTrait for for<'a> fn(&'a u8, &'a u8) -> &'a u8 {
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `for<'a, 'b> fn(&'a u8, &'b u8) -> &'a u8`
+ |
+ = note: `#[warn(coherence_leak_check)]` on by default
+ = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
+ = note: for more information, see issue #56105 <https://github.com/rust-lang/rust/issues/56105>
+ = note: this behavior recently changed as a result of a bug fix; see rust-lang/rust#56105 for details
+
+warning: 1 warning emitted
+
diff --git a/src/test/ui/coherence/coherence-tuple-conflict.rs b/src/test/ui/coherence/coherence-tuple-conflict.rs
new file mode 100644
index 000000000..8cc829726
--- /dev/null
+++ b/src/test/ui/coherence/coherence-tuple-conflict.rs
@@ -0,0 +1,20 @@
+use std::fmt::Debug;
+use std::default::Default;
+
+// Test that a blank impl for all T conflicts with an impl for some
+// specific T.
+
+trait MyTrait {
+ fn get(&self) -> usize;
+}
+
+impl<T> MyTrait for (T,T) {
+ fn get(&self) -> usize { 0 }
+}
+
+impl<A,B> MyTrait for (A,B) {
+//~^ ERROR E0119
+ fn get(&self) -> usize { self.dummy }
+}
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-tuple-conflict.stderr b/src/test/ui/coherence/coherence-tuple-conflict.stderr
new file mode 100644
index 000000000..09ad5e5b2
--- /dev/null
+++ b/src/test/ui/coherence/coherence-tuple-conflict.stderr
@@ -0,0 +1,12 @@
+error[E0119]: conflicting implementations of trait `MyTrait` for type `(_, _)`
+ --> $DIR/coherence-tuple-conflict.rs:15:1
+ |
+LL | impl<T> MyTrait for (T,T) {
+ | ------------------------- first implementation here
+...
+LL | impl<A,B> MyTrait for (A,B) {
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `(_, _)`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-unsafe-trait-object-impl.rs b/src/test/ui/coherence/coherence-unsafe-trait-object-impl.rs
new file mode 100644
index 000000000..9859a226e
--- /dev/null
+++ b/src/test/ui/coherence/coherence-unsafe-trait-object-impl.rs
@@ -0,0 +1,18 @@
+// Check that unsafe trait object do not implement themselves
+// automatically
+
+#![feature(object_safe_for_dispatch)]
+
+trait Trait: Sized {
+ fn call(&self);
+}
+
+fn takes_t<S: Trait>(s: S) {
+ s.call();
+}
+
+fn takes_t_obj(t: &dyn Trait) {
+ takes_t(t); //~ ERROR E0277
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-unsafe-trait-object-impl.stderr b/src/test/ui/coherence/coherence-unsafe-trait-object-impl.stderr
new file mode 100644
index 000000000..2e2dac288
--- /dev/null
+++ b/src/test/ui/coherence/coherence-unsafe-trait-object-impl.stderr
@@ -0,0 +1,17 @@
+error[E0277]: the trait bound `&dyn Trait: Trait` is not satisfied
+ --> $DIR/coherence-unsafe-trait-object-impl.rs:15:13
+ |
+LL | takes_t(t);
+ | ------- ^ the trait `Trait` is not implemented for `&dyn Trait`
+ | |
+ | required by a bound introduced by this call
+ |
+note: required by a bound in `takes_t`
+ --> $DIR/coherence-unsafe-trait-object-impl.rs:10:15
+ |
+LL | fn takes_t<S: Trait>(s: S) {
+ | ^^^^^ required by this bound in `takes_t`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0277`.
diff --git a/src/test/ui/coherence/coherence-vec-local-2.rs b/src/test/ui/coherence/coherence-vec-local-2.rs
new file mode 100644
index 000000000..47df06bac
--- /dev/null
+++ b/src/test/ui/coherence/coherence-vec-local-2.rs
@@ -0,0 +1,14 @@
+// Test that a local, generic type appearing within a
+// *non-fundamental* remote type like `Vec` is not considered local.
+
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::Remote;
+
+struct Local<T>(T);
+
+impl<T> Remote for Vec<Local<T>> { }
+//~^ ERROR E0117
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-vec-local-2.stderr b/src/test/ui/coherence/coherence-vec-local-2.stderr
new file mode 100644
index 000000000..95fdf172e
--- /dev/null
+++ b/src/test/ui/coherence/coherence-vec-local-2.stderr
@@ -0,0 +1,14 @@
+error[E0117]: only traits defined in the current crate can be implemented for types defined outside of the crate
+ --> $DIR/coherence-vec-local-2.rs:11:1
+ |
+LL | impl<T> Remote for Vec<Local<T>> { }
+ | ^^^^^^^^^^^^^^^^^^^-------------
+ | | |
+ | | `Vec` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-vec-local.rs b/src/test/ui/coherence/coherence-vec-local.rs
new file mode 100644
index 000000000..130cc39d0
--- /dev/null
+++ b/src/test/ui/coherence/coherence-vec-local.rs
@@ -0,0 +1,14 @@
+// Test that a local type (with no type parameters) appearing within a
+// *non-fundamental* remote type like `Vec` is not considered local.
+
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::Remote;
+
+struct Local;
+
+impl Remote for Vec<Local> { }
+//~^ ERROR E0117
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence-vec-local.stderr b/src/test/ui/coherence/coherence-vec-local.stderr
new file mode 100644
index 000000000..4835e771a
--- /dev/null
+++ b/src/test/ui/coherence/coherence-vec-local.stderr
@@ -0,0 +1,14 @@
+error[E0117]: only traits defined in the current crate can be implemented for types defined outside of the crate
+ --> $DIR/coherence-vec-local.rs:11:1
+ |
+LL | impl Remote for Vec<Local> { }
+ | ^^^^^^^^^^^^^^^^----------
+ | | |
+ | | `Vec` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence-wasm-bindgen.rs b/src/test/ui/coherence/coherence-wasm-bindgen.rs
new file mode 100644
index 000000000..ee09a7244
--- /dev/null
+++ b/src/test/ui/coherence/coherence-wasm-bindgen.rs
@@ -0,0 +1,37 @@
+// Capture a coherence pattern from wasm-bindgen that we discovered as part of
+// future-compatibility warning #56105. This pattern currently receives a lint
+// warning but we probably want to support it long term.
+//
+// Key distinction: we are implementing once for `A` (take ownership) and one
+// for `&A` (borrow).
+//
+// c.f. #56105
+
+#![deny(coherence_leak_check)]
+
+trait IntoWasmAbi {
+ fn some_method(&self) {}
+}
+
+trait FromWasmAbi {}
+trait RefFromWasmAbi {}
+trait ReturnWasmAbi {}
+
+impl<'a, 'b, A, R> IntoWasmAbi for &'a (dyn Fn(A) -> R + 'b)
+where
+ A: FromWasmAbi,
+ R: ReturnWasmAbi,
+{
+}
+
+// Explicitly writing the bound lifetime.
+impl<'a, 'b, A, R> IntoWasmAbi for &'a (dyn for<'x> Fn(&'x A) -> R + 'b)
+where
+ A: RefFromWasmAbi,
+ R: ReturnWasmAbi,
+{
+ //~^^^^^ ERROR conflicting implementation
+ //~| WARNING this was previously accepted
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-wasm-bindgen.stderr b/src/test/ui/coherence/coherence-wasm-bindgen.stderr
new file mode 100644
index 000000000..aa74e2315
--- /dev/null
+++ b/src/test/ui/coherence/coherence-wasm-bindgen.stderr
@@ -0,0 +1,21 @@
+error: conflicting implementations of trait `IntoWasmAbi` for type `&dyn std::ops::Fn(&_) -> _`
+ --> $DIR/coherence-wasm-bindgen.rs:28:1
+ |
+LL | impl<'a, 'b, A, R> IntoWasmAbi for &'a (dyn Fn(A) -> R + 'b)
+ | ------------------------------------------------------------ first implementation here
+...
+LL | impl<'a, 'b, A, R> IntoWasmAbi for &'a (dyn for<'x> Fn(&'x A) -> R + 'b)
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `&dyn std::ops::Fn(&_) -> _`
+ |
+note: the lint level is defined here
+ --> $DIR/coherence-wasm-bindgen.rs:10:9
+ |
+LL | #![deny(coherence_leak_check)]
+ | ^^^^^^^^^^^^^^^^^^^^
+ = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
+ = note: for more information, see issue #56105 <https://github.com/rust-lang/rust/issues/56105>
+ = note: downstream crates may implement trait `FromWasmAbi` for type `&_`
+ = note: this behavior recently changed as a result of a bug fix; see rust-lang/rust#56105 for details
+
+error: aborting due to previous error
+
diff --git a/src/test/ui/coherence/coherence-where-clause.rs b/src/test/ui/coherence/coherence-where-clause.rs
new file mode 100644
index 000000000..5c40def86
--- /dev/null
+++ b/src/test/ui/coherence/coherence-where-clause.rs
@@ -0,0 +1,38 @@
+// run-pass
+
+use std::fmt::Debug;
+use std::default::Default;
+
+trait MyTrait {
+ fn get(&self) -> Self;
+}
+
+impl<T> MyTrait for T
+ where T : Default
+{
+ fn get(&self) -> T {
+ Default::default()
+ }
+}
+
+#[derive(Clone, Copy, Debug, PartialEq)]
+struct MyType {
+ dummy: usize
+}
+
+impl MyTrait for MyType {
+ fn get(&self) -> MyType { (*self).clone() }
+}
+
+fn test_eq<M>(m: M, n: M)
+where M : MyTrait + Debug + PartialEq
+{
+ assert_eq!(m.get(), n);
+}
+
+pub fn main() {
+ test_eq(0_usize, 0_usize);
+
+ let value = MyType { dummy: 256 + 22 };
+ test_eq(value, value);
+}
diff --git a/src/test/ui/coherence/coherence-with-closure.rs b/src/test/ui/coherence/coherence-with-closure.rs
new file mode 100644
index 000000000..6e3281d85
--- /dev/null
+++ b/src/test/ui/coherence/coherence-with-closure.rs
@@ -0,0 +1,15 @@
+// Test that encountering closures during coherence does not cause issues.
+#![feature(type_alias_impl_trait)]
+type OpaqueClosure = impl Sized;
+fn defining_use() -> OpaqueClosure {
+ || ()
+}
+
+struct Wrapper<T>(T);
+trait Trait {}
+impl Trait for Wrapper<OpaqueClosure> {}
+//~^ ERROR cannot implement trait on type alias impl trait
+impl<T: Sync> Trait for Wrapper<T> {}
+//~^ ERROR conflicting implementations of trait `Trait` for type `Wrapper<OpaqueClosure>`
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-with-closure.stderr b/src/test/ui/coherence/coherence-with-closure.stderr
new file mode 100644
index 000000000..d2ca63fa1
--- /dev/null
+++ b/src/test/ui/coherence/coherence-with-closure.stderr
@@ -0,0 +1,24 @@
+error[E0119]: conflicting implementations of trait `Trait` for type `Wrapper<OpaqueClosure>`
+ --> $DIR/coherence-with-closure.rs:12:1
+ |
+LL | impl Trait for Wrapper<OpaqueClosure> {}
+ | ------------------------------------- first implementation here
+LL |
+LL | impl<T: Sync> Trait for Wrapper<T> {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `Wrapper<OpaqueClosure>`
+
+error: cannot implement trait on type alias impl trait
+ --> $DIR/coherence-with-closure.rs:10:24
+ |
+LL | impl Trait for Wrapper<OpaqueClosure> {}
+ | ^^^^^^^^^^^^^
+ |
+note: type alias impl trait defined here
+ --> $DIR/coherence-with-closure.rs:3:22
+ |
+LL | type OpaqueClosure = impl Sized;
+ | ^^^^^^^^^^
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence-with-generator.rs b/src/test/ui/coherence/coherence-with-generator.rs
new file mode 100644
index 000000000..d34c391db
--- /dev/null
+++ b/src/test/ui/coherence/coherence-with-generator.rs
@@ -0,0 +1,19 @@
+// Test that encountering closures during coherence does not cause issues.
+#![feature(type_alias_impl_trait, generators)]
+type OpaqueGenerator = impl Sized;
+fn defining_use() -> OpaqueGenerator {
+ || {
+ for i in 0..10 {
+ yield i;
+ }
+ }
+}
+
+struct Wrapper<T>(T);
+trait Trait {}
+impl Trait for Wrapper<OpaqueGenerator> {}
+//~^ ERROR cannot implement trait on type alias impl trait
+impl<T: Sync> Trait for Wrapper<T> {}
+//~^ ERROR conflicting implementations of trait `Trait` for type `Wrapper<OpaqueGenerator>`
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence-with-generator.stderr b/src/test/ui/coherence/coherence-with-generator.stderr
new file mode 100644
index 000000000..804bc1c3a
--- /dev/null
+++ b/src/test/ui/coherence/coherence-with-generator.stderr
@@ -0,0 +1,24 @@
+error[E0119]: conflicting implementations of trait `Trait` for type `Wrapper<OpaqueGenerator>`
+ --> $DIR/coherence-with-generator.rs:16:1
+ |
+LL | impl Trait for Wrapper<OpaqueGenerator> {}
+ | --------------------------------------- first implementation here
+LL |
+LL | impl<T: Sync> Trait for Wrapper<T> {}
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `Wrapper<OpaqueGenerator>`
+
+error: cannot implement trait on type alias impl trait
+ --> $DIR/coherence-with-generator.rs:14:24
+ |
+LL | impl Trait for Wrapper<OpaqueGenerator> {}
+ | ^^^^^^^^^^^^^^^
+ |
+note: type alias impl trait defined here
+ --> $DIR/coherence-with-generator.rs:3:24
+ |
+LL | type OpaqueGenerator = impl Sized;
+ | ^^^^^^^^^^
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence_copy_like.rs b/src/test/ui/coherence/coherence_copy_like.rs
new file mode 100644
index 000000000..92af341cc
--- /dev/null
+++ b/src/test/ui/coherence/coherence_copy_like.rs
@@ -0,0 +1,19 @@
+// run-pass
+#![allow(dead_code)]
+// Test that we are able to introduce a negative constraint that
+// `MyType: !MyTrait` along with other "fundamental" wrappers.
+
+// aux-build:coherence_copy_like_lib.rs
+
+extern crate coherence_copy_like_lib as lib;
+
+struct MyType { x: i32 }
+
+trait MyTrait { }
+impl<T: lib::MyCopy> MyTrait for T { }
+impl MyTrait for MyType { }
+impl<'a> MyTrait for &'a MyType { }
+impl MyTrait for Box<MyType> { }
+impl<'a> MyTrait for &'a Box<MyType> { }
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence_copy_like_err_fundamental_struct.rs b/src/test/ui/coherence/coherence_copy_like_err_fundamental_struct.rs
new file mode 100644
index 000000000..edee6cd7b
--- /dev/null
+++ b/src/test/ui/coherence/coherence_copy_like_err_fundamental_struct.rs
@@ -0,0 +1,24 @@
+// Test that we are able to introduce a negative constraint that
+// `MyType: !MyTrait` along with other "fundamental" wrappers.
+
+// aux-build:coherence_copy_like_lib.rs
+// build-pass (FIXME(62277): could be check-pass?)
+// skip-codgen
+#![allow(dead_code)]
+
+extern crate coherence_copy_like_lib as lib;
+
+struct MyType { x: i32 }
+
+trait MyTrait { fn foo() {} }
+impl<T: lib::MyCopy> MyTrait for T { }
+
+// `MyFundamentalStruct` is declared fundamental, so we can test that
+//
+// MyFundamentalStruct<MyTrait>: !MyTrait
+//
+// Huzzah.
+impl MyTrait for lib::MyFundamentalStruct<MyType> { }
+
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence_copy_like_err_fundamental_struct_ref.rs b/src/test/ui/coherence/coherence_copy_like_err_fundamental_struct_ref.rs
new file mode 100644
index 000000000..599c804d2
--- /dev/null
+++ b/src/test/ui/coherence/coherence_copy_like_err_fundamental_struct_ref.rs
@@ -0,0 +1,21 @@
+// Test that we are able to introduce a negative constraint that
+// `MyType: !MyTrait` along with other "fundamental" wrappers.
+
+// check-pass
+// aux-build:coherence_copy_like_lib.rs
+
+extern crate coherence_copy_like_lib as lib;
+
+struct MyType { x: i32 }
+
+trait MyTrait { fn foo() {} }
+impl<T: lib::MyCopy> MyTrait for T { }
+
+// `MyFundamentalStruct` is declared fundamental, so we can test that
+//
+// MyFundamentalStruct<&MyTrait>: !MyTrait
+//
+// Huzzah.
+impl<'a> MyTrait for lib::MyFundamentalStruct<&'a MyType> { }
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence_copy_like_err_fundamental_struct_tuple.rs b/src/test/ui/coherence/coherence_copy_like_err_fundamental_struct_tuple.rs
new file mode 100644
index 000000000..7d851b528
--- /dev/null
+++ b/src/test/ui/coherence/coherence_copy_like_err_fundamental_struct_tuple.rs
@@ -0,0 +1,20 @@
+// Test that we are able to introduce a negative constraint that
+// `MyType: !MyTrait` along with other "fundamental" wrappers.
+
+// aux-build:coherence_copy_like_lib.rs
+
+
+extern crate coherence_copy_like_lib as lib;
+
+struct MyType { x: i32 }
+
+trait MyTrait { fn foo() {} }
+
+impl<T: lib::MyCopy> MyTrait for T { }
+
+// Tuples are not fundamental.
+impl MyTrait for lib::MyFundamentalStruct<(MyType,)> { }
+//~^ ERROR E0119
+
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence_copy_like_err_fundamental_struct_tuple.stderr b/src/test/ui/coherence/coherence_copy_like_err_fundamental_struct_tuple.stderr
new file mode 100644
index 000000000..db7306501
--- /dev/null
+++ b/src/test/ui/coherence/coherence_copy_like_err_fundamental_struct_tuple.stderr
@@ -0,0 +1,14 @@
+error[E0119]: conflicting implementations of trait `MyTrait` for type `lib::MyFundamentalStruct<(MyType,)>`
+ --> $DIR/coherence_copy_like_err_fundamental_struct_tuple.rs:16:1
+ |
+LL | impl<T: lib::MyCopy> MyTrait for T { }
+ | ---------------------------------- first implementation here
+...
+LL | impl MyTrait for lib::MyFundamentalStruct<(MyType,)> { }
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `lib::MyFundamentalStruct<(MyType,)>`
+ |
+ = note: upstream crates may add a new impl of trait `lib::MyCopy` for type `lib::MyFundamentalStruct<(MyType,)>` in future versions
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence_copy_like_err_struct.rs b/src/test/ui/coherence/coherence_copy_like_err_struct.rs
new file mode 100644
index 000000000..fe39370c9
--- /dev/null
+++ b/src/test/ui/coherence/coherence_copy_like_err_struct.rs
@@ -0,0 +1,22 @@
+// aux-build:coherence_copy_like_lib.rs
+
+// Test that we are able to introduce a negative constraint that
+// `MyType: !MyTrait` along with other "fundamental" wrappers.
+
+extern crate coherence_copy_like_lib as lib;
+
+struct MyType { x: i32 }
+
+trait MyTrait { fn foo() {} }
+impl<T: lib::MyCopy> MyTrait for T { }
+
+// `MyStruct` is not declared fundamental, therefore this would
+// require that
+//
+// MyStruct<MyType>: !MyTrait
+//
+// which we cannot approve.
+impl MyTrait for lib::MyStruct<MyType> { }
+//~^ ERROR E0119
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence_copy_like_err_struct.stderr b/src/test/ui/coherence/coherence_copy_like_err_struct.stderr
new file mode 100644
index 000000000..3bc3dffda
--- /dev/null
+++ b/src/test/ui/coherence/coherence_copy_like_err_struct.stderr
@@ -0,0 +1,14 @@
+error[E0119]: conflicting implementations of trait `MyTrait` for type `lib::MyStruct<MyType>`
+ --> $DIR/coherence_copy_like_err_struct.rs:19:1
+ |
+LL | impl<T: lib::MyCopy> MyTrait for T { }
+ | ---------------------------------- first implementation here
+...
+LL | impl MyTrait for lib::MyStruct<MyType> { }
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `lib::MyStruct<MyType>`
+ |
+ = note: upstream crates may add a new impl of trait `lib::MyCopy` for type `lib::MyStruct<MyType>` in future versions
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence_copy_like_err_tuple.rs b/src/test/ui/coherence/coherence_copy_like_err_tuple.rs
new file mode 100644
index 000000000..f63e205c9
--- /dev/null
+++ b/src/test/ui/coherence/coherence_copy_like_err_tuple.rs
@@ -0,0 +1,21 @@
+// Test that we are able to introduce a negative constraint that
+// `MyType: !MyTrait` along with other "fundamental" wrappers.
+
+// aux-build:coherence_copy_like_lib.rs
+
+extern crate coherence_copy_like_lib as lib;
+
+struct MyType { x: i32 }
+
+trait MyTrait { fn foo() {} }
+impl<T: lib::MyCopy> MyTrait for T { }
+
+// Tuples are not fundamental, therefore this would require that
+//
+// (MyType,): !MyTrait
+//
+// which we cannot approve.
+impl MyTrait for (MyType,) { }
+//~^ ERROR E0119
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence_copy_like_err_tuple.stderr b/src/test/ui/coherence/coherence_copy_like_err_tuple.stderr
new file mode 100644
index 000000000..090497ec1
--- /dev/null
+++ b/src/test/ui/coherence/coherence_copy_like_err_tuple.stderr
@@ -0,0 +1,14 @@
+error[E0119]: conflicting implementations of trait `MyTrait` for type `(MyType,)`
+ --> $DIR/coherence_copy_like_err_tuple.rs:18:1
+ |
+LL | impl<T: lib::MyCopy> MyTrait for T { }
+ | ---------------------------------- first implementation here
+...
+LL | impl MyTrait for (MyType,) { }
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `(MyType,)`
+ |
+ = note: upstream crates may add a new impl of trait `lib::MyCopy` for type `(MyType,)` in future versions
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/coherence_inherent.rs b/src/test/ui/coherence/coherence_inherent.rs
new file mode 100644
index 000000000..f3ebf0003
--- /dev/null
+++ b/src/test/ui/coherence/coherence_inherent.rs
@@ -0,0 +1,36 @@
+// Tests that methods that implement a trait cannot be invoked
+// unless the trait is imported.
+
+mod Lib {
+ pub trait TheTrait {
+ fn the_fn(&self);
+ }
+
+ pub struct TheStruct;
+
+ impl TheTrait for TheStruct {
+ fn the_fn(&self) {}
+ }
+}
+
+mod Import {
+ // Trait is in scope here:
+ use Lib::TheStruct;
+ use Lib::TheTrait;
+
+ fn call_the_fn(s: &TheStruct) {
+ s.the_fn();
+ }
+}
+
+mod NoImport {
+ // Trait is not in scope here:
+ use Lib::TheStruct;
+
+ fn call_the_fn(s: &TheStruct) {
+ s.the_fn();
+ //~^ ERROR E0599
+ }
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence_inherent.stderr b/src/test/ui/coherence/coherence_inherent.stderr
new file mode 100644
index 000000000..46b128c08
--- /dev/null
+++ b/src/test/ui/coherence/coherence_inherent.stderr
@@ -0,0 +1,15 @@
+error[E0599]: no method named `the_fn` found for reference `&TheStruct` in the current scope
+ --> $DIR/coherence_inherent.rs:31:11
+ |
+LL | s.the_fn();
+ | ^^^^^^ method not found in `&TheStruct`
+ |
+ = help: items from traits can only be used if the trait is in scope
+help: the following trait is implemented but not in scope; perhaps add a `use` for it:
+ |
+LL | use Lib::TheTrait;
+ |
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0599`.
diff --git a/src/test/ui/coherence/coherence_inherent_cc.rs b/src/test/ui/coherence/coherence_inherent_cc.rs
new file mode 100644
index 000000000..759ada248
--- /dev/null
+++ b/src/test/ui/coherence/coherence_inherent_cc.rs
@@ -0,0 +1,28 @@
+// aux-build:coherence_inherent_cc_lib.rs
+
+// Tests that methods that implement a trait cannot be invoked
+// unless the trait is imported.
+
+extern crate coherence_inherent_cc_lib;
+
+mod Import {
+ // Trait is in scope here:
+ use coherence_inherent_cc_lib::TheStruct;
+ use coherence_inherent_cc_lib::TheTrait;
+
+ fn call_the_fn(s: &TheStruct) {
+ s.the_fn();
+ }
+}
+
+mod NoImport {
+ // Trait is not in scope here:
+ use coherence_inherent_cc_lib::TheStruct;
+
+ fn call_the_fn(s: &TheStruct) {
+ s.the_fn();
+ //~^ ERROR E0599
+ }
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence_inherent_cc.stderr b/src/test/ui/coherence/coherence_inherent_cc.stderr
new file mode 100644
index 000000000..af0ef3b69
--- /dev/null
+++ b/src/test/ui/coherence/coherence_inherent_cc.stderr
@@ -0,0 +1,15 @@
+error[E0599]: no method named `the_fn` found for reference `&TheStruct` in the current scope
+ --> $DIR/coherence_inherent_cc.rs:23:11
+ |
+LL | s.the_fn();
+ | ^^^^^^ method not found in `&TheStruct`
+ |
+ = help: items from traits can only be used if the trait is in scope
+help: the following trait is implemented but not in scope; perhaps add a `use` for it:
+ |
+LL | use coherence_inherent_cc_lib::TheTrait;
+ |
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0599`.
diff --git a/src/test/ui/coherence/coherence_local.rs b/src/test/ui/coherence/coherence_local.rs
new file mode 100644
index 000000000..ea724ada7
--- /dev/null
+++ b/src/test/ui/coherence/coherence_local.rs
@@ -0,0 +1,20 @@
+// Test that we are able to introduce a negative constraint that
+// `MyType: !MyTrait` along with other "fundamental" wrappers.
+
+// check-pass
+// aux-build:coherence_copy_like_lib.rs
+
+extern crate coherence_copy_like_lib as lib;
+
+struct MyType { x: i32 }
+
+// These are all legal because they are all fundamental types:
+
+impl lib::MyCopy for MyType { }
+impl<'a> lib::MyCopy for &'a MyType { }
+impl<'a> lib::MyCopy for &'a Box<MyType> { }
+impl lib::MyCopy for Box<MyType> { }
+impl lib::MyCopy for lib::MyFundamentalStruct<MyType> { }
+impl lib::MyCopy for lib::MyFundamentalStruct<Box<MyType>> { }
+
+fn main() {}
diff --git a/src/test/ui/coherence/coherence_local_err_struct.rs b/src/test/ui/coherence/coherence_local_err_struct.rs
new file mode 100644
index 000000000..a24038eb2
--- /dev/null
+++ b/src/test/ui/coherence/coherence_local_err_struct.rs
@@ -0,0 +1,18 @@
+// Test that we are able to introduce a negative constraint that
+// `MyType: !MyTrait` along with other "fundamental" wrappers.
+
+// aux-build:coherence_copy_like_lib.rs
+#![allow(dead_code)]
+
+extern crate coherence_copy_like_lib as lib;
+
+struct MyType { x: i32 }
+
+// These are all legal because they are all fundamental types:
+
+// MyStruct is not fundamental.
+impl lib::MyCopy for lib::MyStruct<MyType> { }
+//~^ ERROR E0117
+
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence_local_err_struct.stderr b/src/test/ui/coherence/coherence_local_err_struct.stderr
new file mode 100644
index 000000000..afc6fc45d
--- /dev/null
+++ b/src/test/ui/coherence/coherence_local_err_struct.stderr
@@ -0,0 +1,14 @@
+error[E0117]: only traits defined in the current crate can be implemented for types defined outside of the crate
+ --> $DIR/coherence_local_err_struct.rs:14:1
+ |
+LL | impl lib::MyCopy for lib::MyStruct<MyType> { }
+ | ^^^^^^^^^^^^^^^^^^^^^---------------------
+ | | |
+ | | `MyStruct` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence_local_err_tuple.rs b/src/test/ui/coherence/coherence_local_err_tuple.rs
new file mode 100644
index 000000000..f4033862a
--- /dev/null
+++ b/src/test/ui/coherence/coherence_local_err_tuple.rs
@@ -0,0 +1,18 @@
+// Test that we are able to introduce a negative constraint that
+// `MyType: !MyTrait` along with other "fundamental" wrappers.
+
+// aux-build:coherence_copy_like_lib.rs
+#![allow(dead_code)]
+
+extern crate coherence_copy_like_lib as lib;
+
+struct MyType { x: i32 }
+
+// These are all legal because they are all fundamental types:
+
+// Tuples are not fundamental, so this is not a local impl.
+impl lib::MyCopy for (MyType,) { }
+//~^ ERROR E0117
+
+
+fn main() { }
diff --git a/src/test/ui/coherence/coherence_local_err_tuple.stderr b/src/test/ui/coherence/coherence_local_err_tuple.stderr
new file mode 100644
index 000000000..a4953859f
--- /dev/null
+++ b/src/test/ui/coherence/coherence_local_err_tuple.stderr
@@ -0,0 +1,14 @@
+error[E0117]: only traits defined in the current crate can be implemented for arbitrary types
+ --> $DIR/coherence_local_err_tuple.rs:14:1
+ |
+LL | impl lib::MyCopy for (MyType,) { }
+ | ^^^^^^^^^^^^^^^^^^^^^---------
+ | | |
+ | | this is not defined in the current crate because tuples are always foreign
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/coherence_local_ref.rs b/src/test/ui/coherence/coherence_local_ref.rs
new file mode 100644
index 000000000..2e28839c8
--- /dev/null
+++ b/src/test/ui/coherence/coherence_local_ref.rs
@@ -0,0 +1,14 @@
+// Test that we are able to introduce a negative constraint that
+// `MyType: !MyTrait` along with other "fundamental" wrappers.
+
+// check-pass
+// aux-build:coherence_copy_like_lib.rs
+
+extern crate coherence_copy_like_lib as lib;
+
+struct MyType { x: i32 }
+
+// naturally, legal
+impl lib::MyCopy for MyType { }
+
+fn main() { }
diff --git a/src/test/ui/coherence/conflicting-impl-with-err.rs b/src/test/ui/coherence/conflicting-impl-with-err.rs
new file mode 100644
index 000000000..3e0234b87
--- /dev/null
+++ b/src/test/ui/coherence/conflicting-impl-with-err.rs
@@ -0,0 +1,16 @@
+struct ErrorKind;
+struct Error(ErrorKind);
+
+impl From<nope::Thing> for Error { //~ ERROR failed to resolve
+ fn from(_: nope::Thing) -> Self { //~ ERROR failed to resolve
+ unimplemented!()
+ }
+}
+
+impl From<ErrorKind> for Error {
+ fn from(_: ErrorKind) -> Self {
+ unimplemented!()
+ }
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/conflicting-impl-with-err.stderr b/src/test/ui/coherence/conflicting-impl-with-err.stderr
new file mode 100644
index 000000000..3009b452d
--- /dev/null
+++ b/src/test/ui/coherence/conflicting-impl-with-err.stderr
@@ -0,0 +1,15 @@
+error[E0433]: failed to resolve: use of undeclared crate or module `nope`
+ --> $DIR/conflicting-impl-with-err.rs:4:11
+ |
+LL | impl From<nope::Thing> for Error {
+ | ^^^^ use of undeclared crate or module `nope`
+
+error[E0433]: failed to resolve: use of undeclared crate or module `nope`
+ --> $DIR/conflicting-impl-with-err.rs:5:16
+ |
+LL | fn from(_: nope::Thing) -> Self {
+ | ^^^^ use of undeclared crate or module `nope`
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0433`.
diff --git a/src/test/ui/coherence/deep-bad-copy-reason.rs b/src/test/ui/coherence/deep-bad-copy-reason.rs
new file mode 100644
index 000000000..80bbe387a
--- /dev/null
+++ b/src/test/ui/coherence/deep-bad-copy-reason.rs
@@ -0,0 +1,40 @@
+#![feature(extern_types)]
+
+extern "Rust" {
+ type OpaqueListContents;
+}
+
+pub struct ListS<T> {
+ len: usize,
+ data: [T; 0],
+ opaque: OpaqueListContents,
+}
+
+pub struct Interned<'a, T>(&'a T);
+
+impl<'a, T> Clone for Interned<'a, T> {
+ fn clone(&self) -> Self {
+ *self
+ }
+}
+
+impl<'a, T> Copy for Interned<'a, T> {}
+
+pub struct List<'tcx, T>(Interned<'tcx, ListS<T>>);
+//~^ NOTE this field does not implement `Copy`
+//~| NOTE the `Copy` impl for `Interned<'tcx, ListS<T>>` requires that `OpaqueListContents: Sized`
+
+impl<'tcx, T> Clone for List<'tcx, T> {
+ fn clone(&self) -> Self {
+ *self
+ }
+}
+
+impl<'tcx, T> Copy for List<'tcx, T> {}
+//~^ ERROR the trait `Copy` may not be implemented for this type
+
+fn assert_is_copy<T: Copy>() {}
+
+fn main() {
+ assert_is_copy::<List<'static, ()>>();
+}
diff --git a/src/test/ui/coherence/deep-bad-copy-reason.stderr b/src/test/ui/coherence/deep-bad-copy-reason.stderr
new file mode 100644
index 000000000..295538cee
--- /dev/null
+++ b/src/test/ui/coherence/deep-bad-copy-reason.stderr
@@ -0,0 +1,18 @@
+error[E0204]: the trait `Copy` may not be implemented for this type
+ --> $DIR/deep-bad-copy-reason.rs:33:15
+ |
+LL | pub struct List<'tcx, T>(Interned<'tcx, ListS<T>>);
+ | ------------------------ this field does not implement `Copy`
+...
+LL | impl<'tcx, T> Copy for List<'tcx, T> {}
+ | ^^^^
+ |
+note: the `Copy` impl for `Interned<'tcx, ListS<T>>` requires that `OpaqueListContents: Sized`
+ --> $DIR/deep-bad-copy-reason.rs:23:26
+ |
+LL | pub struct List<'tcx, T>(Interned<'tcx, ListS<T>>);
+ | ^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0204`.
diff --git a/src/test/ui/coherence/impl-foreign-for-foreign.rs b/src/test/ui/coherence/impl-foreign-for-foreign.rs
new file mode 100644
index 000000000..4c0d46045
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign-for-foreign.rs
@@ -0,0 +1,15 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl Remote for i32 {
+ //~^ ERROR only traits defined in the current crate
+ // | can be implemented for arbitrary types [E0117]
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl-foreign-for-foreign.stderr b/src/test/ui/coherence/impl-foreign-for-foreign.stderr
new file mode 100644
index 000000000..93f7a6fdc
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign-for-foreign.stderr
@@ -0,0 +1,14 @@
+error[E0117]: only traits defined in the current crate can be implemented for primitive types
+ --> $DIR/impl-foreign-for-foreign.rs:10:1
+ |
+LL | impl Remote for i32 {
+ | ^^^^^^^^^^^^^^^^---
+ | | |
+ | | `i32` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/impl-foreign-for-foreign[foreign].rs b/src/test/ui/coherence/impl-foreign-for-foreign[foreign].rs
new file mode 100644
index 000000000..e79f66c0e
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign-for-foreign[foreign].rs
@@ -0,0 +1,23 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl Remote1<Rc<i32>> for i32 {
+ //~^ ERROR only traits defined in the current crate
+ // | can be implemented for arbitrary types [E0117]
+}
+impl Remote1<Rc<Local>> for f64 {
+ //~^ ERROR only traits defined in the current crate
+ // | can be implemented for arbitrary types [E0117]
+}
+impl<T> Remote1<Rc<T>> for f32 {
+ //~^ ERROR only traits defined in the current crate
+ // | can be implemented for arbitrary types [E0117]
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl-foreign-for-foreign[foreign].stderr b/src/test/ui/coherence/impl-foreign-for-foreign[foreign].stderr
new file mode 100644
index 000000000..e24537bce
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign-for-foreign[foreign].stderr
@@ -0,0 +1,39 @@
+error[E0117]: only traits defined in the current crate can be implemented for primitive types
+ --> $DIR/impl-foreign-for-foreign[foreign].rs:10:1
+ |
+LL | impl Remote1<Rc<i32>> for i32 {
+ | ^^^^^----------------^^^^^---
+ | | | |
+ | | | `i32` is not defined in the current crate
+ | | `Rc` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0117]: only traits defined in the current crate can be implemented for primitive types
+ --> $DIR/impl-foreign-for-foreign[foreign].rs:14:1
+ |
+LL | impl Remote1<Rc<Local>> for f64 {
+ | ^^^^^------------------^^^^^---
+ | | | |
+ | | | `f64` is not defined in the current crate
+ | | `Rc` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0117]: only traits defined in the current crate can be implemented for primitive types
+ --> $DIR/impl-foreign-for-foreign[foreign].rs:18:1
+ |
+LL | impl<T> Remote1<Rc<T>> for f32 {
+ | ^^^^^^^^--------------^^^^^---
+ | | | |
+ | | | `f32` is not defined in the current crate
+ | | `Rc` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to 3 previous errors
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/impl-foreign-for-foreign[local].rs b/src/test/ui/coherence/impl-foreign-for-foreign[local].rs
new file mode 100644
index 000000000..0b1413edf
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign-for-foreign[local].rs
@@ -0,0 +1,14 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local<T>(Rc<T>);
+
+impl Remote1<Local<i32>> for i32 {}
+impl<T> Remote1<Local<T>> for f32 {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl-foreign-for-fundamental[foreign].rs b/src/test/ui/coherence/impl-foreign-for-fundamental[foreign].rs
new file mode 100644
index 000000000..10bdf2db8
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign-for-fundamental[foreign].rs
@@ -0,0 +1,19 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl Remote for Box<i32> {
+ //~^ ERROR only traits defined in the current crate
+ // | can be implemented for arbitrary types [E0117]
+}
+impl<T> Remote for Box<Rc<T>> {
+ //~^ ERROR only traits defined in the current crate
+ // | can be implemented for arbitrary types [E0117]
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl-foreign-for-fundamental[foreign].stderr b/src/test/ui/coherence/impl-foreign-for-fundamental[foreign].stderr
new file mode 100644
index 000000000..55ea4409e
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign-for-fundamental[foreign].stderr
@@ -0,0 +1,27 @@
+error[E0117]: only traits defined in the current crate can be implemented for types defined outside of the crate
+ --> $DIR/impl-foreign-for-fundamental[foreign].rs:10:1
+ |
+LL | impl Remote for Box<i32> {
+ | ^^^^^------^^^^^--------
+ | | | |
+ | | | `i32` is not defined in the current crate
+ | | `std::alloc::Global` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0117]: only traits defined in the current crate can be implemented for types defined outside of the crate
+ --> $DIR/impl-foreign-for-fundamental[foreign].rs:14:1
+ |
+LL | impl<T> Remote for Box<Rc<T>> {
+ | ^^^^^^^^------^^^^^----------
+ | | | |
+ | | | `Rc` is not defined in the current crate
+ | | `std::alloc::Global` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/impl-foreign-for-fundamental[local].rs b/src/test/ui/coherence/impl-foreign-for-fundamental[local].rs
new file mode 100644
index 000000000..c3fc0e6b8
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign-for-fundamental[local].rs
@@ -0,0 +1,15 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+struct Local1<T>(Rc<T>);
+
+impl Remote for Box<Local> {}
+impl<T> Remote for Box<Local1<T>> {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl-foreign-for-local.rs b/src/test/ui/coherence/impl-foreign-for-local.rs
new file mode 100644
index 000000000..04405bc46
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign-for-local.rs
@@ -0,0 +1,13 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl Remote for Local {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl-foreign-for-locally-defined-fundamental.rs b/src/test/ui/coherence/impl-foreign-for-locally-defined-fundamental.rs
new file mode 100644
index 000000000..bc1e18b65
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign-for-locally-defined-fundamental.rs
@@ -0,0 +1,15 @@
+#![feature(fundamental)]
+
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+
+#[fundamental]
+struct Local<T>(T);
+
+impl Remote for Local<()> {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl-foreign-for-locally-defined-fundamental[foreign].rs b/src/test/ui/coherence/impl-foreign-for-locally-defined-fundamental[foreign].rs
new file mode 100644
index 000000000..1e11789ef
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign-for-locally-defined-fundamental[foreign].rs
@@ -0,0 +1,15 @@
+#![feature(fundamental)]
+
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+
+#[fundamental]
+struct MyBox<T>(T);
+
+impl<T> Remote for MyBox<T> {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl-foreign[foreign]-for-foreign.rs b/src/test/ui/coherence/impl-foreign[foreign]-for-foreign.rs
new file mode 100644
index 000000000..99a399ddc
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign[foreign]-for-foreign.rs
@@ -0,0 +1,15 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl Remote1<u32> for f64 {
+ //~^ ERROR only traits defined in the current crate
+ // | can be implemented for arbitrary types [E0117]
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl-foreign[foreign]-for-foreign.stderr b/src/test/ui/coherence/impl-foreign[foreign]-for-foreign.stderr
new file mode 100644
index 000000000..65b3aa394
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign[foreign]-for-foreign.stderr
@@ -0,0 +1,15 @@
+error[E0117]: only traits defined in the current crate can be implemented for primitive types
+ --> $DIR/impl-foreign[foreign]-for-foreign.rs:10:1
+ |
+LL | impl Remote1<u32> for f64 {
+ | ^^^^^------------^^^^^---
+ | | | |
+ | | | `f64` is not defined in the current crate
+ | | `u32` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/impl-foreign[foreign]-for-local.rs b/src/test/ui/coherence/impl-foreign[foreign]-for-local.rs
new file mode 100644
index 000000000..bc6595bb3
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign[foreign]-for-local.rs
@@ -0,0 +1,14 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl Remote1<u32> for Local {
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl-foreign[fundemental[foreign]]-for-foreign.rs b/src/test/ui/coherence/impl-foreign[fundemental[foreign]]-for-foreign.rs
new file mode 100644
index 000000000..0476cdaff
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign[fundemental[foreign]]-for-foreign.rs
@@ -0,0 +1,24 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+struct Local1<T>(Rc<T>);
+
+impl Remote1<Box<String>> for i32 {
+ //~^ ERROR only traits defined in the current crate
+ // | can be implemented for arbitrary types [E0117]
+}
+impl Remote1<Box<Rc<i32>>> for f64 {
+ //~^ ERROR only traits defined in the current crate
+ // | can be implemented for arbitrary types [E0117]
+}
+impl<T> Remote1<Box<Rc<T>>> for f32 {
+ //~^ ERROR only traits defined in the current crate
+ // | can be implemented for arbitrary types [E0117]
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl-foreign[fundemental[foreign]]-for-foreign.stderr b/src/test/ui/coherence/impl-foreign[fundemental[foreign]]-for-foreign.stderr
new file mode 100644
index 000000000..8e77c13e1
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign[fundemental[foreign]]-for-foreign.stderr
@@ -0,0 +1,42 @@
+error[E0117]: only traits defined in the current crate can be implemented for primitive types
+ --> $DIR/impl-foreign[fundemental[foreign]]-for-foreign.rs:11:1
+ |
+LL | impl Remote1<Box<String>> for i32 {
+ | ^^^^^--------------------^^^^^---
+ | | | |
+ | | | `i32` is not defined in the current crate
+ | | `String` is not defined in the current crate
+ | | `std::alloc::Global` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0117]: only traits defined in the current crate can be implemented for primitive types
+ --> $DIR/impl-foreign[fundemental[foreign]]-for-foreign.rs:15:1
+ |
+LL | impl Remote1<Box<Rc<i32>>> for f64 {
+ | ^^^^^---------------------^^^^^---
+ | | | |
+ | | | `f64` is not defined in the current crate
+ | | `Rc` is not defined in the current crate
+ | | `std::alloc::Global` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0117]: only traits defined in the current crate can be implemented for primitive types
+ --> $DIR/impl-foreign[fundemental[foreign]]-for-foreign.rs:19:1
+ |
+LL | impl<T> Remote1<Box<Rc<T>>> for f32 {
+ | ^^^^^^^^-------------------^^^^^---
+ | | | |
+ | | | `f32` is not defined in the current crate
+ | | `Rc` is not defined in the current crate
+ | | `std::alloc::Global` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to 3 previous errors
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/impl-foreign[fundemental[local]]-for-foreign.rs b/src/test/ui/coherence/impl-foreign[fundemental[local]]-for-foreign.rs
new file mode 100644
index 000000000..7b83b0485
--- /dev/null
+++ b/src/test/ui/coherence/impl-foreign[fundemental[local]]-for-foreign.rs
@@ -0,0 +1,16 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+struct Local1<T>(Rc<T>);
+
+impl Remote1<Box<Local>> for i32 {}
+impl Remote1<Box<Local1<i32>>> for f64 {}
+impl<T> Remote1<Box<Local1<T>>> for f32 {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign-for-foreign[t].rs b/src/test/ui/coherence/impl[t]-foreign-for-foreign[t].rs
new file mode 100644
index 000000000..5282de4b2
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign-for-foreign[t].rs
@@ -0,0 +1,21 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+use std::sync::Arc;
+
+struct Local;
+
+impl Remote for Rc<Local> {
+ //~^ ERROR only traits defined in the current crate
+ // | can be implemented for arbitrary types [E0117]
+}
+
+impl<T> Remote for Arc<T> {
+ //~^ ERROR only traits defined in the current crate
+ // | can be implemented for arbitrary types [E0117]
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign-for-foreign[t].stderr b/src/test/ui/coherence/impl[t]-foreign-for-foreign[t].stderr
new file mode 100644
index 000000000..92346c291
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign-for-foreign[t].stderr
@@ -0,0 +1,25 @@
+error[E0117]: only traits defined in the current crate can be implemented for types defined outside of the crate
+ --> $DIR/impl[t]-foreign-for-foreign[t].rs:11:1
+ |
+LL | impl Remote for Rc<Local> {
+ | ^^^^^^^^^^^^^^^^---------
+ | | |
+ | | `Rc` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error[E0117]: only traits defined in the current crate can be implemented for types defined outside of the crate
+ --> $DIR/impl[t]-foreign-for-foreign[t].rs:16:1
+ |
+LL | impl<T> Remote for Arc<T> {
+ | ^^^^^^^^^^^^^^^^^^^------
+ | | |
+ | | `Arc` is not defined in the current crate
+ | impl doesn't use only types from inside the current crate
+ |
+ = note: define and implement a trait or new type instead
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0117`.
diff --git a/src/test/ui/coherence/impl[t]-foreign-for-fundamental[t].rs b/src/test/ui/coherence/impl[t]-foreign-for-fundamental[t].rs
new file mode 100644
index 000000000..6f5605a21
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign-for-fundamental[t].rs
@@ -0,0 +1,15 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<T> Remote for Box<T> {
+ //~^ ERROR type parameter `T` must be used as the type parameter for
+ // | some local type (e.g., `MyStruct<T>`)
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign-for-fundamental[t].stderr b/src/test/ui/coherence/impl[t]-foreign-for-fundamental[t].stderr
new file mode 100644
index 000000000..249a5c44c
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign-for-fundamental[t].stderr
@@ -0,0 +1,12 @@
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/impl[t]-foreign-for-fundamental[t].rs:10:6
+ |
+LL | impl<T> Remote for Box<T> {
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/impl[t]-foreign[foreign[t]_local]-for-foreign.rs b/src/test/ui/coherence/impl[t]-foreign[foreign[t]_local]-for-foreign.rs
new file mode 100644
index 000000000..99f3ce447
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[foreign[t]_local]-for-foreign.rs
@@ -0,0 +1,12 @@
+// check-pass
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+impl<T> Remote2<Rc<T>, Local> for usize { }
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[foreign]-for-fundamental[t].rs b/src/test/ui/coherence/impl[t]-foreign[foreign]-for-fundamental[t].rs
new file mode 100644
index 000000000..81044cd05
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[foreign]-for-fundamental[t].rs
@@ -0,0 +1,18 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<T> Remote1<u32> for Box<T> {
+ //~^ ERROR type parameter `T` must be used as the type parameter for some local type
+}
+
+impl<'a, T> Remote1<u32> for &'a T {
+ //~^ ERROR type parameter `T` must be used as the type parameter for some local type
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[foreign]-for-fundamental[t].stderr b/src/test/ui/coherence/impl[t]-foreign[foreign]-for-fundamental[t].stderr
new file mode 100644
index 000000000..95a20cc5b
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[foreign]-for-fundamental[t].stderr
@@ -0,0 +1,21 @@
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/impl[t]-foreign[foreign]-for-fundamental[t].rs:10:6
+ |
+LL | impl<T> Remote1<u32> for Box<T> {
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/impl[t]-foreign[foreign]-for-fundamental[t].rs:14:10
+ |
+LL | impl<'a, T> Remote1<u32> for &'a T {
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/impl[t]-foreign[foreign]-for-t.rs b/src/test/ui/coherence/impl[t]-foreign[foreign]-for-t.rs
new file mode 100644
index 000000000..680ba9f22
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[foreign]-for-t.rs
@@ -0,0 +1,14 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<T> Remote1<u32> for T {
+ //~^ ERROR type parameter `T` must be used as the type parameter for some local type
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[foreign]-for-t.stderr b/src/test/ui/coherence/impl[t]-foreign[foreign]-for-t.stderr
new file mode 100644
index 000000000..aed184767
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[foreign]-for-t.stderr
@@ -0,0 +1,12 @@
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/impl[t]-foreign[foreign]-for-t.rs:10:6
+ |
+LL | impl<T> Remote1<u32> for T {
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-foreign.rs b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-foreign.rs
new file mode 100644
index 000000000..fc7649085
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-foreign.rs
@@ -0,0 +1,18 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<T> Remote1<Box<T>> for u32 {
+ //~^ ERROR type parameter `T` must be used as the type parameter for some local type
+}
+
+impl<'a, T> Remote1<&'a T> for u32 {
+ //~^ ERROR type parameter `T` must be used as the type parameter for some local type
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-foreign.stderr b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-foreign.stderr
new file mode 100644
index 000000000..73b1e2c6e
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-foreign.stderr
@@ -0,0 +1,21 @@
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/impl[t]-foreign[fundamental[t]]-for-foreign.rs:10:6
+ |
+LL | impl<T> Remote1<Box<T>> for u32 {
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/impl[t]-foreign[fundamental[t]]-for-foreign.rs:14:10
+ |
+LL | impl<'a, T> Remote1<&'a T> for u32 {
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-fundamental[t].rs b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-fundamental[t].rs
new file mode 100644
index 000000000..703f25dd6
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-fundamental[t].rs
@@ -0,0 +1,17 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<'a, T> Remote1<Box<T>> for &'a T {
+ //~^ ERROR type parameter `T` must be used as the type parameter for some local type
+}
+impl<'a, T> Remote1<&'a T> for Box<T> {
+ //~^ ERROR type parameter `T` must be used as the type parameter for some local type
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-fundamental[t].stderr b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-fundamental[t].stderr
new file mode 100644
index 000000000..5f89a7aa4
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-fundamental[t].stderr
@@ -0,0 +1,21 @@
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/impl[t]-foreign[fundamental[t]]-for-fundamental[t].rs:10:10
+ |
+LL | impl<'a, T> Remote1<Box<T>> for &'a T {
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/impl[t]-foreign[fundamental[t]]-for-fundamental[t].rs:13:10
+ |
+LL | impl<'a, T> Remote1<&'a T> for Box<T> {
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-local.rs b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-local.rs
new file mode 100644
index 000000000..ec21fdd4e
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-local.rs
@@ -0,0 +1,15 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<T> Remote1<Box<T>> for Local {}
+
+impl<'a, T> Remote1<&'a T> for Local {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-t.rs b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-t.rs
new file mode 100644
index 000000000..5bdab87bf
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-t.rs
@@ -0,0 +1,17 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<T> Remote1<Box<T>> for T {
+ //~^ ERROR type parameter `T` must be used as the type parameter for some local type
+}
+impl<'a, T> Remote1<&'a T> for T {
+ //~^ ERROR type parameter `T` must be used as the type parameter for some local type
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-t.stderr b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-t.stderr
new file mode 100644
index 000000000..45559d8b6
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]]-for-t.stderr
@@ -0,0 +1,21 @@
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/impl[t]-foreign[fundamental[t]]-for-t.rs:10:6
+ |
+LL | impl<T> Remote1<Box<T>> for T {
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/impl[t]-foreign[fundamental[t]]-for-t.rs:13:10
+ |
+LL | impl<'a, T> Remote1<&'a T> for T {
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/impl[t]-foreign[fundamental[t]_local]-for-foreign.rs b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]_local]-for-foreign.rs
new file mode 100644
index 000000000..c9e3594cd
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]_local]-for-foreign.rs
@@ -0,0 +1,18 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<T> Remote2<Box<T>, Local> for u32 {
+ //~^ ERROR type parameter `T` must be covered by another type
+}
+
+impl<'a, T> Remote2<&'a T, Local> for u32 {
+ //~^ ERROR type parameter `T` must be covered by another type
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[fundamental[t]_local]-for-foreign.stderr b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]_local]-for-foreign.stderr
new file mode 100644
index 000000000..f94f04c8d
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[fundamental[t]_local]-for-foreign.stderr
@@ -0,0 +1,21 @@
+error[E0210]: type parameter `T` must be covered by another type when it appears before the first local type (`Local`)
+ --> $DIR/impl[t]-foreign[fundamental[t]_local]-for-foreign.rs:10:6
+ |
+LL | impl<T> Remote2<Box<T>, Local> for u32 {
+ | ^ type parameter `T` must be covered by another type when it appears before the first local type (`Local`)
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local, and no uncovered type parameters appear before that first local type
+ = note: in this case, 'before' refers to the following order: `impl<..> ForeignTrait<T1, ..., Tn> for T0`, where `T0` is the first and `Tn` is the last
+
+error[E0210]: type parameter `T` must be covered by another type when it appears before the first local type (`Local`)
+ --> $DIR/impl[t]-foreign[fundamental[t]_local]-for-foreign.rs:14:10
+ |
+LL | impl<'a, T> Remote2<&'a T, Local> for u32 {
+ | ^ type parameter `T` must be covered by another type when it appears before the first local type (`Local`)
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local, and no uncovered type parameters appear before that first local type
+ = note: in this case, 'before' refers to the following order: `impl<..> ForeignTrait<T1, ..., Tn> for T0`, where `T0` is the first and `Tn` is the last
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/impl[t]-foreign[fundemental[local]]-for-foreign[t].rs b/src/test/ui/coherence/impl[t]-foreign[fundemental[local]]-for-foreign[t].rs
new file mode 100644
index 000000000..62e69357e
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[fundemental[local]]-for-foreign[t].rs
@@ -0,0 +1,15 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+struct Local1<S>(Rc<S>);
+
+impl<T> Remote1<Box<Local>> for Rc<T> {}
+impl<S, T> Remote1<Box<Local1<S>>> for Rc<T> {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[local]-for-foreign.rs b/src/test/ui/coherence/impl[t]-foreign[local]-for-foreign.rs
new file mode 100644
index 000000000..1fec19bba
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[local]-for-foreign.rs
@@ -0,0 +1,14 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<T> Remote1<Local> for Rc<T> {}
+impl<T> Remote1<Local> for Vec<Box<T>> {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[local]-for-foreign[t].rs b/src/test/ui/coherence/impl[t]-foreign[local]-for-foreign[t].rs
new file mode 100644
index 000000000..c8ed28be6
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[local]-for-foreign[t].rs
@@ -0,0 +1,15 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+struct Local1<S>(Rc<S>);
+
+impl<T> Remote1<Local> for Rc<T> {}
+impl<T, S> Remote1<Local1<S>> for Rc<T> {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[local]-for-fundamental[foreign[t]].rs b/src/test/ui/coherence/impl[t]-foreign[local]-for-fundamental[foreign[t]].rs
new file mode 100644
index 000000000..f9b88c645
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[local]-for-fundamental[foreign[t]].rs
@@ -0,0 +1,17 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+struct Local1<S>(Rc<S>);
+
+impl<T> Remote1<Local> for Box<Rc<T>> {}
+impl<T, S> Remote1<Local1<S>> for Box<Rc<T>> {}
+impl<T> Remote1<Box<Local>> for Box<Rc<T>> {}
+impl<T, S> Remote1<Box<Local1<S>>> for Box<Rc<T>> {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[local]-for-fundamental[t].rs b/src/test/ui/coherence/impl[t]-foreign[local]-for-fundamental[t].rs
new file mode 100644
index 000000000..7709bd9c8
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[local]-for-fundamental[t].rs
@@ -0,0 +1,18 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<T> Remote1<Local> for Box<T> {
+ //~^ ERROR type parameter `T` must be covered by another type
+}
+
+impl<T> Remote1<Local> for &T {
+ //~^ ERROR type parameter `T` must be covered by another type
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[local]-for-fundamental[t].stderr b/src/test/ui/coherence/impl[t]-foreign[local]-for-fundamental[t].stderr
new file mode 100644
index 000000000..e68f2fe58
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[local]-for-fundamental[t].stderr
@@ -0,0 +1,21 @@
+error[E0210]: type parameter `T` must be covered by another type when it appears before the first local type (`Local`)
+ --> $DIR/impl[t]-foreign[local]-for-fundamental[t].rs:10:6
+ |
+LL | impl<T> Remote1<Local> for Box<T> {
+ | ^ type parameter `T` must be covered by another type when it appears before the first local type (`Local`)
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local, and no uncovered type parameters appear before that first local type
+ = note: in this case, 'before' refers to the following order: `impl<..> ForeignTrait<T1, ..., Tn> for T0`, where `T0` is the first and `Tn` is the last
+
+error[E0210]: type parameter `T` must be covered by another type when it appears before the first local type (`Local`)
+ --> $DIR/impl[t]-foreign[local]-for-fundamental[t].rs:14:6
+ |
+LL | impl<T> Remote1<Local> for &T {
+ | ^ type parameter `T` must be covered by another type when it appears before the first local type (`Local`)
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local, and no uncovered type parameters appear before that first local type
+ = note: in this case, 'before' refers to the following order: `impl<..> ForeignTrait<T1, ..., Tn> for T0`, where `T0` is the first and `Tn` is the last
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/impl[t]-foreign[local]-for-local.rs b/src/test/ui/coherence/impl[t]-foreign[local]-for-local.rs
new file mode 100644
index 000000000..9c14eea1b
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[local]-for-local.rs
@@ -0,0 +1,13 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl Remote1<Local> for Local {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[local]-for-t.rs b/src/test/ui/coherence/impl[t]-foreign[local]-for-t.rs
new file mode 100644
index 000000000..eed3a4b5c
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[local]-for-t.rs
@@ -0,0 +1,14 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<T> Remote1<Local> for T {
+ //~^ ERROR type parameter `T` must be covered by another type
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[local]-for-t.stderr b/src/test/ui/coherence/impl[t]-foreign[local]-for-t.stderr
new file mode 100644
index 000000000..d97e85dcb
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[local]-for-t.stderr
@@ -0,0 +1,12 @@
+error[E0210]: type parameter `T` must be covered by another type when it appears before the first local type (`Local`)
+ --> $DIR/impl[t]-foreign[local]-for-t.rs:10:6
+ |
+LL | impl<T> Remote1<Local> for T {
+ | ^ type parameter `T` must be covered by another type when it appears before the first local type (`Local`)
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local, and no uncovered type parameters appear before that first local type
+ = note: in this case, 'before' refers to the following order: `impl<..> ForeignTrait<T1, ..., Tn> for T0`, where `T0` is the first and `Tn` is the last
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/impl[t]-foreign[local_fundamental[t]]-for-foreign.rs b/src/test/ui/coherence/impl[t]-foreign[local_fundamental[t]]-for-foreign.rs
new file mode 100644
index 000000000..63c342b76
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[local_fundamental[t]]-for-foreign.rs
@@ -0,0 +1,17 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+struct Local2<T>(Rc<T>);
+
+impl<T> Remote2<Local, Box<T>> for u32 {}
+impl<'a, T> Remote2<Local, &'a T> for u32 {}
+impl<T> Remote2<Local2<T>, Box<T>> for u32 {}
+impl<'a, T> Remote2<Local2<T>, &'a T> for u32 {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[t]-for-foreign.rs b/src/test/ui/coherence/impl[t]-foreign[t]-for-foreign.rs
new file mode 100644
index 000000000..9bb37c2ba
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[t]-for-foreign.rs
@@ -0,0 +1,14 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<T> Remote1<T> for u32 {
+ //~^ ERROR type parameter `T` must be used as the type parameter for some local type
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[t]-for-foreign.stderr b/src/test/ui/coherence/impl[t]-foreign[t]-for-foreign.stderr
new file mode 100644
index 000000000..44e3b7eed
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[t]-for-foreign.stderr
@@ -0,0 +1,12 @@
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/impl[t]-foreign[t]-for-foreign.rs:10:6
+ |
+LL | impl<T> Remote1<T> for u32 {
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/impl[t]-foreign[t]-for-fundamental.rs b/src/test/ui/coherence/impl[t]-foreign[t]-for-fundamental.rs
new file mode 100644
index 000000000..79b5aa3fc
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[t]-for-fundamental.rs
@@ -0,0 +1,18 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<T> Remote1<T> for Box<T> {
+ //~^ ERROR type parameter `T` must be used as the type parameter for some local type
+}
+
+impl<'a, A, B> Remote1<A> for &'a B {
+ //~^ ERROR type parameter `B` must be used as the type parameter for some local type
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[t]-for-fundamental.stderr b/src/test/ui/coherence/impl[t]-foreign[t]-for-fundamental.stderr
new file mode 100644
index 000000000..80fb5dbec
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[t]-for-fundamental.stderr
@@ -0,0 +1,21 @@
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/impl[t]-foreign[t]-for-fundamental.rs:10:6
+ |
+LL | impl<T> Remote1<T> for Box<T> {
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error[E0210]: type parameter `B` must be used as the type parameter for some local type (e.g., `MyStruct<B>`)
+ --> $DIR/impl[t]-foreign[t]-for-fundamental.rs:14:13
+ |
+LL | impl<'a, A, B> Remote1<A> for &'a B {
+ | ^ type parameter `B` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/impl[t]-foreign[t]-for-local.rs b/src/test/ui/coherence/impl[t]-foreign[t]-for-local.rs
new file mode 100644
index 000000000..bc59721c0
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[t]-for-local.rs
@@ -0,0 +1,13 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+// check-pass
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<T> Remote1<T> for Local {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[t]-for-t.rs b/src/test/ui/coherence/impl[t]-foreign[t]-for-t.rs
new file mode 100644
index 000000000..bcd6b269a
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[t]-for-t.rs
@@ -0,0 +1,14 @@
+// compile-flags:--crate-name=test
+// aux-build:coherence_lib.rs
+
+extern crate coherence_lib as lib;
+use lib::*;
+use std::rc::Rc;
+
+struct Local;
+
+impl<T> Remote1<T> for T {
+ //~^ ERROR type parameter `T` must be used as the type parameter for some local type
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/impl[t]-foreign[t]-for-t.stderr b/src/test/ui/coherence/impl[t]-foreign[t]-for-t.stderr
new file mode 100644
index 000000000..ff72969dc
--- /dev/null
+++ b/src/test/ui/coherence/impl[t]-foreign[t]-for-t.stderr
@@ -0,0 +1,12 @@
+error[E0210]: type parameter `T` must be used as the type parameter for some local type (e.g., `MyStruct<T>`)
+ --> $DIR/impl[t]-foreign[t]-for-t.rs:10:6
+ |
+LL | impl<T> Remote1<T> for T {
+ | ^ type parameter `T` must be used as the type parameter for some local type
+ |
+ = note: implementing a foreign trait is only possible if at least one of the types for which it is implemented is local
+ = note: only traits defined in the current crate can be implemented for a type parameter
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0210`.
diff --git a/src/test/ui/coherence/inter-crate-ambiguity-causes-notes.rs b/src/test/ui/coherence/inter-crate-ambiguity-causes-notes.rs
new file mode 100644
index 000000000..5b11c78ab
--- /dev/null
+++ b/src/test/ui/coherence/inter-crate-ambiguity-causes-notes.rs
@@ -0,0 +1,19 @@
+struct S;
+
+impl From<()> for S {
+ fn from(x: ()) -> Self {
+ S
+ }
+}
+
+impl<I> From<I> for S
+//~^ ERROR conflicting implementations of trait
+where
+ I: Iterator<Item = ()>,
+{
+ fn from(x: I) -> Self {
+ S
+ }
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/inter-crate-ambiguity-causes-notes.stderr b/src/test/ui/coherence/inter-crate-ambiguity-causes-notes.stderr
new file mode 100644
index 000000000..038a0199a
--- /dev/null
+++ b/src/test/ui/coherence/inter-crate-ambiguity-causes-notes.stderr
@@ -0,0 +1,14 @@
+error[E0119]: conflicting implementations of trait `std::convert::From<()>` for type `S`
+ --> $DIR/inter-crate-ambiguity-causes-notes.rs:9:1
+ |
+LL | impl From<()> for S {
+ | ------------------- first implementation here
+...
+LL | impl<I> From<I> for S
+ | ^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `S`
+ |
+ = note: upstream crates may add a new impl of trait `std::iter::Iterator` for type `()` in future versions
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0119`.
diff --git a/src/test/ui/coherence/issue-85026.rs b/src/test/ui/coherence/issue-85026.rs
new file mode 100644
index 000000000..8b116545a
--- /dev/null
+++ b/src/test/ui/coherence/issue-85026.rs
@@ -0,0 +1,10 @@
+#![feature(auto_traits)]
+auto trait AutoTrait {}
+
+// You cannot impl your own `dyn AutoTrait`.
+impl dyn AutoTrait {} //~ERROR E0785
+
+// You cannot impl someone else's `dyn AutoTrait`
+impl dyn Unpin {} //~ERROR E0785
+
+fn main() {}
diff --git a/src/test/ui/coherence/issue-85026.stderr b/src/test/ui/coherence/issue-85026.stderr
new file mode 100644
index 000000000..a5da19bbf
--- /dev/null
+++ b/src/test/ui/coherence/issue-85026.stderr
@@ -0,0 +1,19 @@
+error[E0785]: cannot define inherent `impl` for a dyn auto trait
+ --> $DIR/issue-85026.rs:5:6
+ |
+LL | impl dyn AutoTrait {}
+ | ^^^^^^^^^^^^^ impl requires at least one non-auto trait
+ |
+ = note: define and implement a new trait or type instead
+
+error[E0785]: cannot define inherent `impl` for a dyn auto trait
+ --> $DIR/issue-85026.rs:8:6
+ |
+LL | impl dyn Unpin {}
+ | ^^^^^^^^^ impl requires at least one non-auto trait
+ |
+ = note: define and implement a new trait or type instead
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0785`.
diff --git a/src/test/ui/coherence/issue-99663-2.rs b/src/test/ui/coherence/issue-99663-2.rs
new file mode 100644
index 000000000..10a0a5688
--- /dev/null
+++ b/src/test/ui/coherence/issue-99663-2.rs
@@ -0,0 +1,22 @@
+// check-pass
+
+#![feature(type_alias_impl_trait)]
+
+struct Outer<T: ?Sized> {
+ i: InnerSend<T>,
+}
+
+type InnerSend<T: ?Sized> = impl Send;
+
+fn constrain<T: ?Sized>() -> InnerSend<T> {
+ ()
+}
+
+trait SendMustNotImplDrop {}
+
+#[allow(drop_bounds)]
+impl<T: ?Sized + Send + Drop> SendMustNotImplDrop for T {}
+
+impl<T: ?Sized> SendMustNotImplDrop for Outer<T> {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/issue-99663.rs b/src/test/ui/coherence/issue-99663.rs
new file mode 100644
index 000000000..a2d4d398c
--- /dev/null
+++ b/src/test/ui/coherence/issue-99663.rs
@@ -0,0 +1,22 @@
+// check-pass
+
+#![feature(type_alias_impl_trait)]
+
+struct Send<T> {
+ i: InnerSend<T>,
+}
+
+type InnerSend<T> = impl Sized;
+
+fn constrain<T>() -> InnerSend<T> {
+ ()
+}
+
+trait SendMustNotImplDrop {}
+
+#[allow(drop_bounds)]
+impl<T: Drop> SendMustNotImplDrop for T {}
+
+impl<T> SendMustNotImplDrop for Send<T> {}
+
+fn main() {}
diff --git a/src/test/ui/coherence/re-rebalance-coherence-default-generic-associated-type.rs b/src/test/ui/coherence/re-rebalance-coherence-default-generic-associated-type.rs
new file mode 100644
index 000000000..d18e3f453
--- /dev/null
+++ b/src/test/ui/coherence/re-rebalance-coherence-default-generic-associated-type.rs
@@ -0,0 +1,26 @@
+// run-pass
+// aux-build:re_rebalance_coherence_lib-rpass.rs
+
+#![allow(dead_code)]
+// check that a generic type with a default value from an associated type can be used without
+// specifying the value, and without invoking coherence errors.
+
+extern crate re_rebalance_coherence_lib_rpass as lib;
+use lib::*;
+
+struct MyString {}
+
+impl LibToOwned for MyString {
+ type Owned = String;
+}
+
+impl PartialEq<MyString> for LibCow<MyString> {
+ fn eq(&self, _other: &MyString) -> bool {
+ // Test that the default type is used.
+ let _s: &String = &self.o;
+
+ false
+ }
+}
+
+fn main() {}
diff --git a/src/test/ui/coherence/re-rebalance-coherence.rs b/src/test/ui/coherence/re-rebalance-coherence.rs
new file mode 100644
index 000000000..38d096b08
--- /dev/null
+++ b/src/test/ui/coherence/re-rebalance-coherence.rs
@@ -0,0 +1,11 @@
+// run-pass
+// aux-build:re_rebalance_coherence_lib.rs
+
+extern crate re_rebalance_coherence_lib as lib;
+use lib::*;
+
+struct Oracle;
+impl Backend for Oracle {}
+impl<'a, T:'a, Tab> QueryFragment<Oracle> for BatchInsert<'a, T, Tab> {}
+
+fn main() {}