about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--compiler/rustc_ast_passes/messages.ftl3
-rw-r--r--compiler/rustc_ast_passes/src/ast_validation.rs12
-rw-r--r--compiler/rustc_ast_passes/src/errors.rs7
-rw-r--r--compiler/rustc_hir_analysis/src/astconv/mod.rs2
-rw-r--r--tests/ui/traits/negative-bounds/associated-constraints.rs20
-rw-r--r--tests/ui/traits/negative-bounds/associated-constraints.stderr34
6 files changed, 76 insertions, 2 deletions
diff --git a/compiler/rustc_ast_passes/messages.ftl b/compiler/rustc_ast_passes/messages.ftl
index 90535af781d..2f413789e77 100644
--- a/compiler/rustc_ast_passes/messages.ftl
+++ b/compiler/rustc_ast_passes/messages.ftl
@@ -238,3 +238,6 @@ ast_passes_show_span = {$msg}
 
 ast_passes_negative_bound_not_supported =
     negative bounds are not supported
+
+ast_passes_constraint_on_negative_bound =
+    associated type constraints not allowed on negative bounds
diff --git a/compiler/rustc_ast_passes/src/ast_validation.rs b/compiler/rustc_ast_passes/src/ast_validation.rs
index 6e9d33516ce..bf43bbdbbee 100644
--- a/compiler/rustc_ast_passes/src/ast_validation.rs
+++ b/compiler/rustc_ast_passes/src/ast_validation.rs
@@ -1177,6 +1177,18 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
             }
         }
 
+        // Negative trait bounds are not allowed to have associated constraints
+        if let GenericBound::Trait(trait_ref, TraitBoundModifier::Negative) = bound
+            && let Some(segment) = trait_ref.trait_ref.path.segments.last()
+            && let Some(ast::GenericArgs::AngleBracketed(args)) = segment.args.as_deref()
+        {
+            for arg in &args.args {
+                if let ast::AngleBracketedArg::Constraint(constraint) = arg {
+                    self.err_handler().emit_err(errors::ConstraintOnNegativeBound { span: constraint.span });
+                }
+            }
+        }
+
         visit::walk_param_bound(self, bound)
     }
 
diff --git a/compiler/rustc_ast_passes/src/errors.rs b/compiler/rustc_ast_passes/src/errors.rs
index 66a47db9074..82fe2a21d08 100644
--- a/compiler/rustc_ast_passes/src/errors.rs
+++ b/compiler/rustc_ast_passes/src/errors.rs
@@ -701,3 +701,10 @@ pub struct NegativeBoundUnsupported {
     #[primary_span]
     pub span: Span,
 }
+
+#[derive(Diagnostic)]
+#[diag(ast_passes_constraint_on_negative_bound)]
+pub struct ConstraintOnNegativeBound {
+    #[primary_span]
+    pub span: Span,
+}
diff --git a/compiler/rustc_hir_analysis/src/astconv/mod.rs b/compiler/rustc_hir_analysis/src/astconv/mod.rs
index 0faf7a4ba45..fda59d000ea 100644
--- a/compiler/rustc_hir_analysis/src/astconv/mod.rs
+++ b/compiler/rustc_hir_analysis/src/astconv/mod.rs
@@ -701,8 +701,6 @@ impl<'o, 'tcx> dyn AstConv<'tcx> + 'o {
 
         let mut dup_bindings = FxHashMap::default();
         for binding in &assoc_bindings {
-            // TODO: negative polarity can't have associated type bindings!
-
             // Specify type to assert that error was already reported in `Err` case.
             let _: Result<_, ErrorGuaranteed> = self.add_predicates_for_ast_type_binding(
                 hir_id,
diff --git a/tests/ui/traits/negative-bounds/associated-constraints.rs b/tests/ui/traits/negative-bounds/associated-constraints.rs
new file mode 100644
index 00000000000..bc1a0ef1708
--- /dev/null
+++ b/tests/ui/traits/negative-bounds/associated-constraints.rs
@@ -0,0 +1,20 @@
+#![feature(negative_bounds, associated_type_bounds)]
+//~^ WARN the feature `negative_bounds` is incomplete and may not be safe to use and/or cause compiler crashes
+
+trait Trait {
+    type Assoc;
+}
+
+fn test<T: !Trait<Assoc = i32>>() {}
+//~^ ERROR associated type constraints not allowed on negative bounds
+
+fn test2<T>() where T: !Trait<Assoc = i32> {}
+//~^ ERROR associated type constraints not allowed on negative bounds
+
+fn test3<T: !Trait<Assoc: Send>>() {}
+//~^ ERROR associated type constraints not allowed on negative bounds
+
+fn test4<T>() where T: !Trait<Assoc: Send> {}
+//~^ ERROR associated type constraints not allowed on negative bounds
+
+fn main() {}
diff --git a/tests/ui/traits/negative-bounds/associated-constraints.stderr b/tests/ui/traits/negative-bounds/associated-constraints.stderr
new file mode 100644
index 00000000000..335ac7e5ad9
--- /dev/null
+++ b/tests/ui/traits/negative-bounds/associated-constraints.stderr
@@ -0,0 +1,34 @@
+error: associated type constraints not allowed on negative bounds
+  --> $DIR/associated-constraints.rs:8:19
+   |
+LL | fn test<T: !Trait<Assoc = i32>>() {}
+   |                   ^^^^^^^^^^^
+
+error: associated type constraints not allowed on negative bounds
+  --> $DIR/associated-constraints.rs:11:31
+   |
+LL | fn test2<T>() where T: !Trait<Assoc = i32> {}
+   |                               ^^^^^^^^^^^
+
+error: associated type constraints not allowed on negative bounds
+  --> $DIR/associated-constraints.rs:14:20
+   |
+LL | fn test3<T: !Trait<Assoc: Send>>() {}
+   |                    ^^^^^^^^^^^
+
+error: associated type constraints not allowed on negative bounds
+  --> $DIR/associated-constraints.rs:17:31
+   |
+LL | fn test4<T>() where T: !Trait<Assoc: Send> {}
+   |                               ^^^^^^^^^^^
+
+warning: the feature `negative_bounds` is incomplete and may not be safe to use and/or cause compiler crashes
+  --> $DIR/associated-constraints.rs:1:12
+   |
+LL | #![feature(negative_bounds, associated_type_bounds)]
+   |            ^^^^^^^^^^^^^^^
+   |
+   = note: `#[warn(incomplete_features)]` on by default
+
+error: aborting due to 4 previous errors; 1 warning emitted
+