Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion compiler/rustc_error_codes/src/error_codes/E0224.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,5 +11,5 @@ Rust does not currently support this.
To solve, ensure that the trait object has at least one trait:

```
type Foo = dyn 'static + Copy;
type Foo = dyn 'static + std::fmt::Debug;
```
21 changes: 13 additions & 8 deletions compiler/rustc_hir_analysis/src/check/check.rs
Original file line number Diff line number Diff line change
Expand Up @@ -985,6 +985,7 @@ pub(crate) fn check_item_type(tcx: TyCtxt<'_>, def_id: LocalDefId) -> Result<(),
} else {
check_type_alias_type_params_are_used(tcx, def_id);
res = res.and(enter_wf_checking_ctxt(tcx, def_id, |wfcx| {
// FIXME(fmease): Update comment.
// HACK: We sometimes incidentally check that const arguments have the correct
// type as a side effect of the anon const desugaring. To make this "consistent"
// for users we explicitly check `ConstArgHasType` clauses so that const args
Expand All @@ -995,15 +996,19 @@ pub(crate) fn check_item_type(tcx: TyCtxt<'_>, def_id: LocalDefId) -> Result<(),
//
// Changing this to normalized obligations is a breaking change:
// `type Bar = [(); panic!()];` would become an error
if let Some(unnormalized_obligations) = wfcx.unnormalized_obligations(span, ty.skip_norm_wip())
if let Some(obligations) =
wfcx.unnormalized_obligations(span, ty.skip_norm_wip())
{
let filtered_obligations =
unnormalized_obligations.into_iter().filter(|o| {
matches!(o.predicate.kind().skip_binder(),
ty::PredicateKind::Clause(ty::ClauseKind::ConstArgHasType(ct, _))
if matches!(ct.kind(), ty::ConstKind::Param(..)))
});
wfcx.ocx.register_obligations(filtered_obligations)
wfcx.ocx.register_obligations(obligations.into_iter().filter(|o| {
match o.predicate.kind().skip_binder() {
ty::PredicateKind::Clause(ty::ClauseKind::ConstArgHasType(
ct,
_,
)) => matches!(ct.kind(), ty::ConstKind::Param(..)),
ty::PredicateKind::DynCompatible(_) => true,
_ => false,
}
}))
}
Ok(())
}));
Expand Down
2 changes: 1 addition & 1 deletion tests/rustdoc-html/inline_cross/auxiliary/dyn_trait.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ pub type Ty2 = dyn for<'a, 'r> Container<'r, Item<'a, 'static> = ()>;
pub type Ty3<'s> = &'s dyn ToString;

pub trait Container<'r> {
type Item<'a, 'ctx>;
type Item<'a, 'ctx> where Self: Sized;
}

// Trait-object types inside of a container type that has lifetime bounds ("wrapped").
Expand Down
8 changes: 4 additions & 4 deletions tests/ui/conditional-compilation/cfg-generic-params.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,8 @@ type FnGood = for<#[cfg(yes)] 'a, #[cfg(false)] T> fn(); // OK
type FnBad = for<#[cfg(false)] 'a, #[cfg(yes)] T> fn();
//~^ ERROR only lifetime parameters can be used in this context

type PolyGood = dyn for<#[cfg(yes)] 'a, #[cfg(false)] T> Copy; // OK
type PolyBad = dyn for<#[cfg(false)] 'a, #[cfg(yes)] T> Copy;
type PolyGood = dyn for<#[cfg(yes)] 'a, #[cfg(false)] T> std::any::Any; // OK
type PolyBad = dyn for<#[cfg(false)] 'a, #[cfg(yes)] T> std::any::Any;
//~^ ERROR only lifetime parameters can be used in this context

struct WhereGood where for<#[cfg(yes)] 'a, #[cfg(false)] T> u8: Copy; // OK
Expand All @@ -26,8 +26,8 @@ type FnNo = for<#[cfg_attr(FALSE, unknown)] 'a> fn(); // OK
type FnYes = for<#[cfg_attr(yes, unknown)] 'a> fn();
//~^ ERROR cannot find attribute `unknown` in this scope

type PolyNo = dyn for<#[cfg_attr(FALSE, unknown)] 'a> Copy; // OK
type PolyYes = dyn for<#[cfg_attr(yes, unknown)] 'a> Copy;
type PolyNo = dyn for<#[cfg_attr(FALSE, unknown)] 'a> std::any::Any; // OK
type PolyYes = dyn for<#[cfg_attr(yes, unknown)] 'a> std::any::Any;
//~^ ERROR cannot find attribute `unknown` in this scope

struct WhereNo where for<#[cfg_attr(FALSE, unknown)] 'a> u8: Copy; // OK
Expand Down
4 changes: 2 additions & 2 deletions tests/ui/conditional-compilation/cfg-generic-params.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ LL | type FnYes = for<#[cfg_attr(yes, unknown)] 'a> fn();
error: cannot find attribute `unknown` in this scope
--> $DIR/cfg-generic-params.rs:30:40
|
LL | type PolyYes = dyn for<#[cfg_attr(yes, unknown)] 'a> Copy;
LL | type PolyYes = dyn for<#[cfg_attr(yes, unknown)] 'a> std::any::Any;
| ^^^^^^^

error: cannot find attribute `unknown` in this scope
Expand All @@ -41,7 +41,7 @@ LL | type FnBad = for<#[cfg(false)] 'a, #[cfg(yes)] T> fn();
error[E0658]: only lifetime parameters can be used in this context
--> $DIR/cfg-generic-params.rs:11:54
|
LL | type PolyBad = dyn for<#[cfg(false)] 'a, #[cfg(yes)] T> Copy;
LL | type PolyBad = dyn for<#[cfg(false)] 'a, #[cfg(yes)] T> std::any::Any;
| ^
|
= note: see issue #108185 <https://github.com/rust-lang/rust/issues/108185> for more information
Expand Down
15 changes: 15 additions & 0 deletions tests/ui/dyn-compatibility/in-unchecked-type-alias.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
// FIXME(fmease): Write a description.

type DynIncompat0 = dyn Sized; //~ ERROR not dyn compatible

// FIXME(fmease): Well, if this breakage got accepted linking to this issue
// would be moot / nonsensical. Remove the link.
// issue: <https://github.com/rust-lang/rust/issues/153731>
type DynIncompat1 = dyn HasAssocConst; //~ ERROR not dyn compatible

type DynIncompat2<'a> = dyn HasGenericAssocType<Type<()> = ()>; //~ ERROR not dyn compatible

trait HasAssocConst { const N: usize; }
trait HasGenericAssocType { type Type<T>; }

fn main() {}
45 changes: 45 additions & 0 deletions tests/ui/dyn-compatibility/in-unchecked-type-alias.stderr
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
error[E0038]: the trait `Sized` is not dyn compatible
--> $DIR/in-unchecked-type-alias.rs:3:1
|
LL | type DynIncompat0 = dyn Sized;
| ^^^^^^^^^^^^^^^^^ `Sized` is not dyn compatible
|
= note: the trait is not dyn compatible because it requires `Self: Sized`
= note: for a trait to be dyn compatible it needs to allow building a vtable
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>

error[E0038]: the trait `HasAssocConst` is not dyn compatible
--> $DIR/in-unchecked-type-alias.rs:8:1
|
LL | type DynIncompat1 = dyn HasAssocConst;
| ^^^^^^^^^^^^^^^^^ `HasAssocConst` is not dyn compatible
|
note: for a trait to be dyn compatible it needs to allow building a vtable
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>
--> $DIR/in-unchecked-type-alias.rs:12:29
|
LL | trait HasAssocConst { const N: usize; }
| ------------- ^ ...because it contains associated const `N`
| |
| this trait is not dyn compatible...
= help: consider moving `N` to another trait

error[E0038]: the trait `HasGenericAssocType` is not dyn compatible
--> $DIR/in-unchecked-type-alias.rs:10:1
|
LL | type DynIncompat2<'a> = dyn HasGenericAssocType<Type<()> = ()>;
| ^^^^^^^^^^^^^^^^^^^^^ `HasGenericAssocType` is not dyn compatible
|
note: for a trait to be dyn compatible it needs to allow building a vtable
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>
--> $DIR/in-unchecked-type-alias.rs:13:34
|
LL | trait HasGenericAssocType { type Type<T>; }
| ------------------- ^^^^ ...because it contains generic associated type `Type`
| |
| this trait is not dyn compatible...
= help: consider moving `Type` to another trait

error: aborting due to 3 previous errors

For more information about this error, try `rustc --explain E0038`.
8 changes: 4 additions & 4 deletions tests/ui/hygiene/assoc_ty_bindings.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,10 @@

trait Base {
type AssocTy;
fn f();
fn f(self);
}
trait Derived: Base {
fn g();
fn g(self);
}

macro mac() {
Expand All @@ -16,12 +16,12 @@ macro mac() {

impl Base for u8 {
type AssocTy = u8;
fn f() {
fn f(self) {
let _: Self::AssocTy;
}
}
impl Derived for u8 {
fn g() {
fn g(self) {
let _: Self::AssocTy;
}
}
Expand Down
6 changes: 3 additions & 3 deletions tests/ui/resolve/issue-3907-2.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,14 @@

extern crate issue_3907;

type Foo = dyn issue_3907::Foo + 'static;
type Foo = dyn issue_3907::Foo + 'static; //~ ERROR not dyn compatible [E0038]

struct S {
name: isize
}

fn bar(_x: Foo) {}
//~^ ERROR E0038
//~| ERROR E0277
//~^ ERROR not dyn compatible [E0038]
//~| ERROR cannot be known at compilation time [E0277]

fn main() {}
15 changes: 14 additions & 1 deletion tests/ui/resolve/issue-3907-2.stderr
Original file line number Diff line number Diff line change
@@ -1,3 +1,16 @@
error[E0038]: the trait `issue_3907::Foo` is not dyn compatible
--> $DIR/issue-3907-2.rs:5:1
|
LL | type Foo = dyn issue_3907::Foo + 'static;
| ^^^^^^^^ `issue_3907::Foo` is not dyn compatible
|
note: for a trait to be dyn compatible it needs to allow building a vtable
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>
--> $DIR/auxiliary/issue-3907.rs:2:8
|
LL | fn bar();
| ^^^ the trait is not dyn compatible because associated function `bar` has no `self` parameter

error[E0038]: the trait `issue_3907::Foo` is not dyn compatible
--> $DIR/issue-3907-2.rs:11:12
|
Expand All @@ -24,7 +37,7 @@ help: function arguments must have a statically known size, borrowed types alway
LL | fn bar(_x: &Foo) {}
| +

error: aborting due to 2 previous errors
error: aborting due to 3 previous errors

Some errors have detailed explanations: E0038, E0277.
For more information about an error, try `rustc --explain E0038`.
2 changes: 1 addition & 1 deletion tests/ui/resolve/issue-3907.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

extern crate issue_3907;

type Foo = dyn issue_3907::Foo;
type Foo = dyn issue_3907::Foo; //~ ERROR not dyn compatible

struct S {
name: isize
Expand Down
18 changes: 16 additions & 2 deletions tests/ui/resolve/issue-3907.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,20 @@ help: consider importing this trait instead
LL + use issue_3907::Foo;
|

error: aborting due to 1 previous error
error[E0038]: the trait `issue_3907::Foo` is not dyn compatible
--> $DIR/issue-3907.rs:5:1
|
LL | type Foo = dyn issue_3907::Foo;
| ^^^^^^^^ `issue_3907::Foo` is not dyn compatible
|
note: for a trait to be dyn compatible it needs to allow building a vtable
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>
--> $DIR/auxiliary/issue-3907.rs:2:8
|
LL | fn bar();
| ^^^ the trait is not dyn compatible because associated function `bar` has no `self` parameter

error: aborting due to 2 previous errors

For more information about this error, try `rustc --explain E0404`.
Some errors have detailed explanations: E0038, E0404.
For more information about an error, try `rustc --explain E0038`.
2 changes: 1 addition & 1 deletion tests/ui/sized-hierarchy/trait-alias-elaboration.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ use std::marker::MetaSized;
// wrote `MetaSized` in the `dyn Trait` then that should still be an error so as not to accidentally
// accept this going forwards.

trait Qux = Clone;
trait Qux = std::fmt::Debug;

type Foo = dyn Qux + MetaSized;
//~^ ERROR: only auto traits can be used as additional traits in a trait object
Expand Down
6 changes: 3 additions & 3 deletions tests/ui/sized-hierarchy/trait-alias-elaboration.stderr
Original file line number Diff line number Diff line change
@@ -1,15 +1,15 @@
error[E0225]: only auto traits can be used as additional traits in a trait object
--> $DIR/trait-alias-elaboration.rs:11:16
|
LL | trait Qux = Clone;
| ------------------ additional non-auto trait
LL | trait Qux = std::fmt::Debug;
| ---------------------------- additional non-auto trait
LL |
LL | type Foo = dyn Qux + MetaSized;
| ^^^ --------- first non-auto trait
| |
| second non-auto trait comes from this alias
|
= help: consider creating a new trait with all of these as supertraits and using that trait here instead: `trait NewTrait: MetaSized + MetaSized + Clone {}`
= help: consider creating a new trait with all of these as supertraits and using that trait here instead: `trait NewTrait: MetaSized + MetaSized + Debug {}`
= note: auto-traits like `Send` and `Sync` are traits that have special properties; for more information on them, visit <https://doc.rust-lang.org/reference/special-types-and-traits.html#auto-traits>

error: aborting due to 1 previous error
Expand Down
21 changes: 0 additions & 21 deletions tests/ui/type-alias/lack-of-wfcheck-gat-generic-const-args.rs

This file was deleted.

34 changes: 0 additions & 34 deletions tests/ui/type-alias/lack-of-wfcheck-gat-generic-const-args.stderr

This file was deleted.

Original file line number Diff line number Diff line change
@@ -1,16 +1,16 @@
error[E0191]: the value of the associated constant `N` in `HasAssocConst` must be specified
--> $DIR/lack-of-wfcheck-generic-const-args.rs:19:25
error[E0191]: the value of the associated constant `N` in `HasNonTypeAssocConst` must be specified
--> $DIR/lack-of-wfcheck-generic-const-args.rs:13:20
|
LL | type DynIncompat1 = dyn HasAssocConst;
| ^^^^^^^^^^^^^
LL | type TyAlias = dyn HasNonTypeAssocConst;
| ^^^^^^^^^^^^^^^^^^^^
...
LL | const N: usize;
| -------------- `N` defined here
LL | /*non-type */const N: usize;
| -------------- `N` defined here
|
help: specify the associated constant
|
LL | type DynIncompat1 = dyn HasAssocConst<N = /* CONST */>;
| +++++++++++++++++
LL | type TyAlias = dyn HasNonTypeAssocConst<N = /* CONST */>;
| +++++++++++++++++

error: aborting due to 1 previous error

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
error[E0038]: the trait `HasNonTypeAssocConst` is not dyn compatible
--> $DIR/lack-of-wfcheck-generic-const-args.rs:13:1
|
LL | type TyAlias = dyn HasNonTypeAssocConst;
| ^^^^^^^^^^^^ `HasNonTypeAssocConst` is not dyn compatible
|
note: for a trait to be dyn compatible it needs to allow building a vtable
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>
--> $DIR/lack-of-wfcheck-generic-const-args.rs:17:24
|
LL | trait HasNonTypeAssocConst {
| -------------------- this trait is not dyn compatible...
LL | /*non-type */const N: usize;
| ^ ...because it contains associated const `N`
= help: consider moving `N` to another trait

error: aborting due to 1 previous error

For more information about this error, try `rustc --explain E0038`.
Loading
Loading