diff options
| author | Charles Lew <crlf0710@gmail.com> | 2021-07-31 00:46:43 +0800 |
|---|---|---|
| committer | Charles Lew <crlf0710@gmail.com> | 2021-07-31 10:42:11 +0800 |
| commit | a28ee25483d92b7924752651d9c751ae2c4f2c34 (patch) | |
| tree | b085c9f7256de7093c2f783227009e91e8d182d1 /src | |
| parent | fb4e0a097238c309220d97d1a62350bafd953083 (diff) | |
| download | rust-a28ee25483d92b7924752651d9c751ae2c4f2c34.tar.gz rust-a28ee25483d92b7924752651d9c751ae2c4f2c34.zip | |
Add more tests to cover more corner cases of type-checking.
Diffstat (limited to 'src')
8 files changed, 342 insertions, 0 deletions
diff --git a/src/test/ui/traits/trait-upcasting/type-checking-test-1.rs b/src/test/ui/traits/trait-upcasting/type-checking-test-1.rs new file mode 100644 index 00000000000..1a0e5072843 --- /dev/null +++ b/src/test/ui/traits/trait-upcasting/type-checking-test-1.rs @@ -0,0 +1,33 @@ +#![feature(trait_upcasting)] +#![allow(incomplete_features)] + +trait Foo: Bar<i32> + Bar<u32> {} +trait Bar<T> { + fn bar(&self) -> Option<T> { + None + } +} + +fn test_specific(x: &dyn Foo) { + let _ = x as &dyn Bar<i32>; // FIXME: OK, eventually + //~^ ERROR non-primitive cast + //~^^ ERROR the trait bound `&dyn Foo: Bar<i32>` is not satisfied + let _ = x as &dyn Bar<u32>; // FIXME: OK, eventually + //~^ ERROR non-primitive cast + //~^^ ERROR the trait bound `&dyn Foo: Bar<u32>` is not satisfied +} + +fn test_unknown_version(x: &dyn Foo) { + let _ = x as &dyn Bar<_>; // Ambiguous + //~^ ERROR non-primitive cast + //~^^ ERROR the trait bound `&dyn Foo: Bar<_>` is not satisfied +} + +fn test_infer_version(x: &dyn Foo) { + let a = x as &dyn Bar<_>; // FIXME: OK, eventually + //~^ ERROR non-primitive cast + //~^^ ERROR the trait bound `&dyn Foo: Bar<u32>` is not satisfied + let _: Option<u32> = a.bar(); +} + +fn main() {} diff --git a/src/test/ui/traits/trait-upcasting/type-checking-test-1.stderr b/src/test/ui/traits/trait-upcasting/type-checking-test-1.stderr new file mode 100644 index 00000000000..6aaa8a4a904 --- /dev/null +++ b/src/test/ui/traits/trait-upcasting/type-checking-test-1.stderr @@ -0,0 +1,80 @@ +error[E0605]: non-primitive cast: `&dyn Foo` as `&dyn Bar<i32>` + --> $DIR/type-checking-test-1.rs:12:13 + | +LL | let _ = x as &dyn Bar<i32>; // FIXME: OK, eventually + | ^^^^^^^^^^^^^^^^^^ invalid cast + | +help: consider borrowing the value + | +LL | let _ = &x as &dyn Bar<i32>; // FIXME: OK, eventually + | ^ + +error[E0605]: non-primitive cast: `&dyn Foo` as `&dyn Bar<u32>` + --> $DIR/type-checking-test-1.rs:15:13 + | +LL | let _ = x as &dyn Bar<u32>; // FIXME: OK, eventually + | ^^^^^^^^^^^^^^^^^^ invalid cast + | +help: consider borrowing the value + | +LL | let _ = &x as &dyn Bar<u32>; // FIXME: OK, eventually + | ^ + +error[E0277]: the trait bound `&dyn Foo: Bar<i32>` is not satisfied + --> $DIR/type-checking-test-1.rs:12:13 + | +LL | let _ = x as &dyn Bar<i32>; // FIXME: OK, eventually + | ^ the trait `Bar<i32>` is not implemented for `&dyn Foo` + | + = note: required for the cast to the object type `dyn Bar<i32>` + +error[E0277]: the trait bound `&dyn Foo: Bar<u32>` is not satisfied + --> $DIR/type-checking-test-1.rs:15:13 + | +LL | let _ = x as &dyn Bar<u32>; // FIXME: OK, eventually + | ^ the trait `Bar<u32>` is not implemented for `&dyn Foo` + | + = note: required for the cast to the object type `dyn Bar<u32>` + +error[E0605]: non-primitive cast: `&dyn Foo` as `&dyn Bar<_>` + --> $DIR/type-checking-test-1.rs:21:13 + | +LL | let _ = x as &dyn Bar<_>; // Ambiguous + | ^^^^^^^^^^^^^^^^ invalid cast + | +help: consider borrowing the value + | +LL | let _ = &x as &dyn Bar<_>; // Ambiguous + | ^ + +error[E0277]: the trait bound `&dyn Foo: Bar<_>` is not satisfied + --> $DIR/type-checking-test-1.rs:21:13 + | +LL | let _ = x as &dyn Bar<_>; // Ambiguous + | ^ the trait `Bar<_>` is not implemented for `&dyn Foo` + | + = note: required for the cast to the object type `dyn Bar<_>` + +error[E0605]: non-primitive cast: `&dyn Foo` as `&dyn Bar<u32>` + --> $DIR/type-checking-test-1.rs:27:13 + | +LL | let a = x as &dyn Bar<_>; // FIXME: OK, eventually + | ^^^^^^^^^^^^^^^^ invalid cast + | +help: consider borrowing the value + | +LL | let a = &x as &dyn Bar<_>; // FIXME: OK, eventually + | ^ + +error[E0277]: the trait bound `&dyn Foo: Bar<u32>` is not satisfied + --> $DIR/type-checking-test-1.rs:27:13 + | +LL | let a = x as &dyn Bar<_>; // FIXME: OK, eventually + | ^ the trait `Bar<u32>` is not implemented for `&dyn Foo` + | + = note: required for the cast to the object type `dyn Bar<u32>` + +error: aborting due to 8 previous errors + +Some errors have detailed explanations: E0277, E0605. +For more information about an error, try `rustc --explain E0277`. diff --git a/src/test/ui/traits/trait-upcasting/type-checking-test-2.rs b/src/test/ui/traits/trait-upcasting/type-checking-test-2.rs new file mode 100644 index 00000000000..326df74211e --- /dev/null +++ b/src/test/ui/traits/trait-upcasting/type-checking-test-2.rs @@ -0,0 +1,34 @@ +#![feature(trait_upcasting)] +#![allow(incomplete_features)] + +trait Foo<T>: Bar<i32> + Bar<T> {} +trait Bar<T> { + fn bar(&self) -> Option<T> { + None + } +} + +fn test_specific(x: &dyn Foo<i32>) { + let _ = x as &dyn Bar<i32>; // OK +} + +fn test_specific2(x: &dyn Foo<u32>) { + let _ = x as &dyn Bar<i32>; // FIXME: OK, eventually + //~^ ERROR non-primitive cast + //~^^ ERROR the trait bound `&dyn Foo<u32>: Bar<i32>` is not satisfied +} + +fn test_specific3(x: &dyn Foo<i32>) { + let _ = x as &dyn Bar<u32>; // Error + //~^ ERROR non-primitive cast + //~^^ ERROR the trait bound `&dyn Foo<i32>: Bar<u32>` is not satisfied +} + +fn test_infer_arg(x: &dyn Foo<u32>) { + let a = x as &dyn Bar<_>; // Ambiguous + //~^ ERROR non-primitive cast + //~^^ ERROR the trait bound `&dyn Foo<u32>: Bar<_>` is not satisfied + let _ = a.bar(); +} + +fn main() {} diff --git a/src/test/ui/traits/trait-upcasting/type-checking-test-2.stderr b/src/test/ui/traits/trait-upcasting/type-checking-test-2.stderr new file mode 100644 index 00000000000..a38f8a14604 --- /dev/null +++ b/src/test/ui/traits/trait-upcasting/type-checking-test-2.stderr @@ -0,0 +1,61 @@ +error[E0605]: non-primitive cast: `&dyn Foo<u32>` as `&dyn Bar<i32>` + --> $DIR/type-checking-test-2.rs:16:13 + | +LL | let _ = x as &dyn Bar<i32>; // FIXME: OK, eventually + | ^^^^^^^^^^^^^^^^^^ invalid cast + | +help: consider borrowing the value + | +LL | let _ = &x as &dyn Bar<i32>; // FIXME: OK, eventually + | ^ + +error[E0277]: the trait bound `&dyn Foo<u32>: Bar<i32>` is not satisfied + --> $DIR/type-checking-test-2.rs:16:13 + | +LL | let _ = x as &dyn Bar<i32>; // FIXME: OK, eventually + | ^ the trait `Bar<i32>` is not implemented for `&dyn Foo<u32>` + | + = note: required for the cast to the object type `dyn Bar<i32>` + +error[E0605]: non-primitive cast: `&dyn Foo<i32>` as `&dyn Bar<u32>` + --> $DIR/type-checking-test-2.rs:22:13 + | +LL | let _ = x as &dyn Bar<u32>; // Error + | ^^^^^^^^^^^^^^^^^^ invalid cast + | +help: consider borrowing the value + | +LL | let _ = &x as &dyn Bar<u32>; // Error + | ^ + +error[E0277]: the trait bound `&dyn Foo<i32>: Bar<u32>` is not satisfied + --> $DIR/type-checking-test-2.rs:22:13 + | +LL | let _ = x as &dyn Bar<u32>; // Error + | ^ the trait `Bar<u32>` is not implemented for `&dyn Foo<i32>` + | + = note: required for the cast to the object type `dyn Bar<u32>` + +error[E0605]: non-primitive cast: `&dyn Foo<u32>` as `&dyn Bar<_>` + --> $DIR/type-checking-test-2.rs:28:13 + | +LL | let a = x as &dyn Bar<_>; // Ambiguous + | ^^^^^^^^^^^^^^^^ invalid cast + | +help: consider borrowing the value + | +LL | let a = &x as &dyn Bar<_>; // Ambiguous + | ^ + +error[E0277]: the trait bound `&dyn Foo<u32>: Bar<_>` is not satisfied + --> $DIR/type-checking-test-2.rs:28:13 + | +LL | let a = x as &dyn Bar<_>; // Ambiguous + | ^ the trait `Bar<_>` is not implemented for `&dyn Foo<u32>` + | + = note: required for the cast to the object type `dyn Bar<_>` + +error: aborting due to 6 previous errors + +Some errors have detailed explanations: E0277, E0605. +For more information about an error, try `rustc --explain E0277`. diff --git a/src/test/ui/traits/trait-upcasting/type-checking-test-3.rs b/src/test/ui/traits/trait-upcasting/type-checking-test-3.rs new file mode 100644 index 00000000000..49c24e404dc --- /dev/null +++ b/src/test/ui/traits/trait-upcasting/type-checking-test-3.rs @@ -0,0 +1,22 @@ +// ignore-compare-mode-nll +#![feature(trait_upcasting)] +#![allow(incomplete_features)] + +trait Foo<'a>: Bar<'a> {} +trait Bar<'a> {} + +fn test_correct(x: &dyn Foo<'static>) { + let _ = x as &dyn Bar<'static>; +} + +fn test_wrong1<'a>(x: &dyn Foo<'static>, y: &'a u32) { + let _ = x as &dyn Bar<'a>; // Error + //~^ ERROR mismatched types +} + +fn test_wrong2<'a>(x: &dyn Foo<'a>) { + let _ = x as &dyn Bar<'static>; // Error + //~^ ERROR mismatched types +} + +fn main() {} diff --git a/src/test/ui/traits/trait-upcasting/type-checking-test-3.stderr b/src/test/ui/traits/trait-upcasting/type-checking-test-3.stderr new file mode 100644 index 00000000000..593ee0a3430 --- /dev/null +++ b/src/test/ui/traits/trait-upcasting/type-checking-test-3.stderr @@ -0,0 +1,33 @@ +error[E0308]: mismatched types + --> $DIR/type-checking-test-3.rs:13:13 + | +LL | let _ = x as &dyn Bar<'a>; // Error + | ^ lifetime mismatch + | + = note: expected trait object `dyn Bar<'a>` + found trait object `dyn Bar<'static>` +note: the lifetime `'a` as defined on the function body at 12:16... + --> $DIR/type-checking-test-3.rs:12:16 + | +LL | fn test_wrong1<'a>(x: &dyn Foo<'static>, y: &'a u32) { + | ^^ + = note: ...does not necessarily outlive the static lifetime + +error[E0308]: mismatched types + --> $DIR/type-checking-test-3.rs:18:13 + | +LL | let _ = x as &dyn Bar<'static>; // Error + | ^ lifetime mismatch + | + = note: expected trait object `dyn Bar<'static>` + found trait object `dyn Bar<'a>` +note: the lifetime `'a` as defined on the function body at 17:16... + --> $DIR/type-checking-test-3.rs:17:16 + | +LL | fn test_wrong2<'a>(x: &dyn Foo<'a>) { + | ^^ + = note: ...does not necessarily outlive the static lifetime + +error: aborting due to 2 previous errors + +For more information about this error, try `rustc --explain E0308`. diff --git a/src/test/ui/traits/trait-upcasting/type-checking-test-4.rs b/src/test/ui/traits/trait-upcasting/type-checking-test-4.rs new file mode 100644 index 00000000000..9b27fd46f7a --- /dev/null +++ b/src/test/ui/traits/trait-upcasting/type-checking-test-4.rs @@ -0,0 +1,32 @@ +// ignore-compare-mode-nll +#![feature(trait_upcasting)] +#![allow(incomplete_features)] + +trait Foo<'a>: Bar<'a, 'a> {} +trait Bar<'a, 'b> { + fn get_b(&self) -> Option<&'a u32> { + None + } +} + +fn test_correct(x: &dyn Foo<'static>) { + let _ = x as &dyn Bar<'static, 'static>; +} + +fn test_wrong1<'a>(x: &dyn Foo<'static>, y: &'a u32) { + let _ = x as &dyn Bar<'static, 'a>; // Error + //~^ ERROR mismatched types +} + +fn test_wrong2<'a>(x: &dyn Foo<'static>, y: &'a u32) { + let _ = x as &dyn Bar<'a, 'static>; // Error + //~^ ERROR mismatched types +} + +fn test_wrong3<'a>(x: &dyn Foo<'a>) -> Option<&'static u32> { + let y = x as &dyn Bar<'_, '_>; + //~^ ERROR `x` has lifetime `'a` but it needs to satisfy a `'static` lifetime requirement + y.get_b() // ERROR +} + +fn main() {} diff --git a/src/test/ui/traits/trait-upcasting/type-checking-test-4.stderr b/src/test/ui/traits/trait-upcasting/type-checking-test-4.stderr new file mode 100644 index 00000000000..811e524eda7 --- /dev/null +++ b/src/test/ui/traits/trait-upcasting/type-checking-test-4.stderr @@ -0,0 +1,47 @@ +error[E0308]: mismatched types + --> $DIR/type-checking-test-4.rs:17:13 + | +LL | let _ = x as &dyn Bar<'static, 'a>; // Error + | ^ lifetime mismatch + | + = note: expected trait object `dyn Bar<'static, 'a>` + found trait object `dyn Bar<'static, 'static>` +note: the lifetime `'a` as defined on the function body at 16:16... + --> $DIR/type-checking-test-4.rs:16:16 + | +LL | fn test_wrong1<'a>(x: &dyn Foo<'static>, y: &'a u32) { + | ^^ + = note: ...does not necessarily outlive the static lifetime + +error[E0308]: mismatched types + --> $DIR/type-checking-test-4.rs:22:13 + | +LL | let _ = x as &dyn Bar<'a, 'static>; // Error + | ^ lifetime mismatch + | + = note: expected trait object `dyn Bar<'a, 'static>` + found trait object `dyn Bar<'static, 'static>` +note: the lifetime `'a` as defined on the function body at 21:16... + --> $DIR/type-checking-test-4.rs:21:16 + | +LL | fn test_wrong2<'a>(x: &dyn Foo<'static>, y: &'a u32) { + | ^^ + = note: ...does not necessarily outlive the static lifetime + +error[E0759]: `x` has lifetime `'a` but it needs to satisfy a `'static` lifetime requirement + --> $DIR/type-checking-test-4.rs:27:27 + | +LL | fn test_wrong3<'a>(x: &dyn Foo<'a>) -> Option<&'static u32> { + | ------------ this data with lifetime `'a`... +LL | let y = x as &dyn Bar<'_, '_>; + | - ^^ + | | + | ...is captured here... +LL | +LL | y.get_b() // ERROR + | --------- ...and is required to live as long as `'static` here + +error: aborting due to 3 previous errors + +Some errors have detailed explanations: E0308, E0759. +For more information about an error, try `rustc --explain E0308`. |
