Auto merge of #57428 - alexreg:associated_type_bounds, r=nikomatsakis,Centril
Implementation of RFC 2289 (associated_type_bounds) This PR implements the [`asociated_type_bounds` feature](https://github.com/rust-lang/rfcs/blob/master/text/2289-associated-type-bounds.md). Associated type bounds are implemented in: - function/method arguments and return types - structs, enums, unions - associated items in traits - type aliases - type parameter defaults - trait objects - let bindings CC @nikomatsakis @centril
This commit is contained in:
commit
740668dbd9
116 changed files with 4846 additions and 1054 deletions
|
|
@ -2,7 +2,7 @@
|
|||
{ "type": "test", "event": "started", "name": "a" }
|
||||
{ "type": "test", "name": "a", "event": "ok" }
|
||||
{ "type": "test", "event": "started", "name": "b" }
|
||||
{ "type": "test", "name": "b", "event": "failed", "stdout": "thread 'main' panicked at 'assertion failed: false', f.rs:8:5\nnote: Run with `RUST_BACKTRACE=1` environment variable to display a backtrace.\n" }
|
||||
{ "type": "test", "name": "b", "event": "failed", "stdout": "thread 'main' panicked at 'assertion failed: false', f.rs:8:5\nnote: run with `RUST_BACKTRACE=1` environment variable to display a backtrace.\n" }
|
||||
{ "type": "test", "event": "started", "name": "c" }
|
||||
{ "type": "test", "name": "c", "event": "ok" }
|
||||
{ "type": "test", "event": "started", "name": "d" }
|
||||
|
|
|
|||
|
|
@ -1,23 +1,21 @@
|
|||
// ignore-cross-compile
|
||||
|
||||
|
||||
// The general idea of this test is to enumerate all "interesting" expressions and check that
|
||||
// `parse(print(e)) == e` for all `e`. Here's what's interesting, for the purposes of this test:
|
||||
// `parse(print(e)) == e` for all `e`. Here's what's interesting, for the purposes of this test:
|
||||
//
|
||||
// 1. The test focuses on expression nesting, because interactions between different expression
|
||||
// types are harder to test manually than single expression types in isolation.
|
||||
// 1. The test focuses on expression nesting, because interactions between different expression
|
||||
// types are harder to test manually than single expression types in isolation.
|
||||
//
|
||||
// 2. The test only considers expressions of at most two nontrivial nodes. So it will check `x +
|
||||
// x` and `x + (x - x)` but not `(x * x) + (x - x)`. The assumption here is that the correct
|
||||
// handling of an expression might depend on the expression's parent, but doesn't depend on its
|
||||
// siblings or any more distant ancestors.
|
||||
// 2. The test only considers expressions of at most two nontrivial nodes. So it will check `x +
|
||||
// x` and `x + (x - x)` but not `(x * x) + (x - x)`. The assumption here is that the correct
|
||||
// handling of an expression might depend on the expression's parent, but doesn't depend on its
|
||||
// siblings or any more distant ancestors.
|
||||
//
|
||||
// 3. The test only checks certain expression kinds. The assumption is that similar expression
|
||||
// types, such as `if` and `while` or `+` and `-`, will be handled identically in the printer
|
||||
// and parser. So if all combinations of exprs involving `if` work correctly, then combinations
|
||||
// 3. The test only checks certain expression kinds. The assumption is that similar expression
|
||||
// types, such as `if` and `while` or `+` and `-`, will be handled identically in the printer
|
||||
// and parser. So if all combinations of exprs involving `if` work correctly, then combinations
|
||||
// using `while`, `if let`, and so on will likely work as well.
|
||||
|
||||
|
||||
#![feature(rustc_private)]
|
||||
|
||||
extern crate rustc_data_structures;
|
||||
|
|
@ -155,9 +153,9 @@ fn iter_exprs(depth: usize, f: &mut dyn FnMut(P<Expr>)) {
|
|||
}
|
||||
|
||||
|
||||
// Folders for manipulating the placement of `Paren` nodes. See below for why this is needed.
|
||||
// Folders for manipulating the placement of `Paren` nodes. See below for why this is needed.
|
||||
|
||||
/// MutVisitor that removes all `ExprKind::Paren` nodes.
|
||||
/// `MutVisitor` that removes all `ExprKind::Paren` nodes.
|
||||
struct RemoveParens;
|
||||
|
||||
impl MutVisitor for RemoveParens {
|
||||
|
|
@ -171,7 +169,7 @@ impl MutVisitor for RemoveParens {
|
|||
}
|
||||
|
||||
|
||||
/// MutVisitor that inserts `ExprKind::Paren` nodes around every `Expr`.
|
||||
/// `MutVisitor` that inserts `ExprKind::Paren` nodes around every `Expr`.
|
||||
struct AddParens;
|
||||
|
||||
impl MutVisitor for AddParens {
|
||||
|
|
@ -205,8 +203,8 @@ fn run() {
|
|||
|
||||
// We want to know if `parsed` is structurally identical to `e`, ignoring trivial
|
||||
// differences like placement of `Paren`s or the exact ranges of node spans.
|
||||
// Unfortunately, there is no easy way to make this comparison. Instead, we add `Paren`s
|
||||
// everywhere we can, then pretty-print. This should give an unambiguous representation of
|
||||
// Unfortunately, there is no easy way to make this comparison. Instead, we add `Paren`s
|
||||
// everywhere we can, then pretty-print. This should give an unambiguous representation of
|
||||
// each `Expr`, and it bypasses nearly all of the parenthesization logic, so we aren't
|
||||
// relying on the correctness of the very thing we're testing.
|
||||
RemoveParens.visit_expr(&mut e);
|
||||
|
|
|
|||
|
|
@ -18,5 +18,5 @@ fn record_type<Id: AstId>(i: Id::Untyped) -> u8 {
|
|||
}
|
||||
|
||||
pub fn main() {
|
||||
assert_eq!(record_type::<u32>(3), 42);
|
||||
assert_eq!(record_type::<u32>(3), 42);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -8,7 +8,7 @@ fn check_for_no_backtrace(test: std::process::Output) {
|
|||
let mut it = err.lines();
|
||||
|
||||
assert_eq!(it.next().map(|l| l.starts_with("thread '<unnamed>' panicked at")), Some(true));
|
||||
assert_eq!(it.next(), Some("note: Run with `RUST_BACKTRACE=1` \
|
||||
assert_eq!(it.next(), Some("note: run with `RUST_BACKTRACE=1` \
|
||||
environment variable to display a backtrace."));
|
||||
assert_eq!(it.next().map(|l| l.starts_with("thread 'main' panicked at")), Some(true));
|
||||
assert_eq!(it.next(), None);
|
||||
|
|
|
|||
|
|
@ -1,14 +1,15 @@
|
|||
// run-pass
|
||||
|
||||
#![allow(unused_assignments)]
|
||||
|
||||
// Test that duplicate auto trait bounds in trait objects don't create new types.
|
||||
#[allow(unused_assignments)]
|
||||
|
||||
use std::marker::Send as SendAlias;
|
||||
|
||||
// A dummy trait for the non-auto trait.
|
||||
trait Trait {}
|
||||
|
||||
// A dummy struct to implement Trait, Send, and .
|
||||
// A dummy struct to implement `Trait` and `Send`.
|
||||
struct Struct;
|
||||
|
||||
impl Trait for Struct {}
|
||||
|
|
@ -23,12 +24,12 @@ impl dyn Trait + Send + Send {
|
|||
}
|
||||
|
||||
fn main() {
|
||||
// 1. Moving into a variable with more Sends and back.
|
||||
// 1. Moving into a variable with more `Send`s and back.
|
||||
let mut dyn_trait_send = Box::new(Struct) as Box<dyn Trait + Send>;
|
||||
let dyn_trait_send_send: Box<dyn Trait + Send + Send> = dyn_trait_send;
|
||||
dyn_trait_send = dyn_trait_send_send;
|
||||
|
||||
// 2. Calling methods with different number of Sends.
|
||||
// 2. Calling methods with different number of `Send`s.
|
||||
let dyn_trait_send = Box::new(Struct) as Box<dyn Trait + Send>;
|
||||
takes_dyn_trait_send_send(dyn_trait_send);
|
||||
|
||||
|
|
|
|||
|
|
@ -27,7 +27,7 @@ stderr:
|
|||
stderr 1
|
||||
stderr 2
|
||||
thread 'main' panicked at 'oh no', $DIR/failed-doctest-output.rs:7:1
|
||||
note: Run with `RUST_BACKTRACE=1` environment variable to display a backtrace.
|
||||
note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace.
|
||||
|
||||
|
||||
|
||||
|
|
|
|||
177
src/test/ui/associated-type-bounds/auxiliary/fn-aux.rs
Normal file
177
src/test/ui/associated-type-bounds/auxiliary/fn-aux.rs
Normal file
|
|
@ -0,0 +1,177 @@
|
|||
// Traits:
|
||||
|
||||
pub trait Alpha {
|
||||
fn alpha(self) -> usize;
|
||||
}
|
||||
|
||||
pub trait Beta {
|
||||
type Gamma;
|
||||
fn gamma(self) -> Self::Gamma;
|
||||
}
|
||||
|
||||
pub trait Delta {
|
||||
fn delta(self) -> usize;
|
||||
}
|
||||
|
||||
pub trait Epsilon<'a> {
|
||||
type Zeta;
|
||||
fn zeta(&'a self) -> Self::Zeta;
|
||||
|
||||
fn epsilon(&'a self) -> usize;
|
||||
}
|
||||
|
||||
pub trait Eta {
|
||||
fn eta(self) -> usize;
|
||||
}
|
||||
|
||||
// Assertions:
|
||||
|
||||
pub fn assert_alpha<T: Alpha>(x: T) -> usize { x.alpha() }
|
||||
pub fn assert_static<T: 'static>(_: T) -> usize { 24 }
|
||||
pub fn assert_delta<T: Delta>(x: T) -> usize { x.delta() }
|
||||
pub fn assert_epsilon_specific<'a, T: 'a + Epsilon<'a>>(x: &'a T) -> usize { x.epsilon() }
|
||||
pub fn assert_epsilon_forall<T: for<'a> Epsilon<'a>>() {}
|
||||
pub fn assert_forall_epsilon_zeta_satisfies_eta<T>(x: T) -> usize
|
||||
where
|
||||
T: for<'a> Epsilon<'a>,
|
||||
for<'a> <T as Epsilon<'a>>::Zeta: Eta,
|
||||
{
|
||||
x.epsilon() + x.zeta().eta()
|
||||
}
|
||||
|
||||
// Implementations and types:
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
pub struct BetaType;
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
pub struct GammaType;
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
pub struct ZetaType;
|
||||
|
||||
impl Beta for BetaType {
|
||||
type Gamma = GammaType;
|
||||
fn gamma(self) -> Self::Gamma { GammaType }
|
||||
}
|
||||
|
||||
impl<'a> Beta for &'a BetaType {
|
||||
type Gamma = GammaType;
|
||||
fn gamma(self) -> Self::Gamma { GammaType }
|
||||
}
|
||||
|
||||
impl Beta for GammaType {
|
||||
type Gamma = Self;
|
||||
fn gamma(self) -> Self::Gamma { self }
|
||||
}
|
||||
|
||||
impl Alpha for GammaType {
|
||||
fn alpha(self) -> usize { 42 }
|
||||
}
|
||||
|
||||
impl Delta for GammaType {
|
||||
fn delta(self) -> usize { 1337 }
|
||||
}
|
||||
|
||||
impl<'a> Epsilon<'a> for GammaType {
|
||||
type Zeta = ZetaType;
|
||||
fn zeta(&'a self) -> Self::Zeta { ZetaType }
|
||||
|
||||
fn epsilon(&'a self) -> usize { 7331 }
|
||||
}
|
||||
|
||||
impl Eta for ZetaType {
|
||||
fn eta(self) -> usize { 7 }
|
||||
}
|
||||
|
||||
// Desugared forms to check against:
|
||||
|
||||
pub fn desugared_bound<B>(beta: B) -> usize
|
||||
where
|
||||
B: Beta,
|
||||
B::Gamma: Alpha
|
||||
{
|
||||
let gamma: B::Gamma = beta.gamma();
|
||||
assert_alpha::<B::Gamma>(gamma)
|
||||
}
|
||||
|
||||
pub fn desugared_bound_region<B>(beta: B) -> usize
|
||||
where
|
||||
B: Beta,
|
||||
B::Gamma: 'static,
|
||||
{
|
||||
assert_static::<B::Gamma>(beta.gamma())
|
||||
}
|
||||
|
||||
pub fn desugared_bound_multi<B>(beta: B) -> usize
|
||||
where
|
||||
B: Copy + Beta,
|
||||
B::Gamma: Alpha + 'static + Delta,
|
||||
{
|
||||
assert_alpha::<B::Gamma>(beta.gamma()) +
|
||||
assert_static::<B::Gamma>(beta.gamma()) +
|
||||
assert_delta::<B::Gamma>(beta.gamma())
|
||||
}
|
||||
|
||||
pub fn desugared_bound_region_specific<'a, B>(gamma: &'a B::Gamma) -> usize
|
||||
where
|
||||
B: Beta,
|
||||
B::Gamma: 'a + Epsilon<'a>,
|
||||
{
|
||||
assert_epsilon_specific::<B::Gamma>(gamma)
|
||||
}
|
||||
|
||||
pub fn desugared_bound_region_forall<B>(beta: B) -> usize
|
||||
where
|
||||
B: Beta,
|
||||
B::Gamma: Copy + for<'a> Epsilon<'a>,
|
||||
{
|
||||
assert_epsilon_forall::<B::Gamma>();
|
||||
let g1: B::Gamma = beta.gamma();
|
||||
let g2: B::Gamma = g1;
|
||||
assert_epsilon_specific::<B::Gamma>(&g1) +
|
||||
assert_epsilon_specific::<B::Gamma>(&g2)
|
||||
}
|
||||
|
||||
pub fn desugared_bound_region_forall2<B>(beta: B) -> usize
|
||||
where
|
||||
B: Beta,
|
||||
B::Gamma: Copy + for<'a> Epsilon<'a>,
|
||||
for<'a> <B::Gamma as Epsilon<'a>>::Zeta: Eta,
|
||||
{
|
||||
let gamma = beta.gamma();
|
||||
assert_forall_epsilon_zeta_satisfies_eta::<B::Gamma>(gamma)
|
||||
}
|
||||
|
||||
pub fn desugared_contraint_region_forall<B>(beta: B) -> usize
|
||||
where
|
||||
for<'a> &'a B: Beta,
|
||||
for<'a> <&'a B as Beta>::Gamma: Alpha,
|
||||
{
|
||||
let g1 = beta.gamma();
|
||||
let g2 = beta.gamma();
|
||||
assert_alpha(g1) + assert_alpha(g2)
|
||||
}
|
||||
|
||||
pub fn desugared_bound_nested<B>(beta: B) -> usize
|
||||
where
|
||||
B: Beta,
|
||||
B::Gamma: Copy + Alpha + Beta,
|
||||
<B::Gamma as Beta>::Gamma: Delta,
|
||||
{
|
||||
let go = beta.gamma();
|
||||
let gi = go.gamma();
|
||||
go.alpha() + gi.delta()
|
||||
}
|
||||
|
||||
pub fn desugared() {
|
||||
let beta = BetaType;
|
||||
let gamma = beta.gamma();
|
||||
|
||||
assert_eq!(42, desugared_bound(beta));
|
||||
assert_eq!(24, desugared_bound_region(beta));
|
||||
assert_eq!(42 + 24 + 1337, desugared_bound_multi(beta));
|
||||
assert_eq!(7331, desugared_bound_region_specific::<BetaType>(&gamma));
|
||||
assert_eq!(7331 * 2, desugared_bound_region_forall(beta));
|
||||
assert_eq!(42 + 1337, desugared_bound_nested(beta));
|
||||
}
|
||||
182
src/test/ui/associated-type-bounds/auxiliary/fn-dyn-aux.rs
Normal file
182
src/test/ui/associated-type-bounds/auxiliary/fn-dyn-aux.rs
Normal file
|
|
@ -0,0 +1,182 @@
|
|||
// Traits:
|
||||
|
||||
pub trait Alpha {
|
||||
fn alpha(self) -> usize;
|
||||
}
|
||||
|
||||
pub trait Beta {
|
||||
type Gamma;
|
||||
fn gamma(&self) -> Self::Gamma;
|
||||
}
|
||||
|
||||
pub trait Delta {
|
||||
fn delta(self) -> usize;
|
||||
}
|
||||
|
||||
pub trait Epsilon<'a> {
|
||||
type Zeta;
|
||||
fn zeta(&'a self) -> Self::Zeta;
|
||||
|
||||
fn epsilon(&'a self) -> usize;
|
||||
}
|
||||
|
||||
pub trait Eta {
|
||||
fn eta(self) -> usize;
|
||||
}
|
||||
|
||||
// Assertions:
|
||||
|
||||
pub fn assert_alpha<T: Alpha>(x: T) -> usize { x.alpha() }
|
||||
pub fn assert_static<T: 'static>(_: T) -> usize { 24 }
|
||||
pub fn assert_delta<T: Delta>(x: T) -> usize { x.delta() }
|
||||
pub fn assert_epsilon_specific<'a, T: 'a + Epsilon<'a>>(x: &'a T) -> usize { x.epsilon() }
|
||||
pub fn assert_epsilon_forall<T: for<'a> Epsilon<'a>>() {}
|
||||
pub fn assert_forall_epsilon_zeta_satisfies_eta<T>(x: T) -> usize
|
||||
where
|
||||
T: for<'a> Epsilon<'a>,
|
||||
for<'a> <T as Epsilon<'a>>::Zeta: Eta,
|
||||
{
|
||||
x.epsilon() + x.zeta().eta()
|
||||
}
|
||||
|
||||
// Implementations and types:
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
pub struct BetaType;
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
pub struct GammaType;
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
pub struct ZetaType;
|
||||
|
||||
impl<T> Beta for &(dyn Beta<Gamma = T> + Send) {
|
||||
type Gamma = T;
|
||||
fn gamma(&self) -> Self::Gamma { (*self).gamma() }
|
||||
}
|
||||
|
||||
impl Beta for BetaType {
|
||||
type Gamma = GammaType;
|
||||
fn gamma(&self) -> Self::Gamma { GammaType }
|
||||
}
|
||||
|
||||
impl<'a> Beta for &'a BetaType {
|
||||
type Gamma = GammaType;
|
||||
fn gamma(&self) -> Self::Gamma { GammaType }
|
||||
}
|
||||
|
||||
impl Beta for GammaType {
|
||||
type Gamma = Self;
|
||||
fn gamma(&self) -> Self::Gamma { Self }
|
||||
}
|
||||
|
||||
impl Alpha for GammaType {
|
||||
fn alpha(self) -> usize { 42 }
|
||||
}
|
||||
|
||||
impl Delta for GammaType {
|
||||
fn delta(self) -> usize { 1337 }
|
||||
}
|
||||
|
||||
impl<'a> Epsilon<'a> for GammaType {
|
||||
type Zeta = ZetaType;
|
||||
fn zeta(&'a self) -> Self::Zeta { ZetaType }
|
||||
|
||||
fn epsilon(&'a self) -> usize { 7331 }
|
||||
}
|
||||
|
||||
impl Eta for ZetaType {
|
||||
fn eta(self) -> usize { 7 }
|
||||
}
|
||||
|
||||
// Desugared forms to check against:
|
||||
|
||||
pub fn desugared_bound<B: ?Sized>(beta: &B) -> usize
|
||||
where
|
||||
B: Beta,
|
||||
B::Gamma: Alpha
|
||||
{
|
||||
let gamma: B::Gamma = beta.gamma();
|
||||
assert_alpha::<B::Gamma>(gamma)
|
||||
}
|
||||
|
||||
pub fn desugared_bound_region<B: ?Sized>(beta: &B) -> usize
|
||||
where
|
||||
B: Beta,
|
||||
B::Gamma: 'static,
|
||||
{
|
||||
assert_static::<B::Gamma>(beta.gamma())
|
||||
}
|
||||
|
||||
pub fn desugared_bound_multi<B: ?Sized>(beta: B) -> usize
|
||||
where
|
||||
B: Copy + Beta,
|
||||
B::Gamma: Alpha + 'static + Delta,
|
||||
{
|
||||
assert_alpha::<B::Gamma>(beta.gamma()) +
|
||||
assert_static::<B::Gamma>(beta.gamma()) +
|
||||
assert_delta::<B::Gamma>(beta.gamma())
|
||||
}
|
||||
|
||||
pub fn desugared_bound_region_specific<'a, B: ?Sized>(gamma: &'a B::Gamma) -> usize
|
||||
where
|
||||
B: Beta,
|
||||
B::Gamma: 'a + Epsilon<'a>,
|
||||
{
|
||||
assert_epsilon_specific::<B::Gamma>(gamma)
|
||||
}
|
||||
|
||||
pub fn desugared_bound_region_forall<B: ?Sized>(beta: &B) -> usize
|
||||
where
|
||||
B: Beta,
|
||||
B::Gamma: Copy + for<'a> Epsilon<'a>,
|
||||
{
|
||||
assert_epsilon_forall::<B::Gamma>();
|
||||
let g1: B::Gamma = beta.gamma();
|
||||
let g2: B::Gamma = g1;
|
||||
assert_epsilon_specific::<B::Gamma>(&g1) +
|
||||
assert_epsilon_specific::<B::Gamma>(&g2)
|
||||
}
|
||||
|
||||
pub fn desugared_bound_region_forall2<B: ?Sized>(beta: &B) -> usize
|
||||
where
|
||||
B: Beta,
|
||||
B::Gamma: Copy + for<'a> Epsilon<'a>,
|
||||
for<'a> <B::Gamma as Epsilon<'a>>::Zeta: Eta,
|
||||
{
|
||||
let gamma = beta.gamma();
|
||||
assert_forall_epsilon_zeta_satisfies_eta::<B::Gamma>(gamma)
|
||||
}
|
||||
|
||||
pub fn desugared_contraint_region_forall<B: ?Sized>(beta: &B) -> usize
|
||||
where
|
||||
for<'a> &'a B: Beta,
|
||||
for<'a> <&'a B as Beta>::Gamma: Alpha,
|
||||
{
|
||||
let g1 = beta.gamma();
|
||||
let g2 = beta.gamma();
|
||||
assert_alpha(g1) + assert_alpha(g2)
|
||||
}
|
||||
|
||||
pub fn desugared_bound_nested<B: ?Sized>(beta: &B) -> usize
|
||||
where
|
||||
B: Beta,
|
||||
B::Gamma: Copy + Alpha + Beta,
|
||||
<B::Gamma as Beta>::Gamma: Delta,
|
||||
{
|
||||
let go = beta.gamma();
|
||||
let gi = go.gamma();
|
||||
go.alpha() + gi.delta()
|
||||
}
|
||||
|
||||
pub fn desugared() {
|
||||
let beta = BetaType;
|
||||
let gamma = beta.gamma();
|
||||
|
||||
assert_eq!(42, desugared_bound(&beta));
|
||||
assert_eq!(24, desugared_bound_region(&beta));
|
||||
assert_eq!(42 + 24 + 1337, desugared_bound_multi(beta));
|
||||
assert_eq!(7331, desugared_bound_region_specific::<BetaType>(&gamma));
|
||||
assert_eq!(7331 * 2, desugared_bound_region_forall(&beta));
|
||||
assert_eq!(42 + 1337, desugared_bound_nested(&beta));
|
||||
}
|
||||
|
|
@ -0,0 +1,60 @@
|
|||
// compile-fail
|
||||
// ignore-tidy-linelength
|
||||
|
||||
// NOTE: rustc cannot currently handle bounds of the form `for<'a> <Foo as Bar<'a>>::Assoc: Baz`.
|
||||
// This should hopefully be fixed with Chalk.
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
use std::fmt::Debug;
|
||||
use std::iter::Once;
|
||||
|
||||
trait Lam<Binder> { type App; }
|
||||
|
||||
#[derive(Clone)]
|
||||
struct L1;
|
||||
impl<'a> Lam<&'a u8> for L1 { type App = u8; }
|
||||
|
||||
#[derive(Clone)]
|
||||
struct L2;
|
||||
impl<'a, 'b> Lam<&'a &'b u8> for L2 { type App = u8; }
|
||||
|
||||
trait Case1 {
|
||||
type C: Clone + Iterator<Item:
|
||||
Send + Iterator<Item:
|
||||
for<'a> Lam<&'a u8, App:
|
||||
Debug
|
||||
>
|
||||
> + Sync>;
|
||||
}
|
||||
|
||||
pub struct S1;
|
||||
impl Case1 for S1 {
|
||||
//~^ ERROR `<L1 as Lam<&'a u8>>::App` doesn't implement `std::fmt::Debug` [E0277]
|
||||
type C = Once<Once<L1>>;
|
||||
}
|
||||
|
||||
fn assume_case1<T: Case1>() {
|
||||
//~^ ERROR `<_ as Lam<&'a u8>>::App` doesn't implement `std::fmt::Debug` [E0277]
|
||||
//~| ERROR `<<T as Case1>::C as std::iter::Iterator>::Item` is not an iterator [E0277]
|
||||
//~| ERROR `<<T as Case1>::C as std::iter::Iterator>::Item` cannot be sent between threads safely [E0277]
|
||||
//~| ERROR `<<T as Case1>::C as std::iter::Iterator>::Item` cannot be shared between threads safely [E0277]
|
||||
fn assert_a<_0, A>() where A: Iterator<Item = _0>, _0: Debug {}
|
||||
assert_a::<_, T::A>();
|
||||
|
||||
fn assert_b<_0, B>() where B: Iterator<Item = _0>, _0: 'static {}
|
||||
assert_b::<_, T::B>();
|
||||
|
||||
fn assert_c<_0, _1, _2, C>()
|
||||
where
|
||||
C: Clone + Iterator<Item = _2>,
|
||||
_2: Send + Iterator<Item = _1>,
|
||||
_1: for<'a> Lam<&'a u8, App = _0>,
|
||||
_0: Debug,
|
||||
{}
|
||||
assert_c::<_, _, _, T::C>();
|
||||
}
|
||||
|
||||
fn main() {
|
||||
assume_case1(S1);
|
||||
}
|
||||
|
|
@ -0,0 +1,85 @@
|
|||
error[E0277]: `<L1 as Lam<&'a u8>>::App` doesn't implement `std::fmt::Debug`
|
||||
--> $DIR/bad-bounds-on-assoc-in-trait.rs:32:6
|
||||
|
|
||||
LL | impl Case1 for S1 {
|
||||
| ^^^^^ `<L1 as Lam<&'a u8>>::App` cannot be formatted using `{:?}` because it doesn't implement `std::fmt::Debug`
|
||||
|
|
||||
= help: the trait `for<'a> std::fmt::Debug` is not implemented for `<L1 as Lam<&'a u8>>::App`
|
||||
|
||||
error[E0277]: `<<T as Case1>::C as std::iter::Iterator>::Item` is not an iterator
|
||||
--> $DIR/bad-bounds-on-assoc-in-trait.rs:37:1
|
||||
|
|
||||
LL | / fn assume_case1<T: Case1>() {
|
||||
LL | |
|
||||
LL | |
|
||||
LL | |
|
||||
... |
|
||||
LL | | assert_c::<_, _, _, T::C>();
|
||||
LL | | }
|
||||
| |_^ `<<T as Case1>::C as std::iter::Iterator>::Item` is not an iterator
|
||||
|
|
||||
= help: the trait `std::iter::Iterator` is not implemented for `<<T as Case1>::C as std::iter::Iterator>::Item`
|
||||
= help: consider adding a `where <<T as Case1>::C as std::iter::Iterator>::Item: std::iter::Iterator` bound
|
||||
|
||||
error[E0277]: `<<T as Case1>::C as std::iter::Iterator>::Item` cannot be sent between threads safely
|
||||
--> $DIR/bad-bounds-on-assoc-in-trait.rs:37:1
|
||||
|
|
||||
LL | / fn assume_case1<T: Case1>() {
|
||||
LL | |
|
||||
LL | |
|
||||
LL | |
|
||||
... |
|
||||
LL | | assert_c::<_, _, _, T::C>();
|
||||
LL | | }
|
||||
| |_^ `<<T as Case1>::C as std::iter::Iterator>::Item` cannot be sent between threads safely
|
||||
|
|
||||
= help: the trait `std::marker::Send` is not implemented for `<<T as Case1>::C as std::iter::Iterator>::Item`
|
||||
= help: consider adding a `where <<T as Case1>::C as std::iter::Iterator>::Item: std::marker::Send` bound
|
||||
note: required by `Case1`
|
||||
--> $DIR/bad-bounds-on-assoc-in-trait.rs:22:1
|
||||
|
|
||||
LL | trait Case1 {
|
||||
| ^^^^^^^^^^^
|
||||
|
||||
error[E0277]: `<<T as Case1>::C as std::iter::Iterator>::Item` cannot be shared between threads safely
|
||||
--> $DIR/bad-bounds-on-assoc-in-trait.rs:37:1
|
||||
|
|
||||
LL | / fn assume_case1<T: Case1>() {
|
||||
LL | |
|
||||
LL | |
|
||||
LL | |
|
||||
... |
|
||||
LL | | assert_c::<_, _, _, T::C>();
|
||||
LL | | }
|
||||
| |_^ `<<T as Case1>::C as std::iter::Iterator>::Item` cannot be shared between threads safely
|
||||
|
|
||||
= help: the trait `std::marker::Sync` is not implemented for `<<T as Case1>::C as std::iter::Iterator>::Item`
|
||||
= help: consider adding a `where <<T as Case1>::C as std::iter::Iterator>::Item: std::marker::Sync` bound
|
||||
note: required by `Case1`
|
||||
--> $DIR/bad-bounds-on-assoc-in-trait.rs:22:1
|
||||
|
|
||||
LL | trait Case1 {
|
||||
| ^^^^^^^^^^^
|
||||
|
||||
error[E0277]: `<_ as Lam<&'a u8>>::App` doesn't implement `std::fmt::Debug`
|
||||
--> $DIR/bad-bounds-on-assoc-in-trait.rs:37:1
|
||||
|
|
||||
LL | / fn assume_case1<T: Case1>() {
|
||||
LL | |
|
||||
LL | |
|
||||
LL | |
|
||||
... |
|
||||
LL | | assert_c::<_, _, _, T::C>();
|
||||
LL | | }
|
||||
| |_^ `<_ as Lam<&'a u8>>::App` cannot be formatted using `{:?}` because it doesn't implement `std::fmt::Debug`
|
||||
|
|
||||
= help: the trait `for<'a> std::fmt::Debug` is not implemented for `<_ as Lam<&'a u8>>::App`
|
||||
note: required by `Case1`
|
||||
--> $DIR/bad-bounds-on-assoc-in-trait.rs:22:1
|
||||
|
|
||||
LL | trait Case1 {
|
||||
| ^^^^^^^^^^^
|
||||
|
||||
error: aborting due to 5 previous errors
|
||||
|
||||
For more information about this error, try `rustc --explain E0277`.
|
||||
|
|
@ -0,0 +1,51 @@
|
|||
// run-pass
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
use std::fmt::Debug;
|
||||
use std::iter::Empty;
|
||||
use std::ops::Range;
|
||||
|
||||
trait Lam<Binder> { type App; }
|
||||
|
||||
#[derive(Clone)]
|
||||
struct L1;
|
||||
impl<'a> Lam<&'a u8> for L1 { type App = u8; }
|
||||
|
||||
#[derive(Clone)]
|
||||
struct L2;
|
||||
impl<'a, 'b> Lam<&'a &'b u8> for L2 { type App = u8; }
|
||||
|
||||
trait Case1 {
|
||||
type A: Iterator<Item: Debug>;
|
||||
|
||||
type B: Iterator<Item: 'static>;
|
||||
}
|
||||
|
||||
pub struct S1;
|
||||
impl Case1 for S1 {
|
||||
type A = Empty<String>;
|
||||
type B = Range<u16>;
|
||||
}
|
||||
|
||||
// Ensure we don't have existential desugaring:
|
||||
|
||||
pub trait Foo { type Out: Baz<Assoc: Default>; }
|
||||
pub trait Baz { type Assoc; }
|
||||
|
||||
#[derive(Default)]
|
||||
struct S2;
|
||||
#[derive(Default)]
|
||||
struct S3;
|
||||
struct S4;
|
||||
struct S5;
|
||||
struct S6;
|
||||
struct S7;
|
||||
|
||||
impl Foo for S6 { type Out = S4; }
|
||||
impl Foo for S7 { type Out = S5; }
|
||||
|
||||
impl Baz for S4 { type Assoc = S2; }
|
||||
impl Baz for S5 { type Assoc = S3; }
|
||||
|
||||
fn main() {}
|
||||
161
src/test/ui/associated-type-bounds/duplicate.rs
Normal file
161
src/test/ui/associated-type-bounds/duplicate.rs
Normal file
|
|
@ -0,0 +1,161 @@
|
|||
// compile-fail
|
||||
// ignore-tidy-linelength
|
||||
// error-pattern:could not find defining uses
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
#![feature(existential_type)]
|
||||
#![feature(impl_trait_in_bindings)]
|
||||
#![feature(untagged_unions)]
|
||||
|
||||
use std::iter;
|
||||
|
||||
struct SI1<T: Iterator<Item: Copy, Item: Send>> { f: T }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
struct SI2<T: Iterator<Item: Copy, Item: Copy>> { f: T }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
struct SI3<T: Iterator<Item: 'static, Item: 'static>> { f: T }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
struct SW1<T> where T: Iterator<Item: Copy, Item: Send> { f: T }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
struct SW2<T> where T: Iterator<Item: Copy, Item: Copy> { f: T }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
struct SW3<T> where T: Iterator<Item: 'static, Item: 'static> { f: T }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
|
||||
enum EI1<T: Iterator<Item: Copy, Item: Send>> { V(T) }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
enum EI2<T: Iterator<Item: Copy, Item: Copy>> { V(T) }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
enum EI3<T: Iterator<Item: 'static, Item: 'static>> { V(T) }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
enum EW1<T> where T: Iterator<Item: Copy, Item: Send> { V(T) }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
enum EW2<T> where T: Iterator<Item: Copy, Item: Copy> { V(T) }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
enum EW3<T> where T: Iterator<Item: 'static, Item: 'static> { V(T) }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
|
||||
union UI1<T: Iterator<Item: Copy, Item: Send>> { f: T }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
union UI2<T: Iterator<Item: Copy, Item: Copy>> { f: T }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
union UI3<T: Iterator<Item: 'static, Item: 'static>> { f: T }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
union UW1<T> where T: Iterator<Item: Copy, Item: Send> { f: T }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
union UW2<T> where T: Iterator<Item: Copy, Item: Copy> { f: T }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
union UW3<T> where T: Iterator<Item: 'static, Item: 'static> { f: T }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
|
||||
fn FI1<T: Iterator<Item: Copy, Item: Send>>() {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
fn FI2<T: Iterator<Item: Copy, Item: Copy>>() {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
fn FI3<T: Iterator<Item: 'static, Item: 'static>>() {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
fn FW1<T>() where T: Iterator<Item: Copy, Item: Send> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
fn FW2<T>() where T: Iterator<Item: Copy, Item: Copy> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
fn FW3<T>() where T: Iterator<Item: 'static, Item: 'static> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
|
||||
fn FRPIT1() -> impl Iterator<Item: Copy, Item: Send> { iter::empty() }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
fn FRPIT2() -> impl Iterator<Item: Copy, Item: Copy> { iter::empty() }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
fn FRPIT3() -> impl Iterator<Item: 'static, Item: 'static> { iter::empty() }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
fn FAPIT1(_: impl Iterator<Item: Copy, Item: Send>) {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
fn FAPIT2(_: impl Iterator<Item: Copy, Item: Copy>) {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
fn FAPIT3(_: impl Iterator<Item: 'static, Item: 'static>) {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
|
||||
const CIT1: impl Iterator<Item: Copy, Item: Send> = iter::empty();
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
const CIT2: impl Iterator<Item: Copy, Item: Copy> = iter::empty();
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
const CIT3: impl Iterator<Item: 'static, Item: 'static> = iter::empty();
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
static SIT1: impl Iterator<Item: Copy, Item: Send> = iter::empty();
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
static SIT2: impl Iterator<Item: Copy, Item: Copy> = iter::empty();
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
static SIT3: impl Iterator<Item: 'static, Item: 'static> = iter::empty();
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
|
||||
fn lit1() { let _: impl Iterator<Item: Copy, Item: Send> = iter::empty(); }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
fn lit2() { let _: impl Iterator<Item: Copy, Item: Copy> = iter::empty(); }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
fn lit3() { let _: impl Iterator<Item: 'static, Item: 'static> = iter::empty(); }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
|
||||
type TAI1<T: Iterator<Item: Copy, Item: Send>> = T;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
type TAI2<T: Iterator<Item: Copy, Item: Copy>> = T;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
type TAI3<T: Iterator<Item: 'static, Item: 'static>> = T;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
type TAW1<T> where T: Iterator<Item: Copy, Item: Send> = T;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
type TAW2<T> where T: Iterator<Item: Copy, Item: Copy> = T;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
type TAW3<T> where T: Iterator<Item: 'static, Item: 'static> = T;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
|
||||
existential type ETAI1<T: Iterator<Item: Copy, Item: Send>>: Copy;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
existential type ETAI2<T: Iterator<Item: Copy, Item: Copy>>: Copy;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
existential type ETAI3<T: Iterator<Item: 'static, Item: 'static>>: Copy;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
existential type ETAI4: Iterator<Item: Copy, Item: Send>;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
existential type ETAI5: Iterator<Item: Copy, Item: Copy>;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
existential type ETAI6: Iterator<Item: 'static, Item: 'static>;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
|
||||
trait TRI1<T: Iterator<Item: Copy, Item: Send>> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
trait TRI2<T: Iterator<Item: Copy, Item: Copy>> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
trait TRI3<T: Iterator<Item: 'static, Item: 'static>> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
trait TRS1: Iterator<Item: Copy, Item: Send> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
trait TRS2: Iterator<Item: Copy, Item: Copy> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
trait TRS3: Iterator<Item: 'static, Item: 'static> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
trait TRW1<T> where T: Iterator<Item: Copy, Item: Send> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
trait TRW2<T> where T: Iterator<Item: Copy, Item: Copy> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
trait TRW3<T> where T: Iterator<Item: 'static, Item: 'static> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
trait TRSW1 where Self: Iterator<Item: Copy, Item: Send> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
trait TRSW2 where Self: Iterator<Item: Copy, Item: Copy> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
trait TRSW3 where Self: Iterator<Item: 'static, Item: 'static> {}
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
trait TRA1 { type A: Iterator<Item: Copy, Item: Send>; }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
trait TRA2 { type A: Iterator<Item: Copy, Item: Copy>; }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
trait TRA3 { type A: Iterator<Item: 'static, Item: 'static>; }
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
|
||||
type TADyn1 = dyn Iterator<Item: Copy, Item: Send>;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
type TADyn2 = Box<dyn Iterator<Item: Copy, Item: Copy>>;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
type TADyn3 = dyn Iterator<Item: 'static, Item: 'static>;
|
||||
//~^ the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified [E0719]
|
||||
|
||||
fn main() {}
|
||||
632
src/test/ui/associated-type-bounds/duplicate.stderr
Normal file
632
src/test/ui/associated-type-bounds/duplicate.stderr
Normal file
|
|
@ -0,0 +1,632 @@
|
|||
warning: the feature `impl_trait_in_bindings` is incomplete and may cause the compiler to crash
|
||||
--> $DIR/duplicate.rs:7:12
|
||||
|
|
||||
LL | #![feature(impl_trait_in_bindings)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:12:36
|
||||
|
|
||||
LL | struct SI1<T: Iterator<Item: Copy, Item: Send>> { f: T }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:14:36
|
||||
|
|
||||
LL | struct SI2<T: Iterator<Item: Copy, Item: Copy>> { f: T }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:16:39
|
||||
|
|
||||
LL | struct SI3<T: Iterator<Item: 'static, Item: 'static>> { f: T }
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:18:45
|
||||
|
|
||||
LL | struct SW1<T> where T: Iterator<Item: Copy, Item: Send> { f: T }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:20:45
|
||||
|
|
||||
LL | struct SW2<T> where T: Iterator<Item: Copy, Item: Copy> { f: T }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:22:48
|
||||
|
|
||||
LL | struct SW3<T> where T: Iterator<Item: 'static, Item: 'static> { f: T }
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:25:34
|
||||
|
|
||||
LL | enum EI1<T: Iterator<Item: Copy, Item: Send>> { V(T) }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:27:34
|
||||
|
|
||||
LL | enum EI2<T: Iterator<Item: Copy, Item: Copy>> { V(T) }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:29:37
|
||||
|
|
||||
LL | enum EI3<T: Iterator<Item: 'static, Item: 'static>> { V(T) }
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:31:43
|
||||
|
|
||||
LL | enum EW1<T> where T: Iterator<Item: Copy, Item: Send> { V(T) }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:33:43
|
||||
|
|
||||
LL | enum EW2<T> where T: Iterator<Item: Copy, Item: Copy> { V(T) }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:35:46
|
||||
|
|
||||
LL | enum EW3<T> where T: Iterator<Item: 'static, Item: 'static> { V(T) }
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:38:35
|
||||
|
|
||||
LL | union UI1<T: Iterator<Item: Copy, Item: Send>> { f: T }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:40:35
|
||||
|
|
||||
LL | union UI2<T: Iterator<Item: Copy, Item: Copy>> { f: T }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:42:38
|
||||
|
|
||||
LL | union UI3<T: Iterator<Item: 'static, Item: 'static>> { f: T }
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:44:44
|
||||
|
|
||||
LL | union UW1<T> where T: Iterator<Item: Copy, Item: Send> { f: T }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:46:44
|
||||
|
|
||||
LL | union UW2<T> where T: Iterator<Item: Copy, Item: Copy> { f: T }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:48:47
|
||||
|
|
||||
LL | union UW3<T> where T: Iterator<Item: 'static, Item: 'static> { f: T }
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:51:32
|
||||
|
|
||||
LL | fn FI1<T: Iterator<Item: Copy, Item: Send>>() {}
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:53:32
|
||||
|
|
||||
LL | fn FI2<T: Iterator<Item: Copy, Item: Copy>>() {}
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:55:35
|
||||
|
|
||||
LL | fn FI3<T: Iterator<Item: 'static, Item: 'static>>() {}
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:57:43
|
||||
|
|
||||
LL | fn FW1<T>() where T: Iterator<Item: Copy, Item: Send> {}
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:59:43
|
||||
|
|
||||
LL | fn FW2<T>() where T: Iterator<Item: Copy, Item: Copy> {}
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:61:46
|
||||
|
|
||||
LL | fn FW3<T>() where T: Iterator<Item: 'static, Item: 'static> {}
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:70:40
|
||||
|
|
||||
LL | fn FAPIT1(_: impl Iterator<Item: Copy, Item: Send>) {}
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:72:40
|
||||
|
|
||||
LL | fn FAPIT2(_: impl Iterator<Item: Copy, Item: Copy>) {}
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:74:43
|
||||
|
|
||||
LL | fn FAPIT3(_: impl Iterator<Item: 'static, Item: 'static>) {}
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:64:42
|
||||
|
|
||||
LL | fn FRPIT1() -> impl Iterator<Item: Copy, Item: Send> { iter::empty() }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:66:42
|
||||
|
|
||||
LL | fn FRPIT2() -> impl Iterator<Item: Copy, Item: Copy> { iter::empty() }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:68:45
|
||||
|
|
||||
LL | fn FRPIT3() -> impl Iterator<Item: 'static, Item: 'static> { iter::empty() }
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:77:39
|
||||
|
|
||||
LL | const CIT1: impl Iterator<Item: Copy, Item: Send> = iter::empty();
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:79:39
|
||||
|
|
||||
LL | const CIT2: impl Iterator<Item: Copy, Item: Copy> = iter::empty();
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:81:42
|
||||
|
|
||||
LL | const CIT3: impl Iterator<Item: 'static, Item: 'static> = iter::empty();
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:83:40
|
||||
|
|
||||
LL | static SIT1: impl Iterator<Item: Copy, Item: Send> = iter::empty();
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:85:40
|
||||
|
|
||||
LL | static SIT2: impl Iterator<Item: Copy, Item: Copy> = iter::empty();
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:87:43
|
||||
|
|
||||
LL | static SIT3: impl Iterator<Item: 'static, Item: 'static> = iter::empty();
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:90:46
|
||||
|
|
||||
LL | fn lit1() { let _: impl Iterator<Item: Copy, Item: Send> = iter::empty(); }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:92:46
|
||||
|
|
||||
LL | fn lit2() { let _: impl Iterator<Item: Copy, Item: Copy> = iter::empty(); }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:94:49
|
||||
|
|
||||
LL | fn lit3() { let _: impl Iterator<Item: 'static, Item: 'static> = iter::empty(); }
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:97:35
|
||||
|
|
||||
LL | type TAI1<T: Iterator<Item: Copy, Item: Send>> = T;
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:99:35
|
||||
|
|
||||
LL | type TAI2<T: Iterator<Item: Copy, Item: Copy>> = T;
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:101:38
|
||||
|
|
||||
LL | type TAI3<T: Iterator<Item: 'static, Item: 'static>> = T;
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:103:44
|
||||
|
|
||||
LL | type TAW1<T> where T: Iterator<Item: Copy, Item: Send> = T;
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:105:44
|
||||
|
|
||||
LL | type TAW2<T> where T: Iterator<Item: Copy, Item: Copy> = T;
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:107:47
|
||||
|
|
||||
LL | type TAW3<T> where T: Iterator<Item: 'static, Item: 'static> = T;
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error: could not find defining uses
|
||||
--> $DIR/duplicate.rs:110:1
|
||||
|
|
||||
LL | existential type ETAI1<T: Iterator<Item: Copy, Item: Send>>: Copy;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:110:48
|
||||
|
|
||||
LL | existential type ETAI1<T: Iterator<Item: Copy, Item: Send>>: Copy;
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error: could not find defining uses
|
||||
--> $DIR/duplicate.rs:112:1
|
||||
|
|
||||
LL | existential type ETAI2<T: Iterator<Item: Copy, Item: Copy>>: Copy;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:112:48
|
||||
|
|
||||
LL | existential type ETAI2<T: Iterator<Item: Copy, Item: Copy>>: Copy;
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error: could not find defining uses
|
||||
--> $DIR/duplicate.rs:114:1
|
||||
|
|
||||
LL | existential type ETAI3<T: Iterator<Item: 'static, Item: 'static>>: Copy;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:114:51
|
||||
|
|
||||
LL | existential type ETAI3<T: Iterator<Item: 'static, Item: 'static>>: Copy;
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error: could not find defining uses
|
||||
--> $DIR/duplicate.rs:116:1
|
||||
|
|
||||
LL | existential type ETAI4: Iterator<Item: Copy, Item: Send>;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:116:46
|
||||
|
|
||||
LL | existential type ETAI4: Iterator<Item: Copy, Item: Send>;
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error: could not find defining uses
|
||||
--> $DIR/duplicate.rs:118:1
|
||||
|
|
||||
LL | existential type ETAI5: Iterator<Item: Copy, Item: Copy>;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:118:46
|
||||
|
|
||||
LL | existential type ETAI5: Iterator<Item: Copy, Item: Copy>;
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error: could not find defining uses
|
||||
--> $DIR/duplicate.rs:120:1
|
||||
|
|
||||
LL | existential type ETAI6: Iterator<Item: 'static, Item: 'static>;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:120:49
|
||||
|
|
||||
LL | existential type ETAI6: Iterator<Item: 'static, Item: 'static>;
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:123:36
|
||||
|
|
||||
LL | trait TRI1<T: Iterator<Item: Copy, Item: Send>> {}
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:125:36
|
||||
|
|
||||
LL | trait TRI2<T: Iterator<Item: Copy, Item: Copy>> {}
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:127:39
|
||||
|
|
||||
LL | trait TRI3<T: Iterator<Item: 'static, Item: 'static>> {}
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:129:34
|
||||
|
|
||||
LL | trait TRS1: Iterator<Item: Copy, Item: Send> {}
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:131:34
|
||||
|
|
||||
LL | trait TRS2: Iterator<Item: Copy, Item: Copy> {}
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:133:37
|
||||
|
|
||||
LL | trait TRS3: Iterator<Item: 'static, Item: 'static> {}
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:135:45
|
||||
|
|
||||
LL | trait TRW1<T> where T: Iterator<Item: Copy, Item: Send> {}
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:137:45
|
||||
|
|
||||
LL | trait TRW2<T> where T: Iterator<Item: Copy, Item: Copy> {}
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:139:48
|
||||
|
|
||||
LL | trait TRW3<T> where T: Iterator<Item: 'static, Item: 'static> {}
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:141:46
|
||||
|
|
||||
LL | trait TRSW1 where Self: Iterator<Item: Copy, Item: Send> {}
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:143:46
|
||||
|
|
||||
LL | trait TRSW2 where Self: Iterator<Item: Copy, Item: Copy> {}
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:145:49
|
||||
|
|
||||
LL | trait TRSW3 where Self: Iterator<Item: 'static, Item: 'static> {}
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:147:43
|
||||
|
|
||||
LL | trait TRA1 { type A: Iterator<Item: Copy, Item: Send>; }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:149:43
|
||||
|
|
||||
LL | trait TRA2 { type A: Iterator<Item: Copy, Item: Copy>; }
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:151:46
|
||||
|
|
||||
LL | trait TRA3 { type A: Iterator<Item: 'static, Item: 'static>; }
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:154:40
|
||||
|
|
||||
LL | type TADyn1 = dyn Iterator<Item: Copy, Item: Send>;
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:156:44
|
||||
|
|
||||
LL | type TADyn2 = Box<dyn Iterator<Item: Copy, Item: Copy>>;
|
||||
| ---------- ^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error[E0719]: the value of the associated type `Item` (from the trait `std::iter::Iterator`) is already specified
|
||||
--> $DIR/duplicate.rs:158:43
|
||||
|
|
||||
LL | type TADyn3 = dyn Iterator<Item: 'static, Item: 'static>;
|
||||
| ------------- ^^^^^^^^^^^^^ re-bound here
|
||||
| |
|
||||
| `Item` bound here first
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: aborting due to 93 previous errors
|
||||
|
||||
67
src/test/ui/associated-type-bounds/dyn-existential-type.rs
Normal file
67
src/test/ui/associated-type-bounds/dyn-existential-type.rs
Normal file
|
|
@ -0,0 +1,67 @@
|
|||
// run-pass
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
#![feature(existential_type)]
|
||||
|
||||
use std::ops::Add;
|
||||
|
||||
trait Tr1 { type As1; fn mk(&self) -> Self::As1; }
|
||||
trait Tr2<'a> { fn tr2(self) -> &'a Self; }
|
||||
|
||||
fn assert_copy<T: Copy>(x: T) { let _x = x; let _x = x; }
|
||||
fn assert_static<T: 'static>(_: T) {}
|
||||
fn assert_forall_tr2<T: for<'a> Tr2<'a>>(_: T) {}
|
||||
|
||||
struct S1;
|
||||
#[derive(Copy, Clone)]
|
||||
struct S2;
|
||||
impl Tr1 for S1 { type As1 = S2; fn mk(&self) -> Self::As1 { S2 } }
|
||||
|
||||
type Et1 = Box<dyn Tr1<As1: Copy>>;
|
||||
fn def_et1() -> Et1 { Box::new(S1) }
|
||||
pub fn use_et1() { assert_copy(def_et1().mk()); }
|
||||
|
||||
type Et2 = Box<dyn Tr1<As1: 'static>>;
|
||||
fn def_et2() -> Et2 { Box::new(S1) }
|
||||
pub fn use_et2() { assert_static(def_et2().mk()); }
|
||||
|
||||
type Et3 = Box<dyn Tr1<As1: Clone + Iterator<Item: Add<u8, Output: Into<u8>>>>>;
|
||||
fn def_et3() -> Et3 {
|
||||
struct A;
|
||||
impl Tr1 for A {
|
||||
type As1 = core::ops::Range<u8>;
|
||||
fn mk(&self) -> Self::As1 { 0..10 }
|
||||
};
|
||||
Box::new(A)
|
||||
}
|
||||
pub fn use_et3() {
|
||||
let _0 = def_et3().mk().clone();
|
||||
let mut s = 0u8;
|
||||
for _1 in _0 {
|
||||
let _2 = _1 + 1u8;
|
||||
s += _2.into();
|
||||
}
|
||||
assert_eq!(s, (0..10).map(|x| x + 1).sum());
|
||||
}
|
||||
|
||||
type Et4 = Box<dyn Tr1<As1: for<'a> Tr2<'a>>>;
|
||||
fn def_et4() -> Et4 {
|
||||
#[derive(Copy, Clone)]
|
||||
struct A;
|
||||
impl Tr1 for A {
|
||||
type As1 = A;
|
||||
fn mk(&self) -> A { A }
|
||||
}
|
||||
impl<'a> Tr2<'a> for A {
|
||||
fn tr2(self) -> &'a Self { &A }
|
||||
}
|
||||
Box::new(A)
|
||||
}
|
||||
pub fn use_et4() { assert_forall_tr2(def_et4().mk()); }
|
||||
|
||||
fn main() {
|
||||
let _ = use_et1();
|
||||
let _ = use_et2();
|
||||
let _ = use_et3();
|
||||
let _ = use_et4();
|
||||
}
|
||||
69
src/test/ui/associated-type-bounds/dyn-lcsit.rs
Normal file
69
src/test/ui/associated-type-bounds/dyn-lcsit.rs
Normal file
|
|
@ -0,0 +1,69 @@
|
|||
// run-pass
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
#![feature(impl_trait_in_bindings)]
|
||||
|
||||
#![allow(non_upper_case_globals)]
|
||||
|
||||
use std::ops::Add;
|
||||
|
||||
trait Tr1 { type As1; fn mk(&self) -> Self::As1; }
|
||||
trait Tr2<'a> { fn tr2(self) -> &'a Self; }
|
||||
|
||||
fn assert_copy<T: Copy>(x: T) { let _x = x; let _x = x; }
|
||||
fn assert_static<T: 'static>(_: T) {}
|
||||
fn assert_forall_tr2<T: for<'a> Tr2<'a>>(_: T) {}
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
struct S1;
|
||||
#[derive(Copy, Clone)]
|
||||
struct S2;
|
||||
impl Tr1 for S1 { type As1 = S2; fn mk(&self) -> Self::As1 { S2 } }
|
||||
|
||||
const cdef_et1: &dyn Tr1<As1: Copy> = &S1;
|
||||
const sdef_et1: &dyn Tr1<As1: Copy> = &S1;
|
||||
pub fn use_et1() { assert_copy(cdef_et1.mk()); assert_copy(sdef_et1.mk()); }
|
||||
|
||||
const cdef_et2: &(dyn Tr1<As1: 'static> + Sync) = &S1;
|
||||
static sdef_et2: &(dyn Tr1<As1: 'static> + Sync) = &S1;
|
||||
pub fn use_et2() { assert_static(cdef_et2.mk()); assert_static(sdef_et2.mk()); }
|
||||
|
||||
const cdef_et3: &dyn Tr1<As1: Clone + Iterator<Item: Add<u8, Output: Into<u8>>>> = {
|
||||
struct A;
|
||||
impl Tr1 for A {
|
||||
type As1 = core::ops::Range<u8>;
|
||||
fn mk(&self) -> Self::As1 { 0..10 }
|
||||
};
|
||||
&A
|
||||
};
|
||||
pub fn use_et3() {
|
||||
let _0 = cdef_et3.mk().clone();
|
||||
let mut s = 0u8;
|
||||
for _1 in _0 {
|
||||
let _2 = _1 + 1u8;
|
||||
s += _2.into();
|
||||
}
|
||||
assert_eq!(s, (0..10).map(|x| x + 1).sum());
|
||||
}
|
||||
|
||||
const cdef_et4: &(dyn Tr1<As1: for<'a> Tr2<'a>> + Sync) = {
|
||||
#[derive(Copy, Clone)]
|
||||
struct A;
|
||||
impl Tr1 for A {
|
||||
type As1 = A;
|
||||
fn mk(&self) -> A { A }
|
||||
}
|
||||
impl<'a> Tr2<'a> for A {
|
||||
fn tr2(self) -> &'a Self { &A }
|
||||
}
|
||||
&A
|
||||
};
|
||||
static sdef_et4: &(dyn Tr1<As1: for<'a> Tr2<'a>> + Sync) = cdef_et4;
|
||||
pub fn use_et4() { assert_forall_tr2(cdef_et4.mk()); assert_forall_tr2(sdef_et4.mk()); }
|
||||
|
||||
fn main() {
|
||||
let _ = use_et1();
|
||||
let _ = use_et2();
|
||||
let _ = use_et3();
|
||||
let _ = use_et4();
|
||||
}
|
||||
6
src/test/ui/associated-type-bounds/dyn-lcsit.stderr
Normal file
6
src/test/ui/associated-type-bounds/dyn-lcsit.stderr
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
warning: the feature `impl_trait_in_bindings` is incomplete and may cause the compiler to crash
|
||||
--> $DIR/dyn-lcsit.rs:4:12
|
||||
|
|
||||
LL | #![feature(impl_trait_in_bindings)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
73
src/test/ui/associated-type-bounds/dyn-rpit-and-let.rs
Normal file
73
src/test/ui/associated-type-bounds/dyn-rpit-and-let.rs
Normal file
|
|
@ -0,0 +1,73 @@
|
|||
// run-pass
|
||||
|
||||
// FIXME: uncomment let binding types below when `impl_trait_in_bindings` feature is fixed.
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
use std::ops::Add;
|
||||
|
||||
trait Tr1 { type As1; fn mk(&self) -> Self::As1; }
|
||||
trait Tr2<'a> { fn tr2(self) -> &'a Self; }
|
||||
|
||||
fn assert_copy<T: Copy>(x: T) { let _x = x; let _x = x; }
|
||||
fn assert_static<T: 'static>(_: T) {}
|
||||
fn assert_forall_tr2<T: for<'a> Tr2<'a>>(_: T) {}
|
||||
|
||||
struct S1;
|
||||
#[derive(Copy, Clone)]
|
||||
struct S2;
|
||||
impl Tr1 for S1 { type As1 = S2; fn mk(&self) -> Self::As1 { S2 } }
|
||||
|
||||
fn def_et1() -> Box<dyn Tr1<As1: Copy>> {
|
||||
let x /* : Box<dyn Tr1<As1: Copy>> */ = Box::new(S1);
|
||||
x
|
||||
}
|
||||
pub fn use_et1() { assert_copy(def_et1().mk()); }
|
||||
|
||||
fn def_et2() -> Box<dyn Tr1<As1: Send + 'static>> {
|
||||
let x /* : Box<dyn Tr1<As1: Send + 'static>> */ = Box::new(S1);
|
||||
x
|
||||
}
|
||||
pub fn use_et2() { assert_static(def_et2().mk()); }
|
||||
|
||||
fn def_et3() -> Box<dyn Tr1<As1: Clone + Iterator<Item: Add<u8, Output: Into<u8>>>>> {
|
||||
struct A;
|
||||
impl Tr1 for A {
|
||||
type As1 = core::ops::Range<u8>;
|
||||
fn mk(&self) -> Self::As1 { 0..10 }
|
||||
};
|
||||
let x /* : Box<dyn Tr1<As1: Clone + Iterator<Item: Add<u8, Output: Into<u8>>>>> */
|
||||
= Box::new(A);
|
||||
x
|
||||
}
|
||||
pub fn use_et3() {
|
||||
let _0 = def_et3().mk().clone();
|
||||
let mut s = 0u8;
|
||||
for _1 in _0 {
|
||||
let _2 = _1 + 1u8;
|
||||
s += _2.into();
|
||||
}
|
||||
assert_eq!(s, (0..10).map(|x| x + 1).sum());
|
||||
}
|
||||
|
||||
fn def_et4() -> Box<dyn Tr1<As1: for<'a> Tr2<'a>>> {
|
||||
#[derive(Copy, Clone)]
|
||||
struct A;
|
||||
impl Tr1 for A {
|
||||
type As1 = A;
|
||||
fn mk(&self) -> A { A }
|
||||
}
|
||||
impl<'a> Tr2<'a> for A {
|
||||
fn tr2(self) -> &'a Self { &A }
|
||||
}
|
||||
let x /* : Box<dyn Tr1<As1: for<'a> Tr2<'a>>> */ = Box::new(A);
|
||||
x
|
||||
}
|
||||
pub fn use_et4() { assert_forall_tr2(def_et4().mk()); }
|
||||
|
||||
fn main() {
|
||||
let _ = use_et1();
|
||||
let _ = use_et2();
|
||||
let _ = use_et3();
|
||||
let _ = use_et4();
|
||||
}
|
||||
|
|
@ -0,0 +1,26 @@
|
|||
// compile-pass
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
trait Tr1: Sized { type As1; }
|
||||
trait Tr2<'a>: Sized { type As2; }
|
||||
|
||||
trait ObjTr1 { fn foo() -> Self where Self: Tr1<As1: Copy>; }
|
||||
fn _assert_obj_safe_1(_: Box<dyn ObjTr1>) {}
|
||||
|
||||
trait ObjTr2 { fn foo() -> Self where Self: Tr1<As1: 'static>; }
|
||||
fn _assert_obj_safe_2(_: Box<dyn ObjTr2>) {}
|
||||
|
||||
trait ObjTr3 { fn foo() -> Self where Self: Tr1<As1: Into<u8> + 'static + Copy>; }
|
||||
fn _assert_obj_safe_3(_: Box<dyn ObjTr3>) {}
|
||||
|
||||
trait ObjTr4 { fn foo() -> Self where Self: Tr1<As1: for<'a> Tr2<'a>>; }
|
||||
fn _assert_obj_safe_4(_: Box<dyn ObjTr4>) {}
|
||||
|
||||
trait ObjTr5 { fn foo() -> Self where for<'a> Self: Tr1<As1: Tr2<'a>>; }
|
||||
fn _assert_obj_safe_5(_: Box<dyn ObjTr5>) {}
|
||||
|
||||
trait ObjTr6 { fn foo() -> Self where Self: for<'a> Tr1<As1: Tr2<'a, As2: for<'b> Tr2<'b>>>; }
|
||||
fn _assert_obj_safe_6(_: Box<dyn ObjTr6>) {}
|
||||
|
||||
fn main() {}
|
||||
122
src/test/ui/associated-type-bounds/enum-bounds.rs
Normal file
122
src/test/ui/associated-type-bounds/enum-bounds.rs
Normal file
|
|
@ -0,0 +1,122 @@
|
|||
// run-pass
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
trait Tr1 { type As1; }
|
||||
trait Tr2 { type As2; }
|
||||
trait Tr3 { type As3; }
|
||||
trait Tr4<'a> { type As4; }
|
||||
trait Tr5 { type As5; }
|
||||
|
||||
impl Tr1 for &str { type As1 = bool; }
|
||||
impl Tr2 for bool { type As2 = u8; }
|
||||
impl Tr3 for u8 { type As3 = fn() -> u8; }
|
||||
impl Tr1 for () { type As1 = (usize,); }
|
||||
impl<'a> Tr4<'a> for (usize,) { type As4 = u8; }
|
||||
impl Tr5 for bool { type As5 = u16; }
|
||||
|
||||
enum En1<T: Tr1<As1: Tr2>> {
|
||||
Outest(T),
|
||||
Outer(T::As1),
|
||||
Inner(<T::As1 as Tr2>::As2),
|
||||
}
|
||||
|
||||
fn wrap_en1_1<T>(x: T) -> En1<T> where T: Tr1, T::As1: Tr2 {
|
||||
En1::Outest(x)
|
||||
}
|
||||
|
||||
fn wrap_en1_2<T>(x: T::As1) -> En1<T> where T: Tr1, T::As1: Tr2 {
|
||||
En1::Outer(x)
|
||||
}
|
||||
|
||||
fn wrap_en1_3<T>(x: <T::As1 as Tr2>::As2) -> En1<T> where T: Tr1, T::As1: Tr2 {
|
||||
En1::Inner(x)
|
||||
}
|
||||
|
||||
enum En2<T: Tr1<As1: Tr2<As2: Tr3>>> {
|
||||
V0(T),
|
||||
V1(T::As1),
|
||||
V2(<T::As1 as Tr2>::As2),
|
||||
V3(<<T::As1 as Tr2>::As2 as Tr3>::As3),
|
||||
}
|
||||
|
||||
enum En3<T: Tr1<As1: 'static>> {
|
||||
V0(T),
|
||||
V1(&'static T::As1),
|
||||
}
|
||||
|
||||
enum En4<'x1, 'x2, T: Tr1<As1: for<'l> Tr4<'l>>> {
|
||||
V0(&'x1 <T::As1 as Tr4<'x1>>::As4),
|
||||
V1(&'x2 <T::As1 as Tr4<'x2>>::As4),
|
||||
}
|
||||
|
||||
enum _En5<'x1, 'x2, T: Tr1<As1: for<'l> Tr4<'l, As4: Copy>>> {
|
||||
_V0(&'x1 <T::As1 as Tr4<'x1>>::As4),
|
||||
_V1(&'x2 <T::As1 as Tr4<'x2>>::As4),
|
||||
}
|
||||
|
||||
enum En6<T>
|
||||
where
|
||||
T: Tr1<As1: Tr2 + 'static + Tr5>,
|
||||
{
|
||||
V0(T),
|
||||
V1(<T::As1 as Tr2>::As2),
|
||||
V2(&'static T::As1),
|
||||
V3(<T::As1 as Tr5>::As5),
|
||||
}
|
||||
|
||||
enum _En7<'a, 'b, T> // `<T::As1 as Tr2>::As2: 'a` is implied.
|
||||
where
|
||||
T: Tr1<As1: Tr2>,
|
||||
{
|
||||
V0(&'a T),
|
||||
V1(&'b <T::As1 as Tr2>::As2),
|
||||
}
|
||||
|
||||
fn _make_en7<'a, 'b, T>(x: _En7<'a, 'b, T>)
|
||||
where
|
||||
T: Tr1<As1: Tr2>,
|
||||
{
|
||||
match x {
|
||||
_En7::V0(x) => {
|
||||
let _: &'a T = &x;
|
||||
},
|
||||
_En7::V1(_) => {},
|
||||
}
|
||||
}
|
||||
|
||||
enum EnSelf<T> where Self: Tr1<As1: Tr2> {
|
||||
V0(T),
|
||||
V1(<Self as Tr1>::As1),
|
||||
V2(<<Self as Tr1>::As1 as Tr2>::As2),
|
||||
}
|
||||
|
||||
impl Tr1 for EnSelf<&'static str> { type As1 = bool; }
|
||||
|
||||
fn main() {
|
||||
if let En1::Outest("foo") = wrap_en1_1::<_>("foo") {} else { panic!() };
|
||||
if let En1::Outer(true) = wrap_en1_2::<&str>(true) {} else { panic!() };
|
||||
if let En1::Inner(24u8) = wrap_en1_3::<&str>(24u8) {} else { panic!() };
|
||||
|
||||
let _ = En2::<_>::V0("151571");
|
||||
let _ = En2::<&str>::V1(false);
|
||||
let _ = En2::<&str>::V2(42u8);
|
||||
let _ = En2::<&str>::V3(|| 12u8);
|
||||
|
||||
let _ = En3::<_>::V0("deadbeef");
|
||||
let _ = En3::<&str>::V1(&true);
|
||||
|
||||
let f1 = (1,);
|
||||
let f2 = (2,);
|
||||
let _ = En4::<()>::V0(&f1.0);
|
||||
let _ = En4::<()>::V1(&f2.0);
|
||||
|
||||
let _ = En6::<_>::V0("bar");
|
||||
let _ = En6::<&str>::V1(24u8);
|
||||
let _ = En6::<&str>::V2(&false);
|
||||
let _ = En6::<&str>::V3(12u16);
|
||||
|
||||
let _ = EnSelf::<_>::V0("foo");
|
||||
let _ = EnSelf::<&'static str>::V1(true);
|
||||
let _ = EnSelf::<&'static str>::V2(24u8);
|
||||
}
|
||||
67
src/test/ui/associated-type-bounds/existential-type.rs
Normal file
67
src/test/ui/associated-type-bounds/existential-type.rs
Normal file
|
|
@ -0,0 +1,67 @@
|
|||
// run-pass
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
#![feature(existential_type)]
|
||||
|
||||
use std::ops::Add;
|
||||
|
||||
trait Tr1 { type As1; fn mk(self) -> Self::As1; }
|
||||
trait Tr2<'a> { fn tr2(self) -> &'a Self; }
|
||||
|
||||
fn assert_copy<T: Copy>(x: T) { let _x = x; let _x = x; }
|
||||
fn assert_static<T: 'static>(_: T) {}
|
||||
fn assert_forall_tr2<T: for<'a> Tr2<'a>>(_: T) {}
|
||||
|
||||
struct S1;
|
||||
#[derive(Copy, Clone)]
|
||||
struct S2;
|
||||
impl Tr1 for S1 { type As1 = S2; fn mk(self) -> Self::As1 { S2 } }
|
||||
|
||||
existential type Et1: Tr1<As1: Copy>;
|
||||
fn def_et1() -> Et1 { S1 }
|
||||
pub fn use_et1() { assert_copy(def_et1().mk()); }
|
||||
|
||||
existential type Et2: Tr1<As1: 'static>;
|
||||
fn def_et2() -> Et2 { S1 }
|
||||
pub fn use_et2() { assert_static(def_et2().mk()); }
|
||||
|
||||
existential type Et3: Tr1<As1: Clone + Iterator<Item: Add<u8, Output: Into<u8>>>>;
|
||||
fn def_et3() -> Et3 {
|
||||
struct A;
|
||||
impl Tr1 for A {
|
||||
type As1 = core::ops::Range<u8>;
|
||||
fn mk(self) -> Self::As1 { 0..10 }
|
||||
};
|
||||
A
|
||||
}
|
||||
pub fn use_et3() {
|
||||
let _0 = def_et3().mk().clone();
|
||||
let mut s = 0u8;
|
||||
for _1 in _0 {
|
||||
let _2 = _1 + 1u8;
|
||||
s += _2.into();
|
||||
}
|
||||
assert_eq!(s, (0..10).map(|x| x + 1).sum());
|
||||
}
|
||||
|
||||
existential type Et4: Tr1<As1: for<'a> Tr2<'a>>;
|
||||
fn def_et4() -> Et4 {
|
||||
#[derive(Copy, Clone)]
|
||||
struct A;
|
||||
impl Tr1 for A {
|
||||
type As1 = A;
|
||||
fn mk(self) -> A { A }
|
||||
}
|
||||
impl<'a> Tr2<'a> for A {
|
||||
fn tr2(self) -> &'a Self { &A }
|
||||
}
|
||||
A
|
||||
}
|
||||
pub fn use_et4() { assert_forall_tr2(def_et4().mk()); }
|
||||
|
||||
fn main() {
|
||||
let _ = use_et1();
|
||||
let _ = use_et2();
|
||||
let _ = use_et3();
|
||||
let _ = use_et4();
|
||||
}
|
||||
58
src/test/ui/associated-type-bounds/fn-apit.rs
Normal file
58
src/test/ui/associated-type-bounds/fn-apit.rs
Normal file
|
|
@ -0,0 +1,58 @@
|
|||
// run-pass
|
||||
// aux-build:fn-aux.rs
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
extern crate fn_aux;
|
||||
|
||||
use fn_aux::*;
|
||||
|
||||
fn apit_bound(beta: impl Beta<Gamma: Alpha>) -> usize {
|
||||
desugared_bound(beta)
|
||||
}
|
||||
|
||||
fn apit_bound_region(beta: impl Beta<Gamma: 'static>) -> usize {
|
||||
desugared_bound_region(beta)
|
||||
}
|
||||
|
||||
fn apit_bound_multi(
|
||||
beta: impl Copy + Beta<Gamma: Alpha + 'static + Delta>
|
||||
) -> usize {
|
||||
desugared_bound_multi(beta)
|
||||
}
|
||||
|
||||
fn apit_bound_region_forall(
|
||||
beta: impl Beta<Gamma: Copy + for<'a> Epsilon<'a>>
|
||||
) -> usize {
|
||||
desugared_bound_region_forall(beta)
|
||||
}
|
||||
|
||||
fn apit_bound_region_forall2(
|
||||
beta: impl Beta<Gamma: Copy + for<'a> Epsilon<'a, Zeta: Eta>>
|
||||
) -> usize {
|
||||
desugared_bound_region_forall2(beta)
|
||||
}
|
||||
|
||||
fn apit_bound_nested(
|
||||
beta: impl Beta<Gamma: Copy + Alpha + Beta<Gamma: Delta>>
|
||||
) -> usize {
|
||||
desugared_bound_nested(beta)
|
||||
}
|
||||
|
||||
fn apit_bound_nested2(
|
||||
beta: impl Beta<Gamma = impl Copy + Alpha + Beta<Gamma: Delta>>
|
||||
) -> usize {
|
||||
desugared_bound_nested(beta)
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let beta = BetaType;
|
||||
let _gamma = beta.gamma();
|
||||
|
||||
assert_eq!(42, apit_bound(beta));
|
||||
assert_eq!(24, apit_bound_region(beta));
|
||||
assert_eq!(42 + 24 + 1337, apit_bound_multi(beta));
|
||||
assert_eq!(7331 * 2, apit_bound_region_forall(beta));
|
||||
assert_eq!(42 + 1337, apit_bound_nested(beta));
|
||||
assert_eq!(42 + 1337, apit_bound_nested2(beta));
|
||||
}
|
||||
12
src/test/ui/associated-type-bounds/fn-aux.rs
Normal file
12
src/test/ui/associated-type-bounds/fn-aux.rs
Normal file
|
|
@ -0,0 +1,12 @@
|
|||
// run-pass
|
||||
// aux-build:fn-aux.rs
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
extern crate fn_aux;
|
||||
|
||||
use fn_aux::*;
|
||||
|
||||
fn main() {
|
||||
desugared();
|
||||
}
|
||||
60
src/test/ui/associated-type-bounds/fn-dyn-apit.rs
Normal file
60
src/test/ui/associated-type-bounds/fn-dyn-apit.rs
Normal file
|
|
@ -0,0 +1,60 @@
|
|||
// run-pass
|
||||
// aux-build:fn-dyn-aux.rs
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
extern crate fn_dyn_aux;
|
||||
|
||||
use fn_dyn_aux::*;
|
||||
|
||||
// ATB, APIT (dyn trait):
|
||||
|
||||
fn dyn_apit_bound(beta: &dyn Beta<Gamma: Alpha>) -> usize {
|
||||
desugared_bound(beta)
|
||||
}
|
||||
|
||||
fn dyn_apit_bound_region(beta: &dyn Beta<Gamma: 'static>) -> usize {
|
||||
desugared_bound_region(beta)
|
||||
}
|
||||
|
||||
fn dyn_apit_bound_multi(
|
||||
beta: &(dyn Beta<Gamma: Alpha + 'static + Delta> + Send)
|
||||
) -> usize {
|
||||
desugared_bound_multi(beta)
|
||||
}
|
||||
|
||||
fn dyn_apit_bound_region_forall(
|
||||
beta: &dyn Beta<Gamma: Copy + for<'a> Epsilon<'a>>
|
||||
) -> usize {
|
||||
desugared_bound_region_forall(beta)
|
||||
}
|
||||
|
||||
fn dyn_apit_bound_region_forall2(
|
||||
beta: &dyn Beta<Gamma: Copy + for<'a> Epsilon<'a, Zeta: Eta>>
|
||||
) -> usize {
|
||||
desugared_bound_region_forall2(beta)
|
||||
}
|
||||
|
||||
fn dyn_apit_bound_nested(
|
||||
beta: &dyn Beta<Gamma: Copy + Alpha + Beta<Gamma: Delta>>
|
||||
) -> usize {
|
||||
desugared_bound_nested(beta)
|
||||
}
|
||||
|
||||
fn dyn_apit_bound_nested2(
|
||||
beta: &dyn Beta<Gamma = impl Copy + Alpha + Beta<Gamma: Delta>>
|
||||
) -> usize {
|
||||
desugared_bound_nested(beta)
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let beta = BetaType;
|
||||
let _gamma = beta.gamma();
|
||||
|
||||
assert_eq!(42, dyn_apit_bound(&beta));
|
||||
assert_eq!(24, dyn_apit_bound_region(&beta));
|
||||
assert_eq!(42 + 24 + 1337, dyn_apit_bound_multi(&beta));
|
||||
assert_eq!(7331 * 2, dyn_apit_bound_region_forall(&beta));
|
||||
assert_eq!(42 + 1337, dyn_apit_bound_nested(&beta));
|
||||
assert_eq!(42 + 1337, dyn_apit_bound_nested2(&beta));
|
||||
}
|
||||
62
src/test/ui/associated-type-bounds/fn-inline.rs
Normal file
62
src/test/ui/associated-type-bounds/fn-inline.rs
Normal file
|
|
@ -0,0 +1,62 @@
|
|||
// run-pass
|
||||
// aux-build:fn-aux.rs
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
extern crate fn_aux;
|
||||
|
||||
use fn_aux::*;
|
||||
|
||||
// ATB, Type parameters, Inline bounds:
|
||||
|
||||
fn inline_bound<B: Beta<Gamma: Alpha>>(beta: B) -> usize {
|
||||
desugared_bound(beta)
|
||||
}
|
||||
|
||||
fn inline_bound_region<B: Beta<Gamma: 'static>>(beta: B) -> usize {
|
||||
desugared_bound_region(beta)
|
||||
}
|
||||
|
||||
fn inline_bound_multi<B: Copy + Beta<Gamma: Alpha + 'static + Delta>>(
|
||||
beta: B
|
||||
) -> usize {
|
||||
desugared_bound_multi(beta)
|
||||
}
|
||||
|
||||
fn inline_bound_region_specific<'a, B: Beta<Gamma: 'a + Epsilon<'a>>>(
|
||||
gamma: &'a B::Gamma
|
||||
) -> usize {
|
||||
desugared_bound_region_specific::<B>(gamma)
|
||||
}
|
||||
|
||||
fn inline_bound_region_forall<B: Beta<Gamma: Copy + for<'a> Epsilon<'a>>>(
|
||||
beta: B
|
||||
) -> usize {
|
||||
desugared_bound_region_forall(beta)
|
||||
}
|
||||
|
||||
fn inline_bound_region_forall2<B: Beta<Gamma: Copy + for<'a> Epsilon<'a, Zeta: Eta>>>(
|
||||
beta: B
|
||||
) -> usize {
|
||||
desugared_bound_region_forall2(beta)
|
||||
}
|
||||
|
||||
fn inline_bound_nested<B: Beta<Gamma: Copy + Alpha + Beta<Gamma: Delta>>>(
|
||||
beta: B
|
||||
) -> usize {
|
||||
desugared_bound_nested(beta)
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let beta = BetaType;
|
||||
let gamma = beta.gamma();
|
||||
|
||||
assert_eq!(42, inline_bound(beta));
|
||||
assert_eq!(24, inline_bound_region(beta));
|
||||
assert_eq!(42 + 24 + 1337, inline_bound_multi(beta));
|
||||
assert_eq!(7331, inline_bound_region_specific::<BetaType>(&gamma));
|
||||
assert_eq!(7331 * 2, inline_bound_region_forall(beta));
|
||||
// FIXME: requires lazy normalization.
|
||||
// assert_eq!(7331 * 2, inline_bound_region_forall2(beta));
|
||||
assert_eq!(42 + 1337, inline_bound_nested(beta));
|
||||
}
|
||||
78
src/test/ui/associated-type-bounds/fn-where.rs
Normal file
78
src/test/ui/associated-type-bounds/fn-where.rs
Normal file
|
|
@ -0,0 +1,78 @@
|
|||
// run-pass
|
||||
// aux-build:fn-aux.rs
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
extern crate fn_aux;
|
||||
|
||||
use fn_aux::*;
|
||||
|
||||
// ATB, Type parameters, Where-clauses:
|
||||
|
||||
fn where_bound<B>(beta: B) -> usize
|
||||
where
|
||||
B: Beta<Gamma: Alpha>
|
||||
{
|
||||
desugared_bound(beta)
|
||||
}
|
||||
|
||||
fn where_bound_region<B>(beta: B) -> usize
|
||||
where
|
||||
B: Beta<Gamma: 'static>
|
||||
{
|
||||
desugared_bound_region(beta)
|
||||
}
|
||||
|
||||
fn where_bound_multi<B>(beta: B) -> usize
|
||||
where
|
||||
B: Copy + Beta<Gamma: Alpha + 'static + Delta>,
|
||||
{
|
||||
desugared_bound_multi(beta)
|
||||
}
|
||||
|
||||
fn where_bound_region_specific<'a, B>(gamma: &'a B::Gamma) -> usize
|
||||
where
|
||||
B: Beta<Gamma: 'a + Epsilon<'a>>,
|
||||
{
|
||||
desugared_bound_region_specific::<B>(gamma)
|
||||
}
|
||||
|
||||
fn where_bound_region_forall<B>(beta: B) -> usize
|
||||
where
|
||||
B: Beta<Gamma: Copy + for<'a> Epsilon<'a>>,
|
||||
{
|
||||
desugared_bound_region_forall(beta)
|
||||
}
|
||||
|
||||
fn where_bound_region_forall2<B>(beta: B) -> usize
|
||||
where
|
||||
B: Beta<Gamma: Copy + for<'a> Epsilon<'a, Zeta: Eta>>,
|
||||
{
|
||||
desugared_bound_region_forall2(beta)
|
||||
}
|
||||
|
||||
fn where_contraint_region_forall<B>(beta: B) -> usize
|
||||
where
|
||||
for<'a> &'a B: Beta<Gamma: Alpha>,
|
||||
{
|
||||
desugared_contraint_region_forall(beta)
|
||||
}
|
||||
|
||||
fn where_bound_nested<B>(beta: B) -> usize
|
||||
where
|
||||
B: Beta<Gamma: Copy + Alpha + Beta<Gamma: Delta>>,
|
||||
{
|
||||
desugared_bound_nested(beta)
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let beta = BetaType;
|
||||
let gamma = beta.gamma();
|
||||
|
||||
assert_eq!(42, where_bound(beta));
|
||||
assert_eq!(24, where_bound_region(beta));
|
||||
assert_eq!(42 + 24 + 1337, where_bound_multi(beta));
|
||||
assert_eq!(7331, where_bound_region_specific::<BetaType>(&gamma));
|
||||
assert_eq!(7331 * 2, where_bound_region_forall::<BetaType>(beta));
|
||||
assert_eq!(42 + 1337, where_bound_nested::<BetaType>(beta));
|
||||
}
|
||||
64
src/test/ui/associated-type-bounds/fn-wrap-apit.rs
Normal file
64
src/test/ui/associated-type-bounds/fn-wrap-apit.rs
Normal file
|
|
@ -0,0 +1,64 @@
|
|||
// run-pass
|
||||
// aux-build:fn-aux.rs
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
extern crate fn_aux;
|
||||
|
||||
use fn_aux::*;
|
||||
|
||||
// ATB, APIT + Wrap:
|
||||
|
||||
struct Wrap<T>(T);
|
||||
|
||||
fn wrap_apit_bound(beta: Wrap<impl Beta<Gamma: Alpha>>) -> usize {
|
||||
desugared_bound(beta.0)
|
||||
}
|
||||
|
||||
fn wrap_apit_bound_region(beta: Wrap<impl Beta<Gamma: 'static>>) -> usize {
|
||||
desugared_bound_region(beta.0)
|
||||
}
|
||||
|
||||
fn wrap_apit_bound_multi(
|
||||
beta: Wrap<impl Copy + Beta<Gamma: Alpha + 'static + Delta>>
|
||||
) -> usize {
|
||||
desugared_bound_multi(beta.0)
|
||||
}
|
||||
|
||||
fn wrap_apit_bound_region_forall(
|
||||
beta: Wrap<impl Beta<Gamma: Copy + for<'a> Epsilon<'a>>>
|
||||
) -> usize {
|
||||
desugared_bound_region_forall(beta.0)
|
||||
}
|
||||
|
||||
fn wrap_apit_bound_region_forall2(
|
||||
beta: Wrap<impl Beta<Gamma: Copy + for<'a> Epsilon<'a, Zeta: Eta>>>
|
||||
) -> usize {
|
||||
desugared_bound_region_forall2(beta.0)
|
||||
}
|
||||
|
||||
fn wrap_apit_bound_nested(
|
||||
beta: Wrap<impl Beta<Gamma: Copy + Alpha + Beta<Gamma: Delta>>>
|
||||
) -> usize {
|
||||
desugared_bound_nested(beta.0)
|
||||
}
|
||||
|
||||
fn wrap_apit_bound_nested2(
|
||||
beta: Wrap<impl Beta<Gamma = impl Copy + Alpha + Beta<Gamma: Delta>>>
|
||||
) -> usize {
|
||||
desugared_bound_nested(beta.0)
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let beta = BetaType;
|
||||
let _gamma = beta.gamma();
|
||||
|
||||
assert_eq!(42, wrap_apit_bound(Wrap(beta)));
|
||||
assert_eq!(24, wrap_apit_bound_region(Wrap(beta)));
|
||||
assert_eq!(42 + 24 + 1337, wrap_apit_bound_multi(Wrap(beta)));
|
||||
assert_eq!(7331 * 2, wrap_apit_bound_region_forall(Wrap(beta)));
|
||||
// FIXME: requires lazy normalization.
|
||||
// assert_eq!(7331 * 2, wrap_apit_bound_region_forall2(Wrap(beta)));
|
||||
assert_eq!(42 + 1337, wrap_apit_bound_nested(Wrap(beta)));
|
||||
assert_eq!(42 + 1337, wrap_apit_bound_nested2(Wrap(beta)));
|
||||
}
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
error: lifetime may not live long enough
|
||||
--> $DIR/implied-region-constraints.rs:19:56
|
||||
|
|
||||
LL | fn _bad_st<'a, 'b, T>(x: St<'a, 'b, T>)
|
||||
| -- -- lifetime `'b` defined here
|
||||
| |
|
||||
| lifetime `'a` defined here
|
||||
...
|
||||
LL | let _failure_proves_not_implied_outlives_region_b: &'b T = &x.f0;
|
||||
| ^^^^^ type annotation requires that `'a` must outlive `'b`
|
||||
|
||||
error: lifetime may not live long enough
|
||||
--> $DIR/implied-region-constraints.rs:40:64
|
||||
|
|
||||
LL | fn _bad_en7<'a, 'b, T>(x: En7<'a, 'b, T>)
|
||||
| -- -- lifetime `'b` defined here
|
||||
| |
|
||||
| lifetime `'a` defined here
|
||||
...
|
||||
LL | let _failure_proves_not_implied_outlives_region_b: &'b T = &x;
|
||||
| ^^^^^ type annotation requires that `'a` must outlive `'b`
|
||||
|
||||
error: aborting due to 2 previous errors
|
||||
|
||||
|
|
@ -0,0 +1,47 @@
|
|||
// compile-fail
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
trait Tr1 { type As1; }
|
||||
trait Tr2 { type As2; }
|
||||
|
||||
struct St<'a, 'b, T: Tr1<As1: Tr2>> { // `T: 'b` is *not* implied!
|
||||
f0: &'a T, // `T: 'a` is implied.
|
||||
f1: &'b <T::As1 as Tr2>::As2, // `<T::As1 as Tr2>::As2: 'a` is implied.
|
||||
}
|
||||
|
||||
fn _bad_st<'a, 'b, T>(x: St<'a, 'b, T>)
|
||||
where
|
||||
T: Tr1,
|
||||
T::As1: Tr2,
|
||||
{
|
||||
// This should fail because `T: 'b` is not implied from `WF(St<'a, 'b, T>)`.
|
||||
let _failure_proves_not_implied_outlives_region_b: &'b T = &x.f0;
|
||||
//~^ ERROR lifetime mismatch [E0623]
|
||||
}
|
||||
|
||||
enum En7<'a, 'b, T> // `<T::As1 as Tr2>::As2: 'a` is implied.
|
||||
where
|
||||
T: Tr1,
|
||||
T::As1: Tr2,
|
||||
{
|
||||
V0(&'a T),
|
||||
V1(&'b <T::As1 as Tr2>::As2),
|
||||
}
|
||||
|
||||
fn _bad_en7<'a, 'b, T>(x: En7<'a, 'b, T>)
|
||||
where
|
||||
T: Tr1,
|
||||
T::As1: Tr2,
|
||||
{
|
||||
match x {
|
||||
En7::V0(x) => {
|
||||
// Also fails for the same reason as above:
|
||||
let _failure_proves_not_implied_outlives_region_b: &'b T = &x;
|
||||
//~^ ERROR lifetime mismatch [E0623]
|
||||
},
|
||||
En7::V1(_) => {},
|
||||
}
|
||||
}
|
||||
|
||||
fn main() {}
|
||||
|
|
@ -0,0 +1,20 @@
|
|||
error[E0623]: lifetime mismatch
|
||||
--> $DIR/implied-region-constraints.rs:19:64
|
||||
|
|
||||
LL | fn _bad_st<'a, 'b, T>(x: St<'a, 'b, T>)
|
||||
| ------------- this type is declared with multiple lifetimes...
|
||||
...
|
||||
LL | let _failure_proves_not_implied_outlives_region_b: &'b T = &x.f0;
|
||||
| ^^^^^ ...but data with one lifetime flows into the other here
|
||||
|
||||
error[E0623]: lifetime mismatch
|
||||
--> $DIR/implied-region-constraints.rs:40:72
|
||||
|
|
||||
LL | fn _bad_en7<'a, 'b, T>(x: En7<'a, 'b, T>)
|
||||
| -------------- this type is declared with multiple lifetimes...
|
||||
...
|
||||
LL | let _failure_proves_not_implied_outlives_region_b: &'b T = &x;
|
||||
| ^^ ...but data with one lifetime flows into the other here
|
||||
|
||||
error: aborting due to 2 previous errors
|
||||
|
||||
36
src/test/ui/associated-type-bounds/inside-adt.rs
Normal file
36
src/test/ui/associated-type-bounds/inside-adt.rs
Normal file
|
|
@ -0,0 +1,36 @@
|
|||
// compile-fail
|
||||
// ignore-tidy-linelength
|
||||
// error-pattern:could not find defining uses
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
#![feature(untagged_unions)]
|
||||
|
||||
struct S1 { f: dyn Iterator<Item: Copy> }
|
||||
//~^ associated type bounds are not allowed within structs, enums, or unions
|
||||
//~| the value of the associated type `Item` (from the trait `std::iter::Iterator`) must be specified [E0191]
|
||||
struct S2 { f: Box<dyn Iterator<Item: Copy>> }
|
||||
//~^ associated type bounds are not allowed within structs, enums, or unions
|
||||
//~| the value of the associated type `Item` (from the trait `std::iter::Iterator`) must be specified [E0191]
|
||||
struct S3 { f: dyn Iterator<Item: 'static> }
|
||||
//~^ associated type bounds are not allowed within structs, enums, or unions
|
||||
//~| the value of the associated type `Item` (from the trait `std::iter::Iterator`) must be specified [E0191]
|
||||
|
||||
enum E1 { V(dyn Iterator<Item: Copy>) }
|
||||
//~^ associated type bounds are not allowed within structs, enums, or unions
|
||||
//~| the value of the associated type `Item` (from the trait `std::iter::Iterator`) must be specified [E0191]
|
||||
enum E2 { V(Box<dyn Iterator<Item: Copy>>) }
|
||||
//~^ associated type bounds are not allowed within structs, enums, or unions
|
||||
//~| the value of the associated type `Item` (from the trait `std::iter::Iterator`) must be specified [E0191]
|
||||
enum E3 { V(dyn Iterator<Item: 'static>) }
|
||||
//~^ associated type bounds are not allowed within structs, enums, or unions
|
||||
//~| the value of the associated type `Item` (from the trait `std::iter::Iterator`) must be specified [E0191]
|
||||
|
||||
union U1 { f: dyn Iterator<Item: Copy> }
|
||||
//~^ associated type bounds are not allowed within structs, enums, or unions
|
||||
//~| the value of the associated type `Item` (from the trait `std::iter::Iterator`) must be specified [E0191]
|
||||
union U2 { f: Box<dyn Iterator<Item: Copy>> }
|
||||
//~^ associated type bounds are not allowed within structs, enums, or unions
|
||||
//~| the value of the associated type `Item` (from the trait `std::iter::Iterator`) must be specified [E0191]
|
||||
union U3 { f: dyn Iterator<Item: 'static> }
|
||||
//~^ associated type bounds are not allowed within structs, enums, or unions
|
||||
//~| the value of the associated type `Item` (from the trait `std::iter::Iterator`) must be specified [E0191]
|
||||
79
src/test/ui/associated-type-bounds/inside-adt.stderr
Normal file
79
src/test/ui/associated-type-bounds/inside-adt.stderr
Normal file
|
|
@ -0,0 +1,79 @@
|
|||
error: associated type bounds are not allowed within structs, enums, or unions
|
||||
--> $DIR/inside-adt.rs:8:29
|
||||
|
|
||||
LL | struct S1 { f: dyn Iterator<Item: Copy> }
|
||||
| ^^^^^^^^^^
|
||||
|
||||
error: associated type bounds are not allowed within structs, enums, or unions
|
||||
--> $DIR/inside-adt.rs:11:33
|
||||
|
|
||||
LL | struct S2 { f: Box<dyn Iterator<Item: Copy>> }
|
||||
| ^^^^^^^^^^
|
||||
|
||||
error: associated type bounds are not allowed within structs, enums, or unions
|
||||
--> $DIR/inside-adt.rs:14:29
|
||||
|
|
||||
LL | struct S3 { f: dyn Iterator<Item: 'static> }
|
||||
| ^^^^^^^^^^^^^
|
||||
|
||||
error: associated type bounds are not allowed within structs, enums, or unions
|
||||
--> $DIR/inside-adt.rs:18:26
|
||||
|
|
||||
LL | enum E1 { V(dyn Iterator<Item: Copy>) }
|
||||
| ^^^^^^^^^^
|
||||
|
||||
error: associated type bounds are not allowed within structs, enums, or unions
|
||||
--> $DIR/inside-adt.rs:21:30
|
||||
|
|
||||
LL | enum E2 { V(Box<dyn Iterator<Item: Copy>>) }
|
||||
| ^^^^^^^^^^
|
||||
|
||||
error: associated type bounds are not allowed within structs, enums, or unions
|
||||
--> $DIR/inside-adt.rs:24:26
|
||||
|
|
||||
LL | enum E3 { V(dyn Iterator<Item: 'static>) }
|
||||
| ^^^^^^^^^^^^^
|
||||
|
||||
error: associated type bounds are not allowed within structs, enums, or unions
|
||||
--> $DIR/inside-adt.rs:28:28
|
||||
|
|
||||
LL | union U1 { f: dyn Iterator<Item: Copy> }
|
||||
| ^^^^^^^^^^
|
||||
|
||||
error: associated type bounds are not allowed within structs, enums, or unions
|
||||
--> $DIR/inside-adt.rs:31:32
|
||||
|
|
||||
LL | union U2 { f: Box<dyn Iterator<Item: Copy>> }
|
||||
| ^^^^^^^^^^
|
||||
|
||||
error: associated type bounds are not allowed within structs, enums, or unions
|
||||
--> $DIR/inside-adt.rs:34:28
|
||||
|
|
||||
LL | union U3 { f: dyn Iterator<Item: 'static> }
|
||||
| ^^^^^^^^^^^^^
|
||||
|
||||
error[E0601]: `main` function not found in crate `inside_adt`
|
||||
|
|
||||
= note: consider adding a `main` function to `$DIR/inside-adt.rs`
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: could not find defining uses
|
||||
|
||||
error: aborting due to 19 previous errors
|
||||
|
||||
For more information about this error, try `rustc --explain E0601`.
|
||||
78
src/test/ui/associated-type-bounds/lcsit.rs
Normal file
78
src/test/ui/associated-type-bounds/lcsit.rs
Normal file
|
|
@ -0,0 +1,78 @@
|
|||
// run-pass
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
#![feature(impl_trait_in_bindings)]
|
||||
|
||||
#![allow(non_upper_case_globals)]
|
||||
|
||||
use std::ops::Add;
|
||||
|
||||
trait Tr1 { type As1; fn mk(&self) -> Self::As1; }
|
||||
trait Tr2<'a> { fn tr2(self) -> &'a Self; }
|
||||
|
||||
fn assert_copy<T: Copy>(x: T) { let _x = x; let _x = x; }
|
||||
fn assert_static<T: 'static>(_: T) {}
|
||||
fn assert_forall_tr2<T: for<'a> Tr2<'a>>(_: T) {}
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
struct S1;
|
||||
#[derive(Copy, Clone)]
|
||||
struct S2;
|
||||
impl Tr1 for S1 { type As1 = S2; fn mk(&self) -> Self::As1 { S2 } }
|
||||
|
||||
const cdef_et1: impl Copy + Tr1<As1: Copy> = {
|
||||
let x: impl Copy + Tr1<As1: Copy> = S1;
|
||||
x
|
||||
};
|
||||
static sdef_et1: impl Copy + Tr1<As1: Copy> = cdef_et1;
|
||||
pub fn use_et1() { assert_copy(cdef_et1.mk()); assert_copy(sdef_et1.mk()); }
|
||||
|
||||
const cdef_et2: impl Tr1<As1: 'static> = {
|
||||
let x: impl Tr1<As1: 'static> = S1;
|
||||
x
|
||||
};
|
||||
static sdef_et2: impl Tr1<As1: 'static> = cdef_et2;
|
||||
pub fn use_et2() { assert_static(cdef_et2.mk()); assert_static(sdef_et2.mk()); }
|
||||
|
||||
const cdef_et3: impl Tr1<As1: Clone + Iterator<Item: Add<u8, Output: Into<u8>>>> = {
|
||||
struct A;
|
||||
impl Tr1 for A {
|
||||
type As1 = core::ops::Range<u8>;
|
||||
fn mk(&self) -> Self::As1 { 0..10 }
|
||||
};
|
||||
let x: impl Tr1<As1: Clone + Iterator<Item: Add<u8, Output: Into<u8>>>> = A;
|
||||
x
|
||||
};
|
||||
pub fn use_et3() {
|
||||
let _0 = cdef_et3.mk().clone();
|
||||
let mut s = 0u8;
|
||||
for _1 in _0 {
|
||||
let _2 = _1 + 1u8;
|
||||
s += _2.into();
|
||||
}
|
||||
assert_eq!(s, (0..10).map(|x| x + 1).sum());
|
||||
}
|
||||
|
||||
const cdef_et4: impl Copy + Tr1<As1: for<'a> Tr2<'a>> = {
|
||||
#[derive(Copy, Clone)]
|
||||
struct A;
|
||||
impl Tr1 for A {
|
||||
type As1 = A;
|
||||
fn mk(&self) -> A { A }
|
||||
}
|
||||
impl<'a> Tr2<'a> for A {
|
||||
fn tr2(self) -> &'a Self { &A }
|
||||
}
|
||||
let x: impl Copy + Tr1<As1: for<'a> Tr2<'a>> = A;
|
||||
x
|
||||
};
|
||||
|
||||
static sdef_et4: impl Copy + Tr1<As1: for<'a> Tr2<'a>> = cdef_et4;
|
||||
pub fn use_et4() { assert_forall_tr2(cdef_et4.mk()); assert_forall_tr2(sdef_et4.mk()); }
|
||||
|
||||
fn main() {
|
||||
let _ = use_et1();
|
||||
let _ = use_et2();
|
||||
let _ = use_et3();
|
||||
let _ = use_et4();
|
||||
}
|
||||
6
src/test/ui/associated-type-bounds/lcsit.stderr
Normal file
6
src/test/ui/associated-type-bounds/lcsit.stderr
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
warning: the feature `impl_trait_in_bindings` is incomplete and may cause the compiler to crash
|
||||
--> $DIR/lcsit.rs:4:12
|
||||
|
|
||||
LL | #![feature(impl_trait_in_bindings)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
64
src/test/ui/associated-type-bounds/rpit.rs
Normal file
64
src/test/ui/associated-type-bounds/rpit.rs
Normal file
|
|
@ -0,0 +1,64 @@
|
|||
// run-pass
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
use std::ops::Add;
|
||||
|
||||
trait Tr1 { type As1; fn mk(self) -> Self::As1; }
|
||||
trait Tr2<'a> { fn tr2(self) -> &'a Self; }
|
||||
|
||||
fn assert_copy<T: Copy>(x: T) { let _x = x; let _x = x; }
|
||||
fn assert_static<T: 'static>(_: T) {}
|
||||
fn assert_forall_tr2<T: for<'a> Tr2<'a>>(_: T) {}
|
||||
|
||||
struct S1;
|
||||
#[derive(Copy, Clone)]
|
||||
struct S2;
|
||||
impl Tr1 for S1 { type As1 = S2; fn mk(self) -> Self::As1 { S2 } }
|
||||
|
||||
fn def_et1() -> impl Tr1<As1: Copy> { S1 }
|
||||
pub fn use_et1() { assert_copy(def_et1().mk()); }
|
||||
|
||||
fn def_et2() -> impl Tr1<As1: 'static> { S1 }
|
||||
pub fn use_et2() { assert_static(def_et2().mk()); }
|
||||
|
||||
fn def_et3() -> impl Tr1<As1: Clone + Iterator<Item: Add<u8, Output: Into<u8>>>> {
|
||||
struct A;
|
||||
impl Tr1 for A {
|
||||
type As1 = core::ops::Range<u8>;
|
||||
fn mk(self) -> Self::As1 { 0..10 }
|
||||
};
|
||||
A
|
||||
}
|
||||
|
||||
pub fn use_et3() {
|
||||
let _0 = def_et3().mk().clone();
|
||||
let mut s = 0u8;
|
||||
for _1 in _0 {
|
||||
let _2 = _1 + 1u8;
|
||||
s += _2.into();
|
||||
}
|
||||
assert_eq!(s, (0..10).map(|x| x + 1).sum());
|
||||
}
|
||||
|
||||
fn def_et4() -> impl Tr1<As1: for<'a> Tr2<'a>> {
|
||||
#[derive(Copy, Clone)]
|
||||
struct A;
|
||||
impl Tr1 for A {
|
||||
type As1 = A;
|
||||
fn mk(self) -> A { A }
|
||||
}
|
||||
impl<'a> Tr2<'a> for A {
|
||||
fn tr2(self) -> &'a Self { &A }
|
||||
}
|
||||
A
|
||||
}
|
||||
|
||||
pub fn use_et4() { assert_forall_tr2(def_et4().mk()); }
|
||||
|
||||
fn main() {
|
||||
let _ = use_et1();
|
||||
let _ = use_et2();
|
||||
let _ = use_et3();
|
||||
let _ = use_et4();
|
||||
}
|
||||
115
src/test/ui/associated-type-bounds/struct-bounds.rs
Normal file
115
src/test/ui/associated-type-bounds/struct-bounds.rs
Normal file
|
|
@ -0,0 +1,115 @@
|
|||
// run-pass
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
trait Tr1 { type As1; }
|
||||
trait Tr2 { type As2; }
|
||||
trait Tr3 {}
|
||||
trait Tr4<'a> { type As4; }
|
||||
trait Tr5 { type As5; }
|
||||
|
||||
impl Tr1 for &str { type As1 = bool; }
|
||||
impl Tr2 for bool { type As2 = u8; }
|
||||
impl Tr3 for u8 {}
|
||||
impl Tr1 for () { type As1 = (usize,); }
|
||||
impl<'a> Tr4<'a> for (usize,) { type As4 = u8; }
|
||||
impl Tr5 for bool { type As5 = u16; }
|
||||
|
||||
struct St1<T: Tr1<As1: Tr2>> {
|
||||
outest: T,
|
||||
outer: T::As1,
|
||||
inner: <T::As1 as Tr2>::As2,
|
||||
}
|
||||
|
||||
fn unwrap_1_st1<T: Tr1<As1: Tr2>>(x: St1<T>) -> (T, T::As1, <T::As1 as Tr2>::As2) {
|
||||
(x.outest, x.outer, x.inner)
|
||||
}
|
||||
|
||||
fn unwrap_2_st1<T>(x: St1<T>) -> (T, T::As1, <T::As1 as Tr2>::As2)
|
||||
where
|
||||
T: Tr1,
|
||||
T::As1: Tr2,
|
||||
{
|
||||
unwrap_1_st1(x)
|
||||
}
|
||||
|
||||
struct St2<T: Tr1<As1: Tr2<As2: Tr3>>> {
|
||||
outest: T,
|
||||
outer: T::As1,
|
||||
inner: <T::As1 as Tr2>::As2,
|
||||
}
|
||||
|
||||
struct St3<T: Tr1<As1: 'static>> {
|
||||
outest: T,
|
||||
outer: &'static T::As1,
|
||||
}
|
||||
|
||||
struct St4<'x1, 'x2, T: Tr1<As1: for<'l> Tr4<'l>>> {
|
||||
f1: &'x1 <T::As1 as Tr4<'x1>>::As4,
|
||||
f2: &'x2 <T::As1 as Tr4<'x2>>::As4,
|
||||
}
|
||||
|
||||
struct St5<'x1, 'x2, T: Tr1<As1: for<'l> Tr4<'l, As4: Copy>>> {
|
||||
f1: &'x1 <T::As1 as Tr4<'x1>>::As4,
|
||||
f2: &'x2 <T::As1 as Tr4<'x2>>::As4,
|
||||
}
|
||||
|
||||
struct St6<T>
|
||||
where
|
||||
T: Tr1<As1: Tr2 + 'static + Tr5>,
|
||||
{
|
||||
f0: T,
|
||||
f1: <T::As1 as Tr2>::As2,
|
||||
f2: &'static T::As1,
|
||||
f3: <T::As1 as Tr5>::As5,
|
||||
}
|
||||
|
||||
struct St7<'a, 'b, T> // `<T::As1 as Tr2>::As2: 'a` is implied.
|
||||
where
|
||||
T: Tr1<As1: Tr2>,
|
||||
{
|
||||
f0: &'a T,
|
||||
f1: &'b <T::As1 as Tr2>::As2,
|
||||
}
|
||||
|
||||
fn _use_st7<'a, 'b, T>(x: St7<'a, 'b, T>)
|
||||
where
|
||||
T: Tr1,
|
||||
T::As1: Tr2,
|
||||
{
|
||||
let _: &'a T = &x.f0;
|
||||
}
|
||||
|
||||
struct StSelf<T> where Self: Tr1<As1: Tr2> {
|
||||
f2: <<Self as Tr1>::As1 as Tr2>::As2,
|
||||
}
|
||||
|
||||
impl Tr1 for StSelf<&'static str> { type As1 = bool; }
|
||||
|
||||
fn main() {
|
||||
let st1 = St1 { outest: "foo", outer: true, inner: 42u8 };
|
||||
assert_eq!(("foo", true, 42), unwrap_1_st1(st1));
|
||||
|
||||
let _ = St2 { outest: "foo", outer: true, inner: 42u8 };
|
||||
|
||||
let _ = St3 { outest: "foo", outer: &true };
|
||||
|
||||
let f1 = (1,);
|
||||
let f2 = (2,);
|
||||
let st4 = St4::<()> { f1: &f1.0, f2: &f2.0, };
|
||||
assert_eq!((&1, &2), (st4.f1, st4.f2));
|
||||
|
||||
// FIXME: requires lazy normalization.
|
||||
/*
|
||||
let f1 = (1,);
|
||||
let f2 = (2,);
|
||||
let st5 = St5::<()> { f1: &f1.0, f2: &f2.0, };
|
||||
assert_eq!((&1, &2), (st5.f1, st5.f2));
|
||||
*/
|
||||
|
||||
let st6 = St6 { f0: "bar", f1: 24u8, f2: &true, f3: 12u16, };
|
||||
assert_eq!(("bar", 24, &true, 12), (st6.f0, st6.f1, st6.f2, st6.f3));
|
||||
|
||||
let stself = StSelf::<&'static str> { f2: 42u8 };
|
||||
assert_eq!(stself.f2, 42u8);
|
||||
}
|
||||
116
src/test/ui/associated-type-bounds/trait-params.rs
Normal file
116
src/test/ui/associated-type-bounds/trait-params.rs
Normal file
|
|
@ -0,0 +1,116 @@
|
|||
// compile-pass
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
use std::iter::Once;
|
||||
use std::ops::Range;
|
||||
|
||||
pub trait Three { type A; type B; type C; }
|
||||
pub fn assert_three<T: ?Sized + Three>() {}
|
||||
pub fn assert_iterator<T: Iterator>() {}
|
||||
pub fn assert_copy<T: Copy>() {}
|
||||
pub fn assert_static<T: 'static>() {}
|
||||
pub fn assert_send<T: Send>() {}
|
||||
pub fn assert_forall_into<T: for<'a> Into<&'a u8>>() {}
|
||||
|
||||
struct A; struct B;
|
||||
impl<'a> Into<&'a u8> for A { fn into(self) -> &'a u8 { &0 } }
|
||||
impl Three for B { type A = Range<u8>; type B = Range<u8>; type C = Range<u8>; }
|
||||
|
||||
trait Case1<A, B, C, D, E>
|
||||
where
|
||||
A: Iterator<Item: Copy>,
|
||||
B: Iterator<Item: 'static>,
|
||||
C: Iterator<Item: 'static + Copy + Send>,
|
||||
D: Iterator<Item: for<'a> Into<&'a u8>>,
|
||||
E: Three<A: Iterator<Item: Copy>, B: Iterator<Item: Copy>, C: Iterator<Item: Copy>>,
|
||||
Self: Three<A: 'static, B: Copy, C: Send>,
|
||||
{
|
||||
fn _a() {
|
||||
assert_iterator::<A>();
|
||||
assert_copy::<A::Item>();
|
||||
}
|
||||
fn _b() {
|
||||
assert_iterator::<B>();
|
||||
assert_static::<B::Item>();
|
||||
}
|
||||
fn _c() {
|
||||
assert_iterator::<C>();
|
||||
assert_copy::<C::Item>();
|
||||
assert_static::<C::Item>();
|
||||
assert_send::<C::Item>();
|
||||
}
|
||||
fn _d() {
|
||||
assert_iterator::<D>();
|
||||
assert_forall_into::<D::Item>();
|
||||
}
|
||||
fn _e() {
|
||||
assert_three::<E>();
|
||||
assert_iterator::<E::A>();
|
||||
assert_iterator::<E::B>();
|
||||
assert_iterator::<E::C>();
|
||||
assert_copy::<<E::A as Iterator>::Item>();
|
||||
assert_copy::<<E::B as Iterator>::Item>();
|
||||
assert_copy::<<E::C as Iterator>::Item>();
|
||||
}
|
||||
fn _self() {
|
||||
assert_three::<Self>();
|
||||
assert_copy::<Self::B>();
|
||||
assert_static::<Self::A>();
|
||||
assert_send::<Self::C>();
|
||||
}
|
||||
}
|
||||
|
||||
struct DataCase1;
|
||||
impl Three for DataCase1 { type A = u8; type B = u8; type C = u8; }
|
||||
impl Case1<Range<u8>, Range<u8>, Range<u8>, Once<A>, B> for DataCase1 {}
|
||||
|
||||
trait Case2<
|
||||
A: Iterator<Item: Copy>,
|
||||
B: Iterator<Item: 'static>,
|
||||
C: Iterator<Item: 'static + Copy + Send>,
|
||||
D: Iterator<Item: for<'a> Into<&'a u8>>,
|
||||
E: Three<A: Iterator<Item: Copy>, B: Iterator<Item: Copy>, C: Iterator<Item: Copy>>,
|
||||
>:
|
||||
Three<A: 'static, B: Copy, C: Send>
|
||||
{
|
||||
fn _a() {
|
||||
assert_iterator::<A>();
|
||||
assert_copy::<A::Item>();
|
||||
}
|
||||
fn _b() {
|
||||
assert_iterator::<B>();
|
||||
assert_static::<B::Item>();
|
||||
}
|
||||
fn _c() {
|
||||
assert_iterator::<C>();
|
||||
assert_copy::<C::Item>();
|
||||
assert_static::<C::Item>();
|
||||
assert_send::<C::Item>();
|
||||
}
|
||||
fn _d() {
|
||||
assert_iterator::<D>();
|
||||
assert_forall_into::<D::Item>();
|
||||
}
|
||||
fn _e() {
|
||||
assert_three::<E>();
|
||||
assert_iterator::<E::A>();
|
||||
assert_iterator::<E::B>();
|
||||
assert_iterator::<E::C>();
|
||||
assert_copy::<<E::A as Iterator>::Item>();
|
||||
assert_copy::<<E::B as Iterator>::Item>();
|
||||
assert_copy::<<E::C as Iterator>::Item>();
|
||||
}
|
||||
fn _self() {
|
||||
assert_three::<Self>();
|
||||
assert_copy::<Self::B>();
|
||||
assert_static::<Self::A>();
|
||||
assert_send::<Self::C>();
|
||||
}
|
||||
}
|
||||
|
||||
struct DataCase2;
|
||||
impl Three for DataCase2 { type A = u8; type B = u8; type C = u8; }
|
||||
impl Case2<Range<u8>, Range<u8>, Range<u8>, Once<A>, B> for DataCase2 {}
|
||||
|
||||
fn main() {}
|
||||
19
src/test/ui/associated-type-bounds/type-alias.rs
Normal file
19
src/test/ui/associated-type-bounds/type-alias.rs
Normal file
|
|
@ -0,0 +1,19 @@
|
|||
// compile-pass
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
|
||||
type _TaWhere1<T> where T: Iterator<Item: Copy> = T;
|
||||
type _TaWhere2<T> where T: Iterator<Item: 'static> = T;
|
||||
type _TaWhere3<T> where T: Iterator<Item: 'static> = T;
|
||||
type _TaWhere4<T> where T: Iterator<Item: 'static + Copy + Send> = T;
|
||||
type _TaWhere5<T> where T: Iterator<Item: for<'a> Into<&'a u8>> = T;
|
||||
type _TaWhere6<T> where T: Iterator<Item: Iterator<Item: Copy>> = T;
|
||||
|
||||
type _TaInline1<T: Iterator<Item: Copy>> = T;
|
||||
type _TaInline2<T: Iterator<Item: 'static>> = T;
|
||||
type _TaInline3<T: Iterator<Item: 'static>> = T;
|
||||
type _TaInline4<T: Iterator<Item: 'static + Copy + Send>> = T;
|
||||
type _TaInline5<T: Iterator<Item: for<'a> Into<&'a u8>>> = T;
|
||||
type _TaInline6<T: Iterator<Item: Iterator<Item: Copy>>> = T;
|
||||
|
||||
fn main() {}
|
||||
97
src/test/ui/associated-type-bounds/type-alias.stderr
Normal file
97
src/test/ui/associated-type-bounds/type-alias.stderr
Normal file
|
|
@ -0,0 +1,97 @@
|
|||
warning: where clauses are not enforced in type aliases
|
||||
--> $DIR/type-alias.rs:5:25
|
||||
|
|
||||
LL | type _TaWhere1<T> where T: Iterator<Item: Copy> = T;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= note: #[warn(type_alias_bounds)] on by default
|
||||
= help: the clause will not be checked when the type alias is used, and should be removed
|
||||
|
||||
warning: where clauses are not enforced in type aliases
|
||||
--> $DIR/type-alias.rs:6:25
|
||||
|
|
||||
LL | type _TaWhere2<T> where T: Iterator<Item: 'static> = T;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: the clause will not be checked when the type alias is used, and should be removed
|
||||
|
||||
warning: where clauses are not enforced in type aliases
|
||||
--> $DIR/type-alias.rs:7:25
|
||||
|
|
||||
LL | type _TaWhere3<T> where T: Iterator<Item: 'static> = T;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: the clause will not be checked when the type alias is used, and should be removed
|
||||
|
||||
warning: where clauses are not enforced in type aliases
|
||||
--> $DIR/type-alias.rs:8:25
|
||||
|
|
||||
LL | type _TaWhere4<T> where T: Iterator<Item: 'static + Copy + Send> = T;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: the clause will not be checked when the type alias is used, and should be removed
|
||||
|
||||
warning: where clauses are not enforced in type aliases
|
||||
--> $DIR/type-alias.rs:9:25
|
||||
|
|
||||
LL | type _TaWhere5<T> where T: Iterator<Item: for<'a> Into<&'a u8>> = T;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: the clause will not be checked when the type alias is used, and should be removed
|
||||
|
||||
warning: where clauses are not enforced in type aliases
|
||||
--> $DIR/type-alias.rs:10:25
|
||||
|
|
||||
LL | type _TaWhere6<T> where T: Iterator<Item: Iterator<Item: Copy>> = T;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: the clause will not be checked when the type alias is used, and should be removed
|
||||
|
||||
warning: bounds on generic parameters are not enforced in type aliases
|
||||
--> $DIR/type-alias.rs:12:20
|
||||
|
|
||||
LL | type _TaInline1<T: Iterator<Item: Copy>> = T;
|
||||
| ^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: the bound will not be checked when the type alias is used, and should be removed
|
||||
|
||||
warning: bounds on generic parameters are not enforced in type aliases
|
||||
--> $DIR/type-alias.rs:13:20
|
||||
|
|
||||
LL | type _TaInline2<T: Iterator<Item: 'static>> = T;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: the bound will not be checked when the type alias is used, and should be removed
|
||||
|
||||
warning: bounds on generic parameters are not enforced in type aliases
|
||||
--> $DIR/type-alias.rs:14:20
|
||||
|
|
||||
LL | type _TaInline3<T: Iterator<Item: 'static>> = T;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: the bound will not be checked when the type alias is used, and should be removed
|
||||
|
||||
warning: bounds on generic parameters are not enforced in type aliases
|
||||
--> $DIR/type-alias.rs:15:20
|
||||
|
|
||||
LL | type _TaInline4<T: Iterator<Item: 'static + Copy + Send>> = T;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: the bound will not be checked when the type alias is used, and should be removed
|
||||
|
||||
warning: bounds on generic parameters are not enforced in type aliases
|
||||
--> $DIR/type-alias.rs:16:20
|
||||
|
|
||||
LL | type _TaInline5<T: Iterator<Item: for<'a> Into<&'a u8>>> = T;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: the bound will not be checked when the type alias is used, and should be removed
|
||||
|
||||
warning: bounds on generic parameters are not enforced in type aliases
|
||||
--> $DIR/type-alias.rs:17:20
|
||||
|
|
||||
LL | type _TaInline6<T: Iterator<Item: Iterator<Item: Copy>>> = T;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: the bound will not be checked when the type alias is used, and should be removed
|
||||
|
||||
123
src/test/ui/associated-type-bounds/union-bounds.rs
Normal file
123
src/test/ui/associated-type-bounds/union-bounds.rs
Normal file
|
|
@ -0,0 +1,123 @@
|
|||
// run-pass
|
||||
|
||||
#![feature(associated_type_bounds)]
|
||||
#![feature(untagged_unions)]
|
||||
|
||||
#![allow(unions_with_drop_fields, unused_assignments)]
|
||||
|
||||
trait Tr1 { type As1; }
|
||||
trait Tr2 { type As2; }
|
||||
trait Tr3 { type As3; }
|
||||
trait Tr4<'a> { type As4; }
|
||||
trait Tr5 { type As5; }
|
||||
|
||||
impl Tr1 for &str { type As1 = bool; }
|
||||
impl Tr2 for bool { type As2 = u8; }
|
||||
impl Tr3 for u8 { type As3 = fn() -> u8; }
|
||||
impl Tr1 for () { type As1 = (usize,); }
|
||||
impl<'a> Tr4<'a> for (usize,) { type As4 = u8; }
|
||||
impl Tr5 for bool { type As5 = u16; }
|
||||
|
||||
union Un1<T: Tr1<As1: Tr2>> {
|
||||
outest: T,
|
||||
outer: T::As1,
|
||||
inner: <T::As1 as Tr2>::As2,
|
||||
}
|
||||
|
||||
union Un2<T: Tr1<As1: Tr2<As2: Tr3>>> {
|
||||
outest: T,
|
||||
outer: T::As1,
|
||||
inner: <T::As1 as Tr2>::As2,
|
||||
}
|
||||
|
||||
union Un3<T: Tr1<As1: 'static>> {
|
||||
outest: T,
|
||||
outer: &'static T::As1,
|
||||
}
|
||||
|
||||
union Un4<'x1, 'x2, T: Tr1<As1: for<'l> Tr4<'l>>> {
|
||||
f1: &'x1 <T::As1 as Tr4<'x1>>::As4,
|
||||
f2: &'x2 <T::As1 as Tr4<'x2>>::As4,
|
||||
}
|
||||
|
||||
union _Un5<'x1, 'x2, T: Tr1<As1: for<'l> Tr4<'l, As4: Copy>>> {
|
||||
f1: &'x1 <T::As1 as Tr4<'x1>>::As4,
|
||||
f2: &'x2 <T::As1 as Tr4<'x2>>::As4,
|
||||
}
|
||||
|
||||
union Un6<T>
|
||||
where
|
||||
T: Tr1<As1: Tr2 + 'static + Tr5>,
|
||||
{
|
||||
f0: T,
|
||||
f1: <T::As1 as Tr2>::As2,
|
||||
f2: &'static T::As1,
|
||||
f3: <T::As1 as Tr5>::As5,
|
||||
}
|
||||
|
||||
union _Un7<'a, 'b, T> // `<T::As1 as Tr2>::As2: 'a` is implied.
|
||||
where
|
||||
T: Tr1<As1: Tr2>,
|
||||
{
|
||||
f0: &'a T,
|
||||
f1: &'b <T::As1 as Tr2>::As2,
|
||||
}
|
||||
|
||||
unsafe fn _use_un7<'a, 'b, T>(x: _Un7<'a, 'b, T>)
|
||||
where
|
||||
T: Tr1,
|
||||
T::As1: Tr2,
|
||||
{
|
||||
let _: &'a T = &x.f0;
|
||||
}
|
||||
|
||||
union UnSelf<T> where Self: Tr1<As1: Tr2> {
|
||||
f0: T,
|
||||
f1: <Self as Tr1>::As1,
|
||||
f2: <<Self as Tr1>::As1 as Tr2>::As2,
|
||||
}
|
||||
|
||||
impl Tr1 for UnSelf<&'static str> { type As1 = bool; }
|
||||
|
||||
fn main() {
|
||||
let mut un1 = Un1 { outest: "foo" };
|
||||
un1 = Un1 { outer: true };
|
||||
assert_eq!(unsafe { un1.outer }, true);
|
||||
un1 = Un1 { inner: 42u8 };
|
||||
assert_eq!(unsafe { un1.inner }, 42u8);
|
||||
|
||||
let mut un2 = Un2 { outest: "bar" };
|
||||
assert_eq!(unsafe { un2.outest }, "bar");
|
||||
un2 = Un2 { outer: true };
|
||||
assert_eq!(unsafe { un2.outer }, true);
|
||||
un2 = Un2 { inner: 42u8 };
|
||||
assert_eq!(unsafe { un2.inner }, 42u8);
|
||||
|
||||
let mut un3 = Un3 { outest: "baz" };
|
||||
assert_eq!(unsafe { un3.outest }, "baz");
|
||||
un3 = Un3 { outer: &true };
|
||||
assert_eq!(unsafe { *un3.outer }, true);
|
||||
|
||||
let f1 = (1,);
|
||||
let f2 = (2,);
|
||||
let mut un4 = Un4::<()> { f1: &f1.0 };
|
||||
assert_eq!(1, unsafe { *un4.f1 });
|
||||
un4 = Un4 { f2: &f2.0 };
|
||||
assert_eq!(2, unsafe { *un4.f2 });
|
||||
|
||||
let mut un6 = Un6 { f0: "bar" };
|
||||
assert_eq!(unsafe { un6.f0 }, "bar");
|
||||
un6 = Un6 { f1: 24u8 };
|
||||
assert_eq!(unsafe { un6.f1 }, 24u8);
|
||||
un6 = Un6 { f2: &true };
|
||||
assert_eq!(unsafe { un6.f2 }, &true);
|
||||
un6 = Un6 { f3: 12u16 };
|
||||
assert_eq!(unsafe { un6.f3 }, 12u16);
|
||||
|
||||
let mut unself = UnSelf::<_> { f0: "selfish" };
|
||||
assert_eq!(unsafe { unself.f0 }, "selfish");
|
||||
unself = UnSelf { f1: true };
|
||||
assert_eq!(unsafe { unself.f1 }, true);
|
||||
unself = UnSelf { f2: 24u8 };
|
||||
assert_eq!(unsafe { unself.f2 }, 24u8);
|
||||
}
|
||||
|
|
@ -1,8 +1,8 @@
|
|||
// #[deprecated] can't be used in staged api
|
||||
// #[deprecated] cannot be used in staged API
|
||||
|
||||
#![feature(staged_api)]
|
||||
|
||||
#![stable(feature = "stable_test_feature", since = "1.0.0")]
|
||||
|
||||
#[deprecated]
|
||||
fn main() { } //~ERROR `#[deprecated]` cannot be used in staged api
|
||||
fn main() { } //~ ERROR `#[deprecated]` cannot be used in staged API
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
error: `#[deprecated]` cannot be used in staged api, use `#[rustc_deprecated]` instead
|
||||
error: `#[deprecated]` cannot be used in staged API; use `#[rustc_deprecated]` instead
|
||||
--> $DIR/deprecation-in-staged-api.rs:8:1
|
||||
|
|
||||
LL | fn main() { }
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ mod boo {
|
|||
}
|
||||
}
|
||||
|
||||
// don't actually know the type here
|
||||
// We don't actually know the type here.
|
||||
|
||||
fn bomp2() {
|
||||
let _: &str = bomp(); //~ ERROR mismatched types
|
||||
|
|
|
|||
|
|
@ -0,0 +1,72 @@
|
|||
#![feature(untagged_unions)]
|
||||
|
||||
trait Tr1 { type As1; }
|
||||
trait Tr2 { type As2; }
|
||||
|
||||
struct S1;
|
||||
#[derive(Copy, Clone)]
|
||||
struct S2;
|
||||
impl Tr1 for S1 { type As1 = S2; }
|
||||
|
||||
trait _Tr3 {
|
||||
type A: Iterator<Item: Copy>;
|
||||
//~^ ERROR associated type bounds are unstable
|
||||
|
||||
type B: Iterator<Item: 'static>;
|
||||
//~^ ERROR associated type bounds are unstable
|
||||
}
|
||||
|
||||
struct _St1<T: Tr1<As1: Tr2>> {
|
||||
//~^ ERROR associated type bounds are unstable
|
||||
outest: T,
|
||||
outer: T::As1,
|
||||
inner: <T::As1 as Tr2>::As2,
|
||||
}
|
||||
|
||||
enum _En1<T: Tr1<As1: Tr2>> {
|
||||
//~^ ERROR associated type bounds are unstable
|
||||
Outest(T),
|
||||
Outer(T::As1),
|
||||
Inner(<T::As1 as Tr2>::As2),
|
||||
}
|
||||
|
||||
union _Un1<T: Tr1<As1: Tr2>> {
|
||||
//~^ ERROR associated type bounds are unstable
|
||||
outest: T,
|
||||
outer: T::As1,
|
||||
inner: <T::As1 as Tr2>::As2,
|
||||
}
|
||||
|
||||
type _TaWhere1<T> where T: Iterator<Item: Copy> = T;
|
||||
//~^ ERROR associated type bounds are unstable
|
||||
|
||||
fn _apit(_: impl Tr1<As1: Copy>) {}
|
||||
//~^ ERROR associated type bounds are unstable
|
||||
fn _apit_dyn(_: &dyn Tr1<As1: Copy>) {}
|
||||
//~^ ERROR associated type bounds are unstable
|
||||
|
||||
fn _rpit() -> impl Tr1<As1: Copy> { S1 }
|
||||
//~^ ERROR associated type bounds are unstable
|
||||
|
||||
fn _rpit_dyn() -> Box<dyn Tr1<As1: Copy>> { Box::new(S1) }
|
||||
//~^ ERROR associated type bounds are unstable
|
||||
|
||||
const _cdef: impl Tr1<As1: Copy> = S1;
|
||||
//~^ ERROR associated type bounds are unstable
|
||||
//~| ERROR `impl Trait` not allowed outside of function and inherent method return types [E0562]
|
||||
// FIXME: uncomment when `impl_trait_in_bindings` feature is fixed.
|
||||
// const _cdef_dyn: &dyn Tr1<As1: Copy> = &S1;
|
||||
|
||||
static _sdef: impl Tr1<As1: Copy> = S1;
|
||||
//~^ ERROR associated type bounds are unstable
|
||||
//~| ERROR `impl Trait` not allowed outside of function and inherent method return types [E0562]
|
||||
// FIXME: uncomment when `impl_trait_in_bindings` feature is fixed.
|
||||
// static _sdef_dyn: &dyn Tr1<As1: Copy> = &S1;
|
||||
|
||||
fn main() {
|
||||
let _: impl Tr1<As1: Copy> = S1;
|
||||
//~^ ERROR associated type bounds are unstable
|
||||
//~| ERROR `impl Trait` not allowed outside of function and inherent method return types [E0562]
|
||||
// FIXME: uncomment when `impl_trait_in_bindings` feature is fixed.
|
||||
// let _: &dyn Tr1<As1: Copy> = &S1;
|
||||
}
|
||||
|
|
@ -0,0 +1,145 @@
|
|||
error[E0658]: associated type bounds are unstable
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:12:22
|
||||
|
|
||||
LL | type A: Iterator<Item: Copy>;
|
||||
| ^^^^^^^^^^
|
||||
|
|
||||
= note: for more information, see https://github.com/rust-lang/rust/issues/52662
|
||||
= help: add #![feature(associated_type_bounds)] to the crate attributes to enable
|
||||
|
||||
error[E0658]: associated type bounds are unstable
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:15:22
|
||||
|
|
||||
LL | type B: Iterator<Item: 'static>;
|
||||
| ^^^^^^^^^^^^^
|
||||
|
|
||||
= note: for more information, see https://github.com/rust-lang/rust/issues/52662
|
||||
= help: add #![feature(associated_type_bounds)] to the crate attributes to enable
|
||||
|
||||
error[E0658]: associated type bounds are unstable
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:19:20
|
||||
|
|
||||
LL | struct _St1<T: Tr1<As1: Tr2>> {
|
||||
| ^^^^^^^^
|
||||
|
|
||||
= note: for more information, see https://github.com/rust-lang/rust/issues/52662
|
||||
= help: add #![feature(associated_type_bounds)] to the crate attributes to enable
|
||||
|
||||
error[E0658]: associated type bounds are unstable
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:26:18
|
||||
|
|
||||
LL | enum _En1<T: Tr1<As1: Tr2>> {
|
||||
| ^^^^^^^^
|
||||
|
|
||||
= note: for more information, see https://github.com/rust-lang/rust/issues/52662
|
||||
= help: add #![feature(associated_type_bounds)] to the crate attributes to enable
|
||||
|
||||
error[E0658]: associated type bounds are unstable
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:33:19
|
||||
|
|
||||
LL | union _Un1<T: Tr1<As1: Tr2>> {
|
||||
| ^^^^^^^^
|
||||
|
|
||||
= note: for more information, see https://github.com/rust-lang/rust/issues/52662
|
||||
= help: add #![feature(associated_type_bounds)] to the crate attributes to enable
|
||||
|
||||
error[E0658]: associated type bounds are unstable
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:40:37
|
||||
|
|
||||
LL | type _TaWhere1<T> where T: Iterator<Item: Copy> = T;
|
||||
| ^^^^^^^^^^
|
||||
|
|
||||
= note: for more information, see https://github.com/rust-lang/rust/issues/52662
|
||||
= help: add #![feature(associated_type_bounds)] to the crate attributes to enable
|
||||
|
||||
error[E0658]: associated type bounds are unstable
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:43:22
|
||||
|
|
||||
LL | fn _apit(_: impl Tr1<As1: Copy>) {}
|
||||
| ^^^^^^^^^
|
||||
|
|
||||
= note: for more information, see https://github.com/rust-lang/rust/issues/52662
|
||||
= help: add #![feature(associated_type_bounds)] to the crate attributes to enable
|
||||
|
||||
error[E0658]: associated type bounds are unstable
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:45:26
|
||||
|
|
||||
LL | fn _apit_dyn(_: &dyn Tr1<As1: Copy>) {}
|
||||
| ^^^^^^^^^
|
||||
|
|
||||
= note: for more information, see https://github.com/rust-lang/rust/issues/52662
|
||||
= help: add #![feature(associated_type_bounds)] to the crate attributes to enable
|
||||
|
||||
error[E0658]: associated type bounds are unstable
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:48:24
|
||||
|
|
||||
LL | fn _rpit() -> impl Tr1<As1: Copy> { S1 }
|
||||
| ^^^^^^^^^
|
||||
|
|
||||
= note: for more information, see https://github.com/rust-lang/rust/issues/52662
|
||||
= help: add #![feature(associated_type_bounds)] to the crate attributes to enable
|
||||
|
||||
error[E0658]: associated type bounds are unstable
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:51:31
|
||||
|
|
||||
LL | fn _rpit_dyn() -> Box<dyn Tr1<As1: Copy>> { Box::new(S1) }
|
||||
| ^^^^^^^^^
|
||||
|
|
||||
= note: for more information, see https://github.com/rust-lang/rust/issues/52662
|
||||
= help: add #![feature(associated_type_bounds)] to the crate attributes to enable
|
||||
|
||||
error[E0658]: associated type bounds are unstable
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:54:23
|
||||
|
|
||||
LL | const _cdef: impl Tr1<As1: Copy> = S1;
|
||||
| ^^^^^^^^^
|
||||
|
|
||||
= note: for more information, see https://github.com/rust-lang/rust/issues/52662
|
||||
= help: add #![feature(associated_type_bounds)] to the crate attributes to enable
|
||||
|
||||
error[E0658]: associated type bounds are unstable
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:60:24
|
||||
|
|
||||
LL | static _sdef: impl Tr1<As1: Copy> = S1;
|
||||
| ^^^^^^^^^
|
||||
|
|
||||
= note: for more information, see https://github.com/rust-lang/rust/issues/52662
|
||||
= help: add #![feature(associated_type_bounds)] to the crate attributes to enable
|
||||
|
||||
error[E0658]: associated type bounds are unstable
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:67:21
|
||||
|
|
||||
LL | let _: impl Tr1<As1: Copy> = S1;
|
||||
| ^^^^^^^^^
|
||||
|
|
||||
= note: for more information, see https://github.com/rust-lang/rust/issues/52662
|
||||
= help: add #![feature(associated_type_bounds)] to the crate attributes to enable
|
||||
|
||||
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:54:14
|
||||
|
|
||||
LL | const _cdef: impl Tr1<As1: Copy> = S1;
|
||||
| ^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: add #![feature(impl_trait_in_bindings)] to the crate attributes to enable
|
||||
|
||||
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:60:15
|
||||
|
|
||||
LL | static _sdef: impl Tr1<As1: Copy> = S1;
|
||||
| ^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: add #![feature(impl_trait_in_bindings)] to the crate attributes to enable
|
||||
|
||||
error[E0562]: `impl Trait` not allowed outside of function and inherent method return types
|
||||
--> $DIR/feature-gate-associated_type_bounds.rs:67:12
|
||||
|
|
||||
LL | let _: impl Tr1<As1: Copy> = S1;
|
||||
| ^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: add #![feature(impl_trait_in_bindings)] to the crate attributes to enable
|
||||
|
||||
error: aborting due to 16 previous errors
|
||||
|
||||
Some errors have detailed explanations: E0562, E0658.
|
||||
For more information about an error, try `rustc --explain E0562`.
|
||||
|
|
@ -5,7 +5,7 @@ LL | fn elided(x: &i32) -> impl Copy { x }
|
|||
| - ^^^^^^^^^ opaque type requires that `'1` must outlive `'static`
|
||||
| |
|
||||
| let's call the lifetime of this reference `'1`
|
||||
help: to allow this impl Trait to capture borrowed data with lifetime `'1`, add `'_` as a constraint
|
||||
help: to allow this `impl Trait` to capture borrowed data with lifetime `'1`, add `'_` as a constraint
|
||||
|
|
||||
LL | fn elided(x: &i32) -> impl Copy + '_ { x }
|
||||
| ^^^^^^^^^^^^^^
|
||||
|
|
@ -17,7 +17,7 @@ LL | fn explicit<'a>(x: &'a i32) -> impl Copy { x }
|
|||
| -- ^^^^^^^^^ opaque type requires that `'a` must outlive `'static`
|
||||
| |
|
||||
| lifetime `'a` defined here
|
||||
help: to allow this impl Trait to capture borrowed data with lifetime `'a`, add `'a` as a constraint
|
||||
help: to allow this `impl Trait` to capture borrowed data with lifetime `'a`, add `'a` as a constraint
|
||||
|
|
||||
LL | fn explicit<'a>(x: &'a i32) -> impl Copy + 'a { x }
|
||||
| ^^^^^^^^^^^^^^
|
||||
|
|
|
|||
|
|
@ -5,7 +5,7 @@ LL | fn iter_values_anon(&self) -> impl Iterator<Item=u32> {
|
|||
| - ^^^^^^^^^^^^^^^^^^^^^^^ opaque type requires that `'1` must outlive `'static`
|
||||
| |
|
||||
| let's call the lifetime of this reference `'1`
|
||||
help: to allow this impl Trait to capture borrowed data with lifetime `'1`, add `'_` as a constraint
|
||||
help: to allow this `impl Trait` to capture borrowed data with lifetime `'1`, add `'_` as a constraint
|
||||
|
|
||||
LL | fn iter_values_anon(&self) -> impl Iterator<Item=u32> + '_ {
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
@ -17,7 +17,7 @@ LL | fn iter_values<'a>(&'a self) -> impl Iterator<Item=u32> {
|
|||
| -- ^^^^^^^^^^^^^^^^^^^^^^^ opaque type requires that `'a` must outlive `'static`
|
||||
| |
|
||||
| lifetime `'a` defined here
|
||||
help: to allow this impl Trait to capture borrowed data with lifetime `'a`, add `'a` as a constraint
|
||||
help: to allow this `impl Trait` to capture borrowed data with lifetime `'a`, add `'a` as a constraint
|
||||
|
|
||||
LL | fn iter_values<'a>(&'a self) -> impl Iterator<Item=u32> + 'a {
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
thread 'rustc' panicked at 'assertion failed: rows.iter().all(|r| r.len() == v.len())', src/librustc_mir/hair/pattern/_match.rs:1085:5
|
||||
note: Run with `RUST_BACKTRACE=1` environment variable to display a backtrace.
|
||||
note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace.
|
||||
|
||||
error: internal compiler error: unexpected panic
|
||||
|
||||
|
|
|
|||
14
src/test/ui/symbol-names/basic.stderr
Normal file
14
src/test/ui/symbol-names/basic.stderr
Normal file
|
|
@ -0,0 +1,14 @@
|
|||
error: symbol-name(_ZN5basic4main17hd72940ef9669d526E)
|
||||
--> $DIR/basic.rs:3:1
|
||||
|
|
||||
LL | #[rustc_symbol_name]
|
||||
| ^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
error: def-path(main)
|
||||
--> $DIR/basic.rs:4:1
|
||||
|
|
||||
LL | #[rustc_def_path]
|
||||
| ^^^^^^^^^^^^^^^^^
|
||||
|
||||
error: aborting due to 2 previous errors
|
||||
|
||||
26
src/test/ui/symbol-names/impl1.stderr
Normal file
26
src/test/ui/symbol-names/impl1.stderr
Normal file
|
|
@ -0,0 +1,26 @@
|
|||
error: symbol-name(_ZN5impl13foo3Foo3bar17he53b9bee7600ed8dE)
|
||||
--> $DIR/impl1.rs:8:9
|
||||
|
|
||||
LL | #[rustc_symbol_name]
|
||||
| ^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
error: def-path(foo::Foo::bar)
|
||||
--> $DIR/impl1.rs:9:9
|
||||
|
|
||||
LL | #[rustc_def_path]
|
||||
| ^^^^^^^^^^^^^^^^^
|
||||
|
||||
error: symbol-name(_ZN5impl13bar33_$LT$impl$u20$impl1..foo..Foo$GT$3baz17h86c41f0462d901d4E)
|
||||
--> $DIR/impl1.rs:18:9
|
||||
|
|
||||
LL | #[rustc_symbol_name]
|
||||
| ^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
error: def-path(bar::<impl foo::Foo>::baz)
|
||||
--> $DIR/impl1.rs:19:9
|
||||
|
|
||||
LL | #[rustc_def_path]
|
||||
| ^^^^^^^^^^^^^^^^^
|
||||
|
||||
error: aborting due to 4 previous errors
|
||||
|
||||
|
|
@ -1,44 +1,44 @@
|
|||
// Test ignored_generic_bounds lint warning about bounds in type aliases
|
||||
// Test `ignored_generic_bounds` lint warning about bounds in type aliases.
|
||||
|
||||
// compile-pass
|
||||
#![allow(dead_code)]
|
||||
|
||||
use std::rc::Rc;
|
||||
|
||||
type SVec<T: Send+Send> = Vec<T>;
|
||||
type SVec<T: Send + Send> = Vec<T>;
|
||||
//~^ WARN bounds on generic parameters are not enforced in type aliases [type_alias_bounds]
|
||||
type S2Vec<T> where T: Send = Vec<T>;
|
||||
//~^ WARN where clauses are not enforced in type aliases [type_alias_bounds]
|
||||
type VVec<'b, 'a: 'b+'b> = (&'b u32, Vec<&'a i32>);
|
||||
type VVec<'b, 'a: 'b + 'b> = (&'b u32, Vec<&'a i32>);
|
||||
//~^ WARN bounds on generic parameters are not enforced in type aliases [type_alias_bounds]
|
||||
type WVec<'b, T: 'b+'b> = (&'b u32, Vec<T>);
|
||||
type WVec<'b, T: 'b + 'b> = (&'b u32, Vec<T>);
|
||||
//~^ WARN bounds on generic parameters are not enforced in type aliases [type_alias_bounds]
|
||||
type W2Vec<'b, T> where T: 'b, T: 'b = (&'b u32, Vec<T>);
|
||||
//~^ WARN where clauses are not enforced in type aliases [type_alias_bounds]
|
||||
|
||||
static STATIC : u32 = 0;
|
||||
static STATIC: u32 = 0;
|
||||
|
||||
fn foo<'a>(y: &'a i32) {
|
||||
// If any of the bounds above would matter, the code below would be rejected.
|
||||
// This can be seen when replacing the type aliases above by newtype structs.
|
||||
// (The type aliases have no unused parameters to make that a valid transformation.)
|
||||
let mut x : SVec<_> = Vec::new();
|
||||
let mut x: SVec<_> = Vec::new();
|
||||
x.push(Rc::new(42)); // is not send
|
||||
|
||||
let mut x : S2Vec<_> = Vec::new();
|
||||
x.push(Rc::new(42)); // is not send
|
||||
let mut x: S2Vec<_> = Vec::new();
|
||||
x.push(Rc::new(42)); // is not `Send`
|
||||
|
||||
let mut x : VVec<'static, 'a> = (&STATIC, Vec::new());
|
||||
x.1.push(y); // 'a: 'static does not hold
|
||||
let mut x: VVec<'static, 'a> = (&STATIC, Vec::new());
|
||||
x.1.push(y); // `'a: 'static` does not hold
|
||||
|
||||
let mut x : WVec<'static, &'a i32> = (&STATIC, Vec::new());
|
||||
x.1.push(y); // &'a i32: 'static does not hold
|
||||
let mut x: WVec<'static, &'a i32> = (&STATIC, Vec::new());
|
||||
x.1.push(y); // `&'a i32: 'static` does not hold
|
||||
|
||||
let mut x : W2Vec<'static, &'a i32> = (&STATIC, Vec::new());
|
||||
x.1.push(y); // &'a i32: 'static does not hold
|
||||
let mut x: W2Vec<'static, &'a i32> = (&STATIC, Vec::new());
|
||||
x.1.push(y); // `&'a i32: 'static` does not hold
|
||||
}
|
||||
|
||||
// Bounds are not checked either, i.e., the definition is not necessarily well-formed
|
||||
// Bounds are not checked either; i.e., the definition is not necessarily well-formed.
|
||||
struct Sendable<T: Send>(T);
|
||||
type MySendable<T> = Sendable<T>; // no error here!
|
||||
|
||||
|
|
@ -47,9 +47,9 @@ trait Bound { type Assoc; }
|
|||
type T1<U: Bound> = U::Assoc; //~ WARN not enforced in type aliases
|
||||
type T2<U> where U: Bound = U::Assoc; //~ WARN not enforced in type aliases
|
||||
|
||||
// This errors
|
||||
// type T3<U> = U::Assoc;
|
||||
// Do this instead
|
||||
// This errors:
|
||||
// `type T3<U> = U::Assoc;`
|
||||
// Do this instead:
|
||||
type T4<U> = <U as Bound>::Assoc;
|
||||
|
||||
// Make sure the help about associatd types is not shown incorrectly
|
||||
|
|
|
|||
|
|
@ -1,8 +1,8 @@
|
|||
warning: bounds on generic parameters are not enforced in type aliases
|
||||
--> $DIR/type-alias-bounds.rs:8:14
|
||||
|
|
||||
LL | type SVec<T: Send+Send> = Vec<T>;
|
||||
| ^^^^ ^^^^
|
||||
LL | type SVec<T: Send + Send> = Vec<T>;
|
||||
| ^^^^ ^^^^
|
||||
|
|
||||
= note: #[warn(type_alias_bounds)] on by default
|
||||
= help: the bound will not be checked when the type alias is used, and should be removed
|
||||
|
|
@ -18,16 +18,16 @@ LL | type S2Vec<T> where T: Send = Vec<T>;
|
|||
warning: bounds on generic parameters are not enforced in type aliases
|
||||
--> $DIR/type-alias-bounds.rs:12:19
|
||||
|
|
||||
LL | type VVec<'b, 'a: 'b+'b> = (&'b u32, Vec<&'a i32>);
|
||||
| ^^ ^^
|
||||
LL | type VVec<'b, 'a: 'b + 'b> = (&'b u32, Vec<&'a i32>);
|
||||
| ^^ ^^
|
||||
|
|
||||
= help: the bound will not be checked when the type alias is used, and should be removed
|
||||
|
||||
warning: bounds on generic parameters are not enforced in type aliases
|
||||
--> $DIR/type-alias-bounds.rs:14:18
|
||||
|
|
||||
LL | type WVec<'b, T: 'b+'b> = (&'b u32, Vec<T>);
|
||||
| ^^ ^^
|
||||
LL | type WVec<'b, T: 'b + 'b> = (&'b u32, Vec<T>);
|
||||
| ^^ ^^
|
||||
|
|
||||
= help: the bound will not be checked when the type alias is used, and should be removed
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue