mirror of
https://github.com/rust-lang/rust.git
synced 2025-02-19 18:34:08 +00:00
Move const trait bounds checks to MIR constck
Fixes #109543. When checking paths in HIR typeck, we don't want to check for const predicates since all we want might just be a function pointer. Therefore we move this to MIR constck and check that bounds are met during MIR constck.
This commit is contained in:
parent
cbc064b341
commit
b17e6680d6
@ -722,6 +722,32 @@ impl<'tcx> Visitor<'tcx> for Checker<'_, 'tcx> {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// Check that all trait bounds that are marked as `~const` can be satisfied.
|
||||||
|
//
|
||||||
|
// Typeck only does a "non-const" check since it operates on HIR and cannot distinguish
|
||||||
|
// which path expressions are getting called on and which path expressions are only used
|
||||||
|
// as function pointers. This is required for correctness.
|
||||||
|
let infcx = tcx.infer_ctxt().build();
|
||||||
|
let ocx = ObligationCtxt::new(&infcx);
|
||||||
|
|
||||||
|
let predicates = tcx.predicates_of(callee).instantiate(tcx, substs);
|
||||||
|
let cause = ObligationCause::new(
|
||||||
|
terminator.source_info.span,
|
||||||
|
self.body.source.def_id().expect_local(),
|
||||||
|
ObligationCauseCode::ItemObligation(callee),
|
||||||
|
);
|
||||||
|
let normalized_predicates = ocx.normalize(&cause, param_env, predicates);
|
||||||
|
ocx.register_obligations(traits::predicates_for_generics(
|
||||||
|
|_, _| cause.clone(),
|
||||||
|
self.param_env,
|
||||||
|
normalized_predicates,
|
||||||
|
));
|
||||||
|
|
||||||
|
let errors = ocx.select_all_or_error();
|
||||||
|
if !errors.is_empty() {
|
||||||
|
infcx.err_ctxt().report_fulfillment_errors(&errors);
|
||||||
|
}
|
||||||
|
|
||||||
// Attempting to call a trait method?
|
// Attempting to call a trait method?
|
||||||
if let Some(trait_id) = tcx.trait_of_item(callee) {
|
if let Some(trait_id) = tcx.trait_of_item(callee) {
|
||||||
trace!("attempting to call a trait method");
|
trace!("attempting to call a trait method");
|
||||||
@ -749,31 +775,6 @@ impl<'tcx> Visitor<'tcx> for Checker<'_, 'tcx> {
|
|||||||
selcx.select(&obligation)
|
selcx.select(&obligation)
|
||||||
};
|
};
|
||||||
|
|
||||||
// do a well-formedness check on the trait method being called. This is because typeck only does a
|
|
||||||
// "non-const" check. This is required for correctness here.
|
|
||||||
{
|
|
||||||
let infcx = tcx.infer_ctxt().build();
|
|
||||||
let ocx = ObligationCtxt::new(&infcx);
|
|
||||||
|
|
||||||
let predicates = tcx.predicates_of(callee).instantiate(tcx, substs);
|
|
||||||
let cause = ObligationCause::new(
|
|
||||||
terminator.source_info.span,
|
|
||||||
self.body.source.def_id().expect_local(),
|
|
||||||
ObligationCauseCode::ItemObligation(callee),
|
|
||||||
);
|
|
||||||
let normalized_predicates = ocx.normalize(&cause, param_env, predicates);
|
|
||||||
ocx.register_obligations(traits::predicates_for_generics(
|
|
||||||
|_, _| cause.clone(),
|
|
||||||
self.param_env,
|
|
||||||
normalized_predicates,
|
|
||||||
));
|
|
||||||
|
|
||||||
let errors = ocx.select_all_or_error();
|
|
||||||
if !errors.is_empty() {
|
|
||||||
infcx.err_ctxt().report_fulfillment_errors(&errors);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
match implsrc {
|
match implsrc {
|
||||||
Ok(Some(ImplSource::Param(_, ty::BoundConstness::ConstIfConst))) => {
|
Ok(Some(ImplSource::Param(_, ty::BoundConstness::ConstIfConst))) => {
|
||||||
debug!(
|
debug!(
|
||||||
|
@ -1416,41 +1416,19 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
|||||||
) {
|
) {
|
||||||
let param_env = self.param_env;
|
let param_env = self.param_env;
|
||||||
|
|
||||||
let remap = match self.tcx.def_kind(def_id) {
|
|
||||||
// Associated consts have `Self: ~const Trait` bounds that should be satisfiable when
|
|
||||||
// `Self: Trait` is satisfied because it does not matter whether the impl is `const`.
|
|
||||||
// Therefore we have to remap the param env here to be non-const.
|
|
||||||
hir::def::DefKind::AssocConst => true,
|
|
||||||
hir::def::DefKind::AssocFn
|
|
||||||
if self.tcx.def_kind(self.tcx.parent(def_id)) == hir::def::DefKind::Trait =>
|
|
||||||
{
|
|
||||||
// N.B.: All callsites to this function involve checking a path expression.
|
|
||||||
//
|
|
||||||
// When instantiating a trait method as a function item, it does not actually matter whether
|
|
||||||
// the trait is `const` or not, or whether `where T: ~const Tr` needs to be satisfied as
|
|
||||||
// `const`. If we were to introduce instantiating trait methods as `const fn`s, we would
|
|
||||||
// check that after this, either via a bound `where F: ~const FnOnce` or when coercing to a
|
|
||||||
// `const fn` pointer.
|
|
||||||
//
|
|
||||||
// FIXME(fee1-dead) FIXME(const_trait_impl): update this doc when trait methods can satisfy
|
|
||||||
// `~const FnOnce` or can be coerced to `const fn` pointer.
|
|
||||||
true
|
|
||||||
}
|
|
||||||
_ => false,
|
|
||||||
};
|
|
||||||
let bounds = self.instantiate_bounds(span, def_id, &substs);
|
let bounds = self.instantiate_bounds(span, def_id, &substs);
|
||||||
|
|
||||||
for mut obligation in traits::predicates_for_generics(
|
for obligation in traits::predicates_for_generics(
|
||||||
|idx, predicate_span| {
|
|idx, predicate_span| {
|
||||||
traits::ObligationCause::new(span, self.body_id, code(idx, predicate_span))
|
traits::ObligationCause::new(span, self.body_id, code(idx, predicate_span))
|
||||||
},
|
},
|
||||||
param_env,
|
param_env,
|
||||||
bounds,
|
bounds,
|
||||||
) {
|
) {
|
||||||
if remap {
|
// N.B. We are remapping all predicates to non-const since we don't know if we just
|
||||||
obligation = obligation.without_const(self.tcx);
|
// want them as function pointers or we are calling them from a const-context. The
|
||||||
}
|
// actual checking will occur in `rustc_const_eval::transform::check_consts`.
|
||||||
self.register_predicate(obligation);
|
self.register_predicate(obligation.without_const(self.tcx));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
struct X<const N: usize = {
|
struct X<const N: usize = {
|
||||||
(||1usize)()
|
(||1usize)()
|
||||||
//~^ ERROR cannot call non-const closure
|
//~^ ERROR cannot call non-const closure
|
||||||
|
//~| ERROR the trait bound
|
||||||
}>;
|
}>;
|
||||||
|
|
||||||
fn main() {}
|
fn main() {}
|
||||||
|
@ -1,3 +1,17 @@
|
|||||||
|
error[E0277]: the trait bound `[closure@$DIR/issue-93647.rs:2:6: 2:8]: Fn<()>` is not satisfied
|
||||||
|
--> $DIR/issue-93647.rs:2:5
|
||||||
|
|
|
||||||
|
LL | (||1usize)()
|
||||||
|
| ^^^^^^^^^^^^ expected an `Fn<()>` closure, found `[closure@$DIR/issue-93647.rs:2:6: 2:8]`
|
||||||
|
|
|
||||||
|
= help: the trait `~const Fn<()>` is not implemented for closure `[closure@$DIR/issue-93647.rs:2:6: 2:8]`
|
||||||
|
note: the trait `Fn<()>` is implemented for `[closure@$DIR/issue-93647.rs:2:6: 2:8]`, but that implementation is not `const`
|
||||||
|
--> $DIR/issue-93647.rs:2:5
|
||||||
|
|
|
||||||
|
LL | (||1usize)()
|
||||||
|
| ^^^^^^^^^^^^
|
||||||
|
= note: wrap the `[closure@$DIR/issue-93647.rs:2:6: 2:8]` in a closure with no arguments: `|| { /* code */ }`
|
||||||
|
|
||||||
error[E0015]: cannot call non-const closure in constants
|
error[E0015]: cannot call non-const closure in constants
|
||||||
--> $DIR/issue-93647.rs:2:5
|
--> $DIR/issue-93647.rs:2:5
|
||||||
|
|
|
|
||||||
@ -8,6 +22,7 @@ LL | (||1usize)()
|
|||||||
= note: calls in constants are limited to constant functions, tuple structs and tuple variants
|
= note: calls in constants are limited to constant functions, tuple structs and tuple variants
|
||||||
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
|
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
|
||||||
|
|
||||||
error: aborting due to previous error
|
error: aborting due to 2 previous errors
|
||||||
|
|
||||||
For more information about this error, try `rustc --explain E0015`.
|
Some errors have detailed explanations: E0015, E0277.
|
||||||
|
For more information about an error, try `rustc --explain E0015`.
|
||||||
|
@ -1,44 +1,30 @@
|
|||||||
error[E0277]: can't drop `UnconstDrop` in const contexts
|
error[E0277]: can't drop `UnconstDrop` in const contexts
|
||||||
--> $DIR/const-block-const-bound.rs:20:11
|
--> $DIR/const-block-const-bound.rs:20:9
|
||||||
|
|
|
|
||||||
LL | f(UnconstDrop);
|
LL | f(UnconstDrop);
|
||||||
| - ^^^^^^^^^^^ the trait `~const Destruct` is not implemented for `UnconstDrop`
|
| ^^^^^^^^^^^^^^ the trait `~const Destruct` is not implemented for `UnconstDrop`
|
||||||
| |
|
|
||||||
| required by a bound introduced by this call
|
|
||||||
|
|
|
|
||||||
= note: the trait bound `UnconstDrop: ~const Destruct` is not satisfied
|
= note: the trait bound `UnconstDrop: ~const Destruct` is not satisfied
|
||||||
note: required by a bound in `f`
|
|
||||||
--> $DIR/const-block-const-bound.rs:6:15
|
|
||||||
|
|
|
||||||
LL | const fn f<T: ~const Destruct>(x: T) {}
|
|
||||||
| ^^^^^^^^^^^^^^^ required by this bound in `f`
|
|
||||||
help: consider borrowing here
|
help: consider borrowing here
|
||||||
|
|
|
|
||||||
LL | f(&UnconstDrop);
|
LL | &f(UnconstDrop);
|
||||||
| +
|
| +
|
||||||
LL | f(&mut UnconstDrop);
|
LL | &mut f(UnconstDrop);
|
||||||
| ++++
|
| ++++
|
||||||
|
|
||||||
error[E0277]: can't drop `NonDrop` in const contexts
|
error[E0277]: can't drop `NonDrop` in const contexts
|
||||||
--> $DIR/const-block-const-bound.rs:22:11
|
--> $DIR/const-block-const-bound.rs:22:9
|
||||||
|
|
|
|
||||||
LL | f(NonDrop);
|
LL | f(NonDrop);
|
||||||
| - ^^^^^^^ the trait `~const Destruct` is not implemented for `NonDrop`
|
| ^^^^^^^^^^ the trait `~const Destruct` is not implemented for `NonDrop`
|
||||||
| |
|
|
||||||
| required by a bound introduced by this call
|
|
||||||
|
|
|
|
||||||
= note: the trait bound `NonDrop: ~const Destruct` is not satisfied
|
= note: the trait bound `NonDrop: ~const Destruct` is not satisfied
|
||||||
note: required by a bound in `f`
|
|
||||||
--> $DIR/const-block-const-bound.rs:6:15
|
|
||||||
|
|
|
||||||
LL | const fn f<T: ~const Destruct>(x: T) {}
|
|
||||||
| ^^^^^^^^^^^^^^^ required by this bound in `f`
|
|
||||||
help: consider borrowing here
|
help: consider borrowing here
|
||||||
|
|
|
|
||||||
LL | f(&NonDrop);
|
LL | &f(NonDrop);
|
||||||
| +
|
| +
|
||||||
LL | f(&mut NonDrop);
|
LL | &mut f(NonDrop);
|
||||||
| ++++
|
| ++++
|
||||||
|
|
||||||
error: aborting due to 2 previous errors
|
error: aborting due to 2 previous errors
|
||||||
|
|
||||||
|
@ -5,5 +5,6 @@ fn main() {
|
|||||||
match () {
|
match () {
|
||||||
const { (|| {})() } => {}
|
const { (|| {})() } => {}
|
||||||
//~^ ERROR cannot call non-const closure in constants
|
//~^ ERROR cannot call non-const closure in constants
|
||||||
|
//~| ERROR the trait bound
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,3 +1,17 @@
|
|||||||
|
error[E0277]: the trait bound `[closure@$DIR/invalid-inline-const-in-match-arm.rs:6:18: 6:20]: Fn<()>` is not satisfied
|
||||||
|
--> $DIR/invalid-inline-const-in-match-arm.rs:6:17
|
||||||
|
|
|
||||||
|
LL | const { (|| {})() } => {}
|
||||||
|
| ^^^^^^^^^ expected an `Fn<()>` closure, found `[closure@$DIR/invalid-inline-const-in-match-arm.rs:6:18: 6:20]`
|
||||||
|
|
|
||||||
|
= help: the trait `~const Fn<()>` is not implemented for closure `[closure@$DIR/invalid-inline-const-in-match-arm.rs:6:18: 6:20]`
|
||||||
|
note: the trait `Fn<()>` is implemented for `[closure@$DIR/invalid-inline-const-in-match-arm.rs:6:18: 6:20]`, but that implementation is not `const`
|
||||||
|
--> $DIR/invalid-inline-const-in-match-arm.rs:6:17
|
||||||
|
|
|
||||||
|
LL | const { (|| {})() } => {}
|
||||||
|
| ^^^^^^^^^
|
||||||
|
= note: wrap the `[closure@$DIR/invalid-inline-const-in-match-arm.rs:6:18: 6:20]` in a closure with no arguments: `|| { /* code */ }`
|
||||||
|
|
||||||
error[E0015]: cannot call non-const closure in constants
|
error[E0015]: cannot call non-const closure in constants
|
||||||
--> $DIR/invalid-inline-const-in-match-arm.rs:6:17
|
--> $DIR/invalid-inline-const-in-match-arm.rs:6:17
|
||||||
|
|
|
|
||||||
@ -8,6 +22,7 @@ LL | const { (|| {})() } => {}
|
|||||||
= note: calls in constants are limited to constant functions, tuple structs and tuple variants
|
= note: calls in constants are limited to constant functions, tuple structs and tuple variants
|
||||||
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
|
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
|
||||||
|
|
||||||
error: aborting due to previous error
|
error: aborting due to 2 previous errors
|
||||||
|
|
||||||
For more information about this error, try `rustc --explain E0015`.
|
Some errors have detailed explanations: E0015, E0277.
|
||||||
|
For more information about an error, try `rustc --explain E0015`.
|
||||||
|
@ -3,6 +3,7 @@
|
|||||||
const X: u8 =
|
const X: u8 =
|
||||||
|| -> u8 { 5 }()
|
|| -> u8 { 5 }()
|
||||||
//~^ ERROR cannot call non-const closure
|
//~^ ERROR cannot call non-const closure
|
||||||
|
//~| ERROR the trait bound
|
||||||
;
|
;
|
||||||
|
|
||||||
fn main() {}
|
fn main() {}
|
||||||
|
@ -1,3 +1,17 @@
|
|||||||
|
error[E0277]: the trait bound `[closure@$DIR/issue-28113.rs:4:5: 4:13]: Fn<()>` is not satisfied
|
||||||
|
--> $DIR/issue-28113.rs:4:5
|
||||||
|
|
|
||||||
|
LL | || -> u8 { 5 }()
|
||||||
|
| ^^^^^^^^^^^^^^^^ expected an `Fn<()>` closure, found `[closure@$DIR/issue-28113.rs:4:5: 4:13]`
|
||||||
|
|
|
||||||
|
= help: the trait `~const Fn<()>` is not implemented for closure `[closure@$DIR/issue-28113.rs:4:5: 4:13]`
|
||||||
|
note: the trait `Fn<()>` is implemented for `[closure@$DIR/issue-28113.rs:4:5: 4:13]`, but that implementation is not `const`
|
||||||
|
--> $DIR/issue-28113.rs:4:5
|
||||||
|
|
|
||||||
|
LL | || -> u8 { 5 }()
|
||||||
|
| ^^^^^^^^^^^^^^^^
|
||||||
|
= note: wrap the `[closure@$DIR/issue-28113.rs:4:5: 4:13]` in a closure with no arguments: `|| { /* code */ }`
|
||||||
|
|
||||||
error[E0015]: cannot call non-const closure in constants
|
error[E0015]: cannot call non-const closure in constants
|
||||||
--> $DIR/issue-28113.rs:4:5
|
--> $DIR/issue-28113.rs:4:5
|
||||||
|
|
|
|
||||||
@ -8,6 +22,7 @@ LL | || -> u8 { 5 }()
|
|||||||
= note: calls in constants are limited to constant functions, tuple structs and tuple variants
|
= note: calls in constants are limited to constant functions, tuple structs and tuple variants
|
||||||
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
|
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
|
||||||
|
|
||||||
error: aborting due to previous error
|
error: aborting due to 2 previous errors
|
||||||
|
|
||||||
For more information about this error, try `rustc --explain E0015`.
|
Some errors have detailed explanations: E0015, E0277.
|
||||||
|
For more information about an error, try `rustc --explain E0015`.
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
const fn foo() { (||{})() }
|
const fn foo() { (||{})() }
|
||||||
//~^ ERROR cannot call non-const closure
|
//~^ ERROR cannot call non-const closure
|
||||||
|
//~| ERROR the trait bound
|
||||||
|
|
||||||
const fn bad(input: fn()) {
|
const fn bad(input: fn()) {
|
||||||
input()
|
input()
|
||||||
|
@ -1,3 +1,17 @@
|
|||||||
|
error[E0277]: the trait bound `[closure@$DIR/issue-56164.rs:1:19: 1:21]: Fn<()>` is not satisfied
|
||||||
|
--> $DIR/issue-56164.rs:1:18
|
||||||
|
|
|
||||||
|
LL | const fn foo() { (||{})() }
|
||||||
|
| ^^^^^^^^ expected an `Fn<()>` closure, found `[closure@$DIR/issue-56164.rs:1:19: 1:21]`
|
||||||
|
|
|
||||||
|
= help: the trait `~const Fn<()>` is not implemented for closure `[closure@$DIR/issue-56164.rs:1:19: 1:21]`
|
||||||
|
note: the trait `Fn<()>` is implemented for `[closure@$DIR/issue-56164.rs:1:19: 1:21]`, but that implementation is not `const`
|
||||||
|
--> $DIR/issue-56164.rs:1:18
|
||||||
|
|
|
||||||
|
LL | const fn foo() { (||{})() }
|
||||||
|
| ^^^^^^^^
|
||||||
|
= note: wrap the `[closure@$DIR/issue-56164.rs:1:19: 1:21]` in a closure with no arguments: `|| { /* code */ }`
|
||||||
|
|
||||||
error[E0015]: cannot call non-const closure in constant functions
|
error[E0015]: cannot call non-const closure in constant functions
|
||||||
--> $DIR/issue-56164.rs:1:18
|
--> $DIR/issue-56164.rs:1:18
|
||||||
|
|
|
|
||||||
@ -9,7 +23,7 @@ LL | const fn foo() { (||{})() }
|
|||||||
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
|
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
|
||||||
|
|
||||||
error: function pointer calls are not allowed in constant functions
|
error: function pointer calls are not allowed in constant functions
|
||||||
--> $DIR/issue-56164.rs:5:5
|
--> $DIR/issue-56164.rs:6:5
|
||||||
|
|
|
|
||||||
LL | input()
|
LL | input()
|
||||||
| ^^^^^^^
|
| ^^^^^^^
|
||||||
@ -26,6 +40,7 @@ note: erroneous constant used
|
|||||||
LL | const fn foo() { (||{})() }
|
LL | const fn foo() { (||{})() }
|
||||||
| ^^^^^^
|
| ^^^^^^
|
||||||
|
|
||||||
error: aborting due to 2 previous errors
|
error: aborting due to 3 previous errors
|
||||||
|
|
||||||
For more information about this error, try `rustc --explain E0015`.
|
Some errors have detailed explanations: E0015, E0277.
|
||||||
|
For more information about an error, try `rustc --explain E0015`.
|
||||||
|
@ -4,6 +4,7 @@
|
|||||||
|
|
||||||
struct Bug {
|
struct Bug {
|
||||||
a: [(); (|| { 0 })()] //~ ERROR cannot call non-const closure
|
a: [(); (|| { 0 })()] //~ ERROR cannot call non-const closure
|
||||||
|
//~^ ERROR the trait bound
|
||||||
}
|
}
|
||||||
|
|
||||||
fn main() {}
|
fn main() {}
|
||||||
|
@ -1,3 +1,17 @@
|
|||||||
|
error[E0277]: the trait bound `[closure@$DIR/issue-68542-closure-in-array-len.rs:6:14: 6:16]: Fn<()>` is not satisfied
|
||||||
|
--> $DIR/issue-68542-closure-in-array-len.rs:6:13
|
||||||
|
|
|
||||||
|
LL | a: [(); (|| { 0 })()]
|
||||||
|
| ^^^^^^^^^^^^ expected an `Fn<()>` closure, found `[closure@$DIR/issue-68542-closure-in-array-len.rs:6:14: 6:16]`
|
||||||
|
|
|
||||||
|
= help: the trait `~const Fn<()>` is not implemented for closure `[closure@$DIR/issue-68542-closure-in-array-len.rs:6:14: 6:16]`
|
||||||
|
note: the trait `Fn<()>` is implemented for `[closure@$DIR/issue-68542-closure-in-array-len.rs:6:14: 6:16]`, but that implementation is not `const`
|
||||||
|
--> $DIR/issue-68542-closure-in-array-len.rs:6:13
|
||||||
|
|
|
||||||
|
LL | a: [(); (|| { 0 })()]
|
||||||
|
| ^^^^^^^^^^^^
|
||||||
|
= note: wrap the `[closure@$DIR/issue-68542-closure-in-array-len.rs:6:14: 6:16]` in a closure with no arguments: `|| { /* code */ }`
|
||||||
|
|
||||||
error[E0015]: cannot call non-const closure in constants
|
error[E0015]: cannot call non-const closure in constants
|
||||||
--> $DIR/issue-68542-closure-in-array-len.rs:6:13
|
--> $DIR/issue-68542-closure-in-array-len.rs:6:13
|
||||||
|
|
|
|
||||||
@ -8,6 +22,7 @@ LL | a: [(); (|| { 0 })()]
|
|||||||
= note: calls in constants are limited to constant functions, tuple structs and tuple variants
|
= note: calls in constants are limited to constant functions, tuple structs and tuple variants
|
||||||
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
|
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
|
||||||
|
|
||||||
error: aborting due to previous error
|
error: aborting due to 2 previous errors
|
||||||
|
|
||||||
For more information about this error, try `rustc --explain E0015`.
|
Some errors have detailed explanations: E0015, E0277.
|
||||||
|
For more information about an error, try `rustc --explain E0015`.
|
||||||
|
@ -11,4 +11,5 @@ fn main() {
|
|||||||
//~| ERROR cannot convert
|
//~| ERROR cannot convert
|
||||||
//~| ERROR mutable references
|
//~| ERROR mutable references
|
||||||
//~| ERROR cannot call
|
//~| ERROR cannot call
|
||||||
|
//~| ERROR the trait bound
|
||||||
}
|
}
|
||||||
|
@ -58,6 +58,19 @@ LL | [(); { for _ in 0usize.. {}; 0}];
|
|||||||
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
|
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
|
||||||
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
|
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
|
||||||
|
|
||||||
|
error[E0277]: the trait bound `RangeFrom<usize>: Iterator` is not satisfied
|
||||||
|
--> $DIR/issue-52443.rs:9:21
|
||||||
|
|
|
||||||
|
LL | [(); { for _ in 0usize.. {}; 0}];
|
||||||
|
| ^^^^^^^^ `RangeFrom<usize>` is not an iterator
|
||||||
|
|
|
||||||
|
= help: the trait `~const Iterator` is not implemented for `RangeFrom<usize>`
|
||||||
|
note: the trait `Iterator` is implemented for `RangeFrom<usize>`, but that implementation is not `const`
|
||||||
|
--> $DIR/issue-52443.rs:9:21
|
||||||
|
|
|
||||||
|
LL | [(); { for _ in 0usize.. {}; 0}];
|
||||||
|
| ^^^^^^^^
|
||||||
|
|
||||||
error[E0015]: cannot call non-const fn `<RangeFrom<usize> as Iterator>::next` in constants
|
error[E0015]: cannot call non-const fn `<RangeFrom<usize> as Iterator>::next` in constants
|
||||||
--> $DIR/issue-52443.rs:9:21
|
--> $DIR/issue-52443.rs:9:21
|
||||||
|
|
|
|
||||||
@ -67,7 +80,7 @@ LL | [(); { for _ in 0usize.. {}; 0}];
|
|||||||
= note: calls in constants are limited to constant functions, tuple structs and tuple variants
|
= note: calls in constants are limited to constant functions, tuple structs and tuple variants
|
||||||
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
|
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
|
||||||
|
|
||||||
error: aborting due to 6 previous errors; 1 warning emitted
|
error: aborting due to 7 previous errors; 1 warning emitted
|
||||||
|
|
||||||
Some errors have detailed explanations: E0015, E0308, E0658.
|
Some errors have detailed explanations: E0015, E0277, E0308, E0658.
|
||||||
For more information about an error, try `rustc --explain E0015`.
|
For more information about an error, try `rustc --explain E0015`.
|
||||||
|
@ -1,21 +1,14 @@
|
|||||||
error[E0277]: the trait bound `S: ~const Foo` is not satisfied
|
error[E0277]: the trait bound `S: ~const Foo` is not satisfied
|
||||||
--> $DIR/call-generic-method-nonconst.rs:23:34
|
--> $DIR/call-generic-method-nonconst.rs:23:22
|
||||||
|
|
|
|
||||||
LL | pub const EQ: bool = equals_self(&S);
|
LL | pub const EQ: bool = equals_self(&S);
|
||||||
| ----------- ^^ the trait `~const Foo` is not implemented for `S`
|
| ^^^^^^^^^^^^^^^ the trait `~const Foo` is not implemented for `S`
|
||||||
| |
|
|
||||||
| required by a bound introduced by this call
|
|
||||||
|
|
|
|
||||||
note: the trait `Foo` is implemented for `S`, but that implementation is not `const`
|
note: the trait `Foo` is implemented for `S`, but that implementation is not `const`
|
||||||
--> $DIR/call-generic-method-nonconst.rs:23:34
|
--> $DIR/call-generic-method-nonconst.rs:23:22
|
||||||
|
|
|
|
||||||
LL | pub const EQ: bool = equals_self(&S);
|
LL | pub const EQ: bool = equals_self(&S);
|
||||||
| ^^
|
| ^^^^^^^^^^^^^^^
|
||||||
note: required by a bound in `equals_self`
|
|
||||||
--> $DIR/call-generic-method-nonconst.rs:16:25
|
|
||||||
|
|
|
||||||
LL | const fn equals_self<T: ~const Foo>(t: &T) -> bool {
|
|
||||||
| ^^^^^^^^^^ required by this bound in `equals_self`
|
|
||||||
|
|
||||||
error: aborting due to previous error
|
error: aborting due to previous error
|
||||||
|
|
||||||
|
@ -1,22 +1,15 @@
|
|||||||
error[E0277]: the trait bound `(): ~const Tr` is not satisfied in `fn(()) -> i32 {<() as Tr>::a}`
|
error[E0277]: the trait bound `(): ~const Tr` is not satisfied in `fn(()) -> i32 {<() as Tr>::a}`
|
||||||
--> $DIR/const-closure-trait-method-fail.rs:16:42
|
--> $DIR/const-closure-trait-method-fail.rs:16:23
|
||||||
|
|
|
|
||||||
LL | const _: () = assert!(need_const_closure(Tr::a) == 42);
|
LL | const _: () = assert!(need_const_closure(Tr::a) == 42);
|
||||||
| ------------------ ^^^^^ within `fn(()) -> i32 {<() as Tr>::a}`, the trait `~const Tr` is not implemented for `()`
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^ within `fn(()) -> i32 {<() as Tr>::a}`, the trait `~const Tr` is not implemented for `()`
|
||||||
| |
|
|
||||||
| required by a bound introduced by this call
|
|
||||||
|
|
|
|
||||||
note: the trait `Tr` is implemented for `()`, but that implementation is not `const`
|
note: the trait `Tr` is implemented for `()`, but that implementation is not `const`
|
||||||
--> $DIR/const-closure-trait-method-fail.rs:16:42
|
--> $DIR/const-closure-trait-method-fail.rs:16:23
|
||||||
|
|
|
|
||||||
LL | const _: () = assert!(need_const_closure(Tr::a) == 42);
|
LL | const _: () = assert!(need_const_closure(Tr::a) == 42);
|
||||||
| ^^^^^
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
= note: required because it appears within the type `fn(()) -> i32 {<() as Tr>::a}`
|
= note: required because it appears within the type `fn(()) -> i32 {<() as Tr>::a}`
|
||||||
note: required by a bound in `need_const_closure`
|
|
||||||
--> $DIR/const-closure-trait-method-fail.rs:12:32
|
|
||||||
|
|
|
||||||
LL | const fn need_const_closure<T: ~const FnOnce(()) -> i32>(x: T) -> i32 {
|
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^ required by this bound in `need_const_closure`
|
|
||||||
|
|
||||||
error: aborting due to previous error
|
error: aborting due to previous error
|
||||||
|
|
||||||
|
@ -0,0 +1,50 @@
|
|||||||
|
error[E0277]: the trait bound `NonTrivialDrop: ~const A` is not satisfied
|
||||||
|
--> $DIR/const-drop-fail-2.rs:31:23
|
||||||
|
|
|
||||||
|
LL | const _: () = check::<ConstDropImplWithBounds<NonTrivialDrop>>(ConstDropImplWithBounds(PhantomData));
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `~const A` is not implemented for `NonTrivialDrop`
|
||||||
|
|
|
||||||
|
note: the trait `A` is implemented for `NonTrivialDrop`, but that implementation is not `const`
|
||||||
|
--> $DIR/const-drop-fail-2.rs:31:23
|
||||||
|
|
|
||||||
|
LL | const _: () = check::<ConstDropImplWithBounds<NonTrivialDrop>>(ConstDropImplWithBounds(PhantomData));
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
|
note: required by a bound in `ConstDropImplWithBounds`
|
||||||
|
--> $DIR/const-drop-fail-2.rs:21:35
|
||||||
|
|
|
||||||
|
LL | struct ConstDropImplWithBounds<T: ~const A>(PhantomData<T>);
|
||||||
|
| ^^^^^^^^ required by this bound in `ConstDropImplWithBounds`
|
||||||
|
|
||||||
|
error[E0277]: the trait bound `NonTrivialDrop: ~const A` is not satisfied
|
||||||
|
--> $DIR/const-drop-fail-2.rs:31:64
|
||||||
|
|
|
||||||
|
LL | const _: () = check::<ConstDropImplWithBounds<NonTrivialDrop>>(ConstDropImplWithBounds(PhantomData));
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `~const A` is not implemented for `NonTrivialDrop`
|
||||||
|
|
|
||||||
|
note: the trait `A` is implemented for `NonTrivialDrop`, but that implementation is not `const`
|
||||||
|
--> $DIR/const-drop-fail-2.rs:31:64
|
||||||
|
|
|
||||||
|
LL | const _: () = check::<ConstDropImplWithBounds<NonTrivialDrop>>(ConstDropImplWithBounds(PhantomData));
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
|
note: required by a bound in `ConstDropImplWithBounds`
|
||||||
|
--> $DIR/const-drop-fail-2.rs:21:35
|
||||||
|
|
|
||||||
|
LL | struct ConstDropImplWithBounds<T: ~const A>(PhantomData<T>);
|
||||||
|
| ^^^^^^^^ required by this bound in `ConstDropImplWithBounds`
|
||||||
|
|
||||||
|
error[E0367]: `Drop` impl requires `T: ~const A` but the struct it is implemented for does not
|
||||||
|
--> $DIR/const-drop-fail-2.rs:37:9
|
||||||
|
|
|
||||||
|
LL | impl<T: ~const A> const Drop for ConstDropImplWithNonConstBounds<T> {
|
||||||
|
| ^^^^^^^^
|
||||||
|
|
|
||||||
|
note: the implementor must specify the same requirement
|
||||||
|
--> $DIR/const-drop-fail-2.rs:35:1
|
||||||
|
|
|
||||||
|
LL | struct ConstDropImplWithNonConstBounds<T: A>(PhantomData<T>);
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
|
|
||||||
|
error: aborting due to 3 previous errors
|
||||||
|
|
||||||
|
Some errors have detailed explanations: E0277, E0367.
|
||||||
|
For more information about an error, try `rustc --explain E0277`.
|
44
tests/ui/rfc-2632-const-trait-impl/const-drop-fail-2.rs
Normal file
44
tests/ui/rfc-2632-const-trait-impl/const-drop-fail-2.rs
Normal file
@ -0,0 +1,44 @@
|
|||||||
|
// revisions: stock precise
|
||||||
|
#![feature(const_trait_impl)]
|
||||||
|
#![feature(const_mut_refs)]
|
||||||
|
#![cfg_attr(precise, feature(const_precise_live_drops))]
|
||||||
|
|
||||||
|
use std::marker::{Destruct, PhantomData};
|
||||||
|
|
||||||
|
struct NonTrivialDrop;
|
||||||
|
|
||||||
|
impl Drop for NonTrivialDrop {
|
||||||
|
fn drop(&mut self) {
|
||||||
|
println!("Non trivial drop");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[const_trait]
|
||||||
|
trait A { fn a() { } }
|
||||||
|
|
||||||
|
impl A for NonTrivialDrop {}
|
||||||
|
|
||||||
|
struct ConstDropImplWithBounds<T: ~const A>(PhantomData<T>);
|
||||||
|
|
||||||
|
impl<T: ~const A> const Drop for ConstDropImplWithBounds<T> {
|
||||||
|
fn drop(&mut self) {
|
||||||
|
T::a();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const fn check<T: ~const Destruct>(_: T) {}
|
||||||
|
|
||||||
|
const _: () = check::<ConstDropImplWithBounds<NonTrivialDrop>>(ConstDropImplWithBounds(PhantomData));
|
||||||
|
//~^ ERROR the trait bound
|
||||||
|
//~| ERROR the trait bound
|
||||||
|
|
||||||
|
struct ConstDropImplWithNonConstBounds<T: A>(PhantomData<T>);
|
||||||
|
|
||||||
|
impl<T: ~const A> const Drop for ConstDropImplWithNonConstBounds<T> {
|
||||||
|
//~^ ERROR `Drop` impl requires `T: ~const A` but the struct it is implemented for does not
|
||||||
|
fn drop(&mut self) {
|
||||||
|
T::a();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn main() {}
|
@ -0,0 +1,50 @@
|
|||||||
|
error[E0277]: the trait bound `NonTrivialDrop: ~const A` is not satisfied
|
||||||
|
--> $DIR/const-drop-fail-2.rs:31:23
|
||||||
|
|
|
||||||
|
LL | const _: () = check::<ConstDropImplWithBounds<NonTrivialDrop>>(ConstDropImplWithBounds(PhantomData));
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `~const A` is not implemented for `NonTrivialDrop`
|
||||||
|
|
|
||||||
|
note: the trait `A` is implemented for `NonTrivialDrop`, but that implementation is not `const`
|
||||||
|
--> $DIR/const-drop-fail-2.rs:31:23
|
||||||
|
|
|
||||||
|
LL | const _: () = check::<ConstDropImplWithBounds<NonTrivialDrop>>(ConstDropImplWithBounds(PhantomData));
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
|
note: required by a bound in `ConstDropImplWithBounds`
|
||||||
|
--> $DIR/const-drop-fail-2.rs:21:35
|
||||||
|
|
|
||||||
|
LL | struct ConstDropImplWithBounds<T: ~const A>(PhantomData<T>);
|
||||||
|
| ^^^^^^^^ required by this bound in `ConstDropImplWithBounds`
|
||||||
|
|
||||||
|
error[E0277]: the trait bound `NonTrivialDrop: ~const A` is not satisfied
|
||||||
|
--> $DIR/const-drop-fail-2.rs:31:64
|
||||||
|
|
|
||||||
|
LL | const _: () = check::<ConstDropImplWithBounds<NonTrivialDrop>>(ConstDropImplWithBounds(PhantomData));
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `~const A` is not implemented for `NonTrivialDrop`
|
||||||
|
|
|
||||||
|
note: the trait `A` is implemented for `NonTrivialDrop`, but that implementation is not `const`
|
||||||
|
--> $DIR/const-drop-fail-2.rs:31:64
|
||||||
|
|
|
||||||
|
LL | const _: () = check::<ConstDropImplWithBounds<NonTrivialDrop>>(ConstDropImplWithBounds(PhantomData));
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
|
note: required by a bound in `ConstDropImplWithBounds`
|
||||||
|
--> $DIR/const-drop-fail-2.rs:21:35
|
||||||
|
|
|
||||||
|
LL | struct ConstDropImplWithBounds<T: ~const A>(PhantomData<T>);
|
||||||
|
| ^^^^^^^^ required by this bound in `ConstDropImplWithBounds`
|
||||||
|
|
||||||
|
error[E0367]: `Drop` impl requires `T: ~const A` but the struct it is implemented for does not
|
||||||
|
--> $DIR/const-drop-fail-2.rs:37:9
|
||||||
|
|
|
||||||
|
LL | impl<T: ~const A> const Drop for ConstDropImplWithNonConstBounds<T> {
|
||||||
|
| ^^^^^^^^
|
||||||
|
|
|
||||||
|
note: the implementor must specify the same requirement
|
||||||
|
--> $DIR/const-drop-fail-2.rs:35:1
|
||||||
|
|
|
||||||
|
LL | struct ConstDropImplWithNonConstBounds<T: A>(PhantomData<T>);
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
|
|
||||||
|
error: aborting due to 3 previous errors
|
||||||
|
|
||||||
|
Some errors have detailed explanations: E0277, E0367.
|
||||||
|
For more information about an error, try `rustc --explain E0277`.
|
@ -1,99 +1,58 @@
|
|||||||
error[E0277]: can't drop `NonTrivialDrop` in const contexts
|
error[E0277]: can't drop `NonTrivialDrop` in const contexts
|
||||||
--> $DIR/const-drop-fail.rs:44:5
|
--> $DIR/const-drop-fail.rs:26:23
|
||||||
|
|
|
|
||||||
LL | const _: () = check($exp);
|
LL | const _: () = check($exp);
|
||||||
| ----- required by a bound introduced by this call
|
| ^^^^^^^^^^^ the trait `~const Destruct` is not implemented for `NonTrivialDrop`
|
||||||
...
|
...
|
||||||
LL | NonTrivialDrop,
|
LL | / check_all! {
|
||||||
| ^^^^^^^^^^^^^^ the trait `~const Destruct` is not implemented for `NonTrivialDrop`
|
LL | | NonTrivialDrop,
|
||||||
|
|
LL | | ConstImplWithDropGlue(NonTrivialDrop),
|
||||||
= note: the trait bound `NonTrivialDrop: ~const Destruct` is not satisfied
|
LL | | }
|
||||||
note: required by a bound in `check`
|
| |_- in this macro invocation
|
||||||
--> $DIR/const-drop-fail.rs:35:19
|
|
||||||
|
|
|
||||||
LL | const fn check<T: ~const Destruct>(_: T) {}
|
|
||||||
| ^^^^^^^^^^^^^^^ required by this bound in `check`
|
|
||||||
help: consider borrowing here
|
|
||||||
|
|
|
||||||
LL | &NonTrivialDrop,
|
|
||||||
| +
|
|
||||||
LL | &mut NonTrivialDrop,
|
|
||||||
| ++++
|
|
||||||
|
|
||||||
error[E0277]: can't drop `NonTrivialDrop` in const contexts
|
|
||||||
--> $DIR/const-drop-fail.rs:46:5
|
|
||||||
|
|
|
||||||
LL | const _: () = check($exp);
|
|
||||||
| ----- required by a bound introduced by this call
|
|
||||||
...
|
|
||||||
LL | ConstImplWithDropGlue(NonTrivialDrop),
|
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ within `ConstImplWithDropGlue`, the trait `~const Destruct` is not implemented for `NonTrivialDrop`
|
|
||||||
|
|
|
|
||||||
note: the trait `Destruct` is implemented for `NonTrivialDrop`, but that implementation is not `const`
|
note: the trait `Destruct` is implemented for `NonTrivialDrop`, but that implementation is not `const`
|
||||||
--> $DIR/const-drop-fail.rs:46:5
|
--> $DIR/const-drop-fail.rs:26:23
|
||||||
|
|
|
|
||||||
LL | ConstImplWithDropGlue(NonTrivialDrop),
|
LL | const _: () = check($exp);
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^
|
||||||
|
...
|
||||||
|
LL | / check_all! {
|
||||||
|
LL | | NonTrivialDrop,
|
||||||
|
LL | | ConstImplWithDropGlue(NonTrivialDrop),
|
||||||
|
LL | | }
|
||||||
|
| |_- in this macro invocation
|
||||||
|
= note: this error originates in the macro `check_all` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||||
|
|
||||||
|
error[E0277]: can't drop `NonTrivialDrop` in const contexts
|
||||||
|
--> $DIR/const-drop-fail.rs:26:23
|
||||||
|
|
|
||||||
|
LL | const _: () = check($exp);
|
||||||
|
| ^^^^^^^^^^^ within `ConstImplWithDropGlue`, the trait `~const Destruct` is not implemented for `NonTrivialDrop`
|
||||||
|
...
|
||||||
|
LL | / check_all! {
|
||||||
|
LL | | NonTrivialDrop,
|
||||||
|
LL | | ConstImplWithDropGlue(NonTrivialDrop),
|
||||||
|
LL | | }
|
||||||
|
| |_- in this macro invocation
|
||||||
|
|
|
||||||
|
note: the trait `Destruct` is implemented for `NonTrivialDrop`, but that implementation is not `const`
|
||||||
|
--> $DIR/const-drop-fail.rs:26:23
|
||||||
|
|
|
||||||
|
LL | const _: () = check($exp);
|
||||||
|
| ^^^^^^^^^^^
|
||||||
|
...
|
||||||
|
LL | / check_all! {
|
||||||
|
LL | | NonTrivialDrop,
|
||||||
|
LL | | ConstImplWithDropGlue(NonTrivialDrop),
|
||||||
|
LL | | }
|
||||||
|
| |_- in this macro invocation
|
||||||
note: required because it appears within the type `ConstImplWithDropGlue`
|
note: required because it appears within the type `ConstImplWithDropGlue`
|
||||||
--> $DIR/const-drop-fail.rs:16:8
|
--> $DIR/const-drop-fail.rs:16:8
|
||||||
|
|
|
|
||||||
LL | struct ConstImplWithDropGlue(NonTrivialDrop);
|
LL | struct ConstImplWithDropGlue(NonTrivialDrop);
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^^^^^^^^^^^
|
||||||
note: required by a bound in `check`
|
= note: this error originates in the macro `check_all` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||||
--> $DIR/const-drop-fail.rs:35:19
|
|
||||||
|
|
|
||||||
LL | const fn check<T: ~const Destruct>(_: T) {}
|
|
||||||
| ^^^^^^^^^^^^^^^ required by this bound in `check`
|
|
||||||
|
|
||||||
error[E0277]: the trait bound `NonTrivialDrop: ~const A` is not satisfied
|
error: aborting due to 2 previous errors
|
||||||
--> $DIR/const-drop-fail.rs:48:47
|
|
||||||
|
|
|
||||||
LL | ConstDropImplWithBounds::<NonTrivialDrop>(PhantomData),
|
|
||||||
| ----------------------------------------- ^^^^^^^^^^^ the trait `~const A` is not implemented for `NonTrivialDrop`
|
|
||||||
| |
|
|
||||||
| required by a bound introduced by this call
|
|
||||||
|
|
|
||||||
note: the trait `A` is implemented for `NonTrivialDrop`, but that implementation is not `const`
|
|
||||||
--> $DIR/const-drop-fail.rs:48:47
|
|
||||||
|
|
|
||||||
LL | ConstDropImplWithBounds::<NonTrivialDrop>(PhantomData),
|
|
||||||
| ^^^^^^^^^^^
|
|
||||||
note: required by a bound in `ConstDropImplWithBounds`
|
|
||||||
--> $DIR/const-drop-fail.rs:27:35
|
|
||||||
|
|
|
||||||
LL | struct ConstDropImplWithBounds<T: ~const A>(PhantomData<T>);
|
|
||||||
| ^^^^^^^^ required by this bound in `ConstDropImplWithBounds`
|
|
||||||
|
|
||||||
error[E0277]: the trait bound `NonTrivialDrop: ~const A` is not satisfied
|
For more information about this error, try `rustc --explain E0277`.
|
||||||
--> $DIR/const-drop-fail.rs:48:5
|
|
||||||
|
|
|
||||||
LL | ConstDropImplWithBounds::<NonTrivialDrop>(PhantomData),
|
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `~const A` is not implemented for `NonTrivialDrop`
|
|
||||||
|
|
|
||||||
note: the trait `A` is implemented for `NonTrivialDrop`, but that implementation is not `const`
|
|
||||||
--> $DIR/const-drop-fail.rs:48:5
|
|
||||||
|
|
|
||||||
LL | ConstDropImplWithBounds::<NonTrivialDrop>(PhantomData),
|
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
||||||
note: required by a bound in `ConstDropImplWithBounds`
|
|
||||||
--> $DIR/const-drop-fail.rs:27:35
|
|
||||||
|
|
|
||||||
LL | struct ConstDropImplWithBounds<T: ~const A>(PhantomData<T>);
|
|
||||||
| ^^^^^^^^ required by this bound in `ConstDropImplWithBounds`
|
|
||||||
|
|
||||||
error[E0367]: `Drop` impl requires `T: ~const A` but the struct it is implemented for does not
|
|
||||||
--> $DIR/const-drop-fail.rs:55:9
|
|
||||||
|
|
|
||||||
LL | impl<T: ~const A> const Drop for ConstDropImplWithNonConstBounds<T> {
|
|
||||||
| ^^^^^^^^
|
|
||||||
|
|
|
||||||
note: the implementor must specify the same requirement
|
|
||||||
--> $DIR/const-drop-fail.rs:53:1
|
|
||||||
|
|
|
||||||
LL | struct ConstDropImplWithNonConstBounds<T: A>(PhantomData<T>);
|
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
||||||
|
|
||||||
error: aborting due to 5 previous errors
|
|
||||||
|
|
||||||
Some errors have detailed explanations: E0277, E0367.
|
|
||||||
For more information about an error, try `rustc --explain E0277`.
|
|
||||||
|
@ -19,44 +19,19 @@ impl const Drop for ConstImplWithDropGlue {
|
|||||||
fn drop(&mut self) {}
|
fn drop(&mut self) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[const_trait]
|
|
||||||
trait A { fn a() { } }
|
|
||||||
|
|
||||||
impl A for NonTrivialDrop {}
|
|
||||||
|
|
||||||
struct ConstDropImplWithBounds<T: ~const A>(PhantomData<T>);
|
|
||||||
|
|
||||||
impl<T: ~const A> const Drop for ConstDropImplWithBounds<T> {
|
|
||||||
fn drop(&mut self) {
|
|
||||||
T::a();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
const fn check<T: ~const Destruct>(_: T) {}
|
const fn check<T: ~const Destruct>(_: T) {}
|
||||||
|
|
||||||
macro_rules! check_all {
|
macro_rules! check_all {
|
||||||
($($exp:expr),*$(,)?) => {$(
|
($($exp:expr),*$(,)?) => {$(
|
||||||
const _: () = check($exp);
|
const _: () = check($exp);
|
||||||
|
//~^ ERROR can't drop
|
||||||
|
//~| ERROR can't drop
|
||||||
)*};
|
)*};
|
||||||
}
|
}
|
||||||
|
|
||||||
check_all! {
|
check_all! {
|
||||||
NonTrivialDrop,
|
NonTrivialDrop,
|
||||||
//~^ ERROR can't drop
|
|
||||||
ConstImplWithDropGlue(NonTrivialDrop),
|
ConstImplWithDropGlue(NonTrivialDrop),
|
||||||
//~^ ERROR can't drop
|
|
||||||
ConstDropImplWithBounds::<NonTrivialDrop>(PhantomData),
|
|
||||||
//~^ ERROR the trait bound
|
|
||||||
//~| ERROR the trait bound
|
|
||||||
}
|
|
||||||
|
|
||||||
struct ConstDropImplWithNonConstBounds<T: A>(PhantomData<T>);
|
|
||||||
|
|
||||||
impl<T: ~const A> const Drop for ConstDropImplWithNonConstBounds<T> {
|
|
||||||
//~^ ERROR `Drop` impl requires `T: ~const A` but the struct it is implemented for does not
|
|
||||||
fn drop(&mut self) {
|
|
||||||
T::a();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn main() {}
|
fn main() {}
|
||||||
|
@ -1,99 +1,58 @@
|
|||||||
error[E0277]: can't drop `NonTrivialDrop` in const contexts
|
error[E0277]: can't drop `NonTrivialDrop` in const contexts
|
||||||
--> $DIR/const-drop-fail.rs:44:5
|
--> $DIR/const-drop-fail.rs:26:23
|
||||||
|
|
|
|
||||||
LL | const _: () = check($exp);
|
LL | const _: () = check($exp);
|
||||||
| ----- required by a bound introduced by this call
|
| ^^^^^^^^^^^ the trait `~const Destruct` is not implemented for `NonTrivialDrop`
|
||||||
...
|
...
|
||||||
LL | NonTrivialDrop,
|
LL | / check_all! {
|
||||||
| ^^^^^^^^^^^^^^ the trait `~const Destruct` is not implemented for `NonTrivialDrop`
|
LL | | NonTrivialDrop,
|
||||||
|
|
LL | | ConstImplWithDropGlue(NonTrivialDrop),
|
||||||
= note: the trait bound `NonTrivialDrop: ~const Destruct` is not satisfied
|
LL | | }
|
||||||
note: required by a bound in `check`
|
| |_- in this macro invocation
|
||||||
--> $DIR/const-drop-fail.rs:35:19
|
|
||||||
|
|
|
||||||
LL | const fn check<T: ~const Destruct>(_: T) {}
|
|
||||||
| ^^^^^^^^^^^^^^^ required by this bound in `check`
|
|
||||||
help: consider borrowing here
|
|
||||||
|
|
|
||||||
LL | &NonTrivialDrop,
|
|
||||||
| +
|
|
||||||
LL | &mut NonTrivialDrop,
|
|
||||||
| ++++
|
|
||||||
|
|
||||||
error[E0277]: can't drop `NonTrivialDrop` in const contexts
|
|
||||||
--> $DIR/const-drop-fail.rs:46:5
|
|
||||||
|
|
|
||||||
LL | const _: () = check($exp);
|
|
||||||
| ----- required by a bound introduced by this call
|
|
||||||
...
|
|
||||||
LL | ConstImplWithDropGlue(NonTrivialDrop),
|
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ within `ConstImplWithDropGlue`, the trait `~const Destruct` is not implemented for `NonTrivialDrop`
|
|
||||||
|
|
|
|
||||||
note: the trait `Destruct` is implemented for `NonTrivialDrop`, but that implementation is not `const`
|
note: the trait `Destruct` is implemented for `NonTrivialDrop`, but that implementation is not `const`
|
||||||
--> $DIR/const-drop-fail.rs:46:5
|
--> $DIR/const-drop-fail.rs:26:23
|
||||||
|
|
|
|
||||||
LL | ConstImplWithDropGlue(NonTrivialDrop),
|
LL | const _: () = check($exp);
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^
|
||||||
|
...
|
||||||
|
LL | / check_all! {
|
||||||
|
LL | | NonTrivialDrop,
|
||||||
|
LL | | ConstImplWithDropGlue(NonTrivialDrop),
|
||||||
|
LL | | }
|
||||||
|
| |_- in this macro invocation
|
||||||
|
= note: this error originates in the macro `check_all` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||||
|
|
||||||
|
error[E0277]: can't drop `NonTrivialDrop` in const contexts
|
||||||
|
--> $DIR/const-drop-fail.rs:26:23
|
||||||
|
|
|
||||||
|
LL | const _: () = check($exp);
|
||||||
|
| ^^^^^^^^^^^ within `ConstImplWithDropGlue`, the trait `~const Destruct` is not implemented for `NonTrivialDrop`
|
||||||
|
...
|
||||||
|
LL | / check_all! {
|
||||||
|
LL | | NonTrivialDrop,
|
||||||
|
LL | | ConstImplWithDropGlue(NonTrivialDrop),
|
||||||
|
LL | | }
|
||||||
|
| |_- in this macro invocation
|
||||||
|
|
|
||||||
|
note: the trait `Destruct` is implemented for `NonTrivialDrop`, but that implementation is not `const`
|
||||||
|
--> $DIR/const-drop-fail.rs:26:23
|
||||||
|
|
|
||||||
|
LL | const _: () = check($exp);
|
||||||
|
| ^^^^^^^^^^^
|
||||||
|
...
|
||||||
|
LL | / check_all! {
|
||||||
|
LL | | NonTrivialDrop,
|
||||||
|
LL | | ConstImplWithDropGlue(NonTrivialDrop),
|
||||||
|
LL | | }
|
||||||
|
| |_- in this macro invocation
|
||||||
note: required because it appears within the type `ConstImplWithDropGlue`
|
note: required because it appears within the type `ConstImplWithDropGlue`
|
||||||
--> $DIR/const-drop-fail.rs:16:8
|
--> $DIR/const-drop-fail.rs:16:8
|
||||||
|
|
|
|
||||||
LL | struct ConstImplWithDropGlue(NonTrivialDrop);
|
LL | struct ConstImplWithDropGlue(NonTrivialDrop);
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^^^^^^^^^^^
|
||||||
note: required by a bound in `check`
|
= note: this error originates in the macro `check_all` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||||
--> $DIR/const-drop-fail.rs:35:19
|
|
||||||
|
|
|
||||||
LL | const fn check<T: ~const Destruct>(_: T) {}
|
|
||||||
| ^^^^^^^^^^^^^^^ required by this bound in `check`
|
|
||||||
|
|
||||||
error[E0277]: the trait bound `NonTrivialDrop: ~const A` is not satisfied
|
error: aborting due to 2 previous errors
|
||||||
--> $DIR/const-drop-fail.rs:48:47
|
|
||||||
|
|
|
||||||
LL | ConstDropImplWithBounds::<NonTrivialDrop>(PhantomData),
|
|
||||||
| ----------------------------------------- ^^^^^^^^^^^ the trait `~const A` is not implemented for `NonTrivialDrop`
|
|
||||||
| |
|
|
||||||
| required by a bound introduced by this call
|
|
||||||
|
|
|
||||||
note: the trait `A` is implemented for `NonTrivialDrop`, but that implementation is not `const`
|
|
||||||
--> $DIR/const-drop-fail.rs:48:47
|
|
||||||
|
|
|
||||||
LL | ConstDropImplWithBounds::<NonTrivialDrop>(PhantomData),
|
|
||||||
| ^^^^^^^^^^^
|
|
||||||
note: required by a bound in `ConstDropImplWithBounds`
|
|
||||||
--> $DIR/const-drop-fail.rs:27:35
|
|
||||||
|
|
|
||||||
LL | struct ConstDropImplWithBounds<T: ~const A>(PhantomData<T>);
|
|
||||||
| ^^^^^^^^ required by this bound in `ConstDropImplWithBounds`
|
|
||||||
|
|
||||||
error[E0277]: the trait bound `NonTrivialDrop: ~const A` is not satisfied
|
For more information about this error, try `rustc --explain E0277`.
|
||||||
--> $DIR/const-drop-fail.rs:48:5
|
|
||||||
|
|
|
||||||
LL | ConstDropImplWithBounds::<NonTrivialDrop>(PhantomData),
|
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `~const A` is not implemented for `NonTrivialDrop`
|
|
||||||
|
|
|
||||||
note: the trait `A` is implemented for `NonTrivialDrop`, but that implementation is not `const`
|
|
||||||
--> $DIR/const-drop-fail.rs:48:5
|
|
||||||
|
|
|
||||||
LL | ConstDropImplWithBounds::<NonTrivialDrop>(PhantomData),
|
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
||||||
note: required by a bound in `ConstDropImplWithBounds`
|
|
||||||
--> $DIR/const-drop-fail.rs:27:35
|
|
||||||
|
|
|
||||||
LL | struct ConstDropImplWithBounds<T: ~const A>(PhantomData<T>);
|
|
||||||
| ^^^^^^^^ required by this bound in `ConstDropImplWithBounds`
|
|
||||||
|
|
||||||
error[E0367]: `Drop` impl requires `T: ~const A` but the struct it is implemented for does not
|
|
||||||
--> $DIR/const-drop-fail.rs:55:9
|
|
||||||
|
|
|
||||||
LL | impl<T: ~const A> const Drop for ConstDropImplWithNonConstBounds<T> {
|
|
||||||
| ^^^^^^^^
|
|
||||||
|
|
|
||||||
note: the implementor must specify the same requirement
|
|
||||||
--> $DIR/const-drop-fail.rs:53:1
|
|
||||||
|
|
|
||||||
LL | struct ConstDropImplWithNonConstBounds<T: A>(PhantomData<T>);
|
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
||||||
|
|
||||||
error: aborting due to 5 previous errors
|
|
||||||
|
|
||||||
Some errors have detailed explanations: E0277, E0367.
|
|
||||||
For more information about an error, try `rustc --explain E0277`.
|
|
||||||
|
@ -9,5 +9,6 @@ impl Default for A {
|
|||||||
#[derive_const(Default)]
|
#[derive_const(Default)]
|
||||||
pub struct S(A);
|
pub struct S(A);
|
||||||
//~^ cannot call non-const fn
|
//~^ cannot call non-const fn
|
||||||
|
//~| the trait bound
|
||||||
|
|
||||||
fn main() {}
|
fn main() {}
|
||||||
|
@ -1,3 +1,24 @@
|
|||||||
|
error[E0277]: the trait bound `A: Default` is not satisfied
|
||||||
|
--> $DIR/derive-const-non-const-type.rs:10:14
|
||||||
|
|
|
||||||
|
LL | #[derive_const(Default)]
|
||||||
|
| ------- in this derive macro expansion
|
||||||
|
LL | pub struct S(A);
|
||||||
|
| ^ the trait `~const Default` is not implemented for `A`
|
||||||
|
|
|
||||||
|
note: the trait `Default` is implemented for `A`, but that implementation is not `const`
|
||||||
|
--> $DIR/derive-const-non-const-type.rs:10:14
|
||||||
|
|
|
||||||
|
LL | #[derive_const(Default)]
|
||||||
|
| ------- in this derive macro expansion
|
||||||
|
LL | pub struct S(A);
|
||||||
|
| ^
|
||||||
|
= note: this error originates in the derive macro `Default` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||||
|
help: consider annotating `A` with `#[derive(Default)]`
|
||||||
|
|
|
||||||
|
LL | #[derive(Default)]
|
||||||
|
|
|
||||||
|
|
||||||
error[E0015]: cannot call non-const fn `<A as Default>::default` in constant functions
|
error[E0015]: cannot call non-const fn `<A as Default>::default` in constant functions
|
||||||
--> $DIR/derive-const-non-const-type.rs:10:14
|
--> $DIR/derive-const-non-const-type.rs:10:14
|
||||||
|
|
|
|
||||||
@ -10,6 +31,7 @@ LL | pub struct S(A);
|
|||||||
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
|
= help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
|
||||||
= note: this error originates in the derive macro `Default` (in Nightly builds, run with -Z macro-backtrace for more info)
|
= note: this error originates in the derive macro `Default` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||||
|
|
||||||
error: aborting due to previous error
|
error: aborting due to 2 previous errors
|
||||||
|
|
||||||
For more information about this error, try `rustc --explain E0015`.
|
Some errors have detailed explanations: E0015, E0277.
|
||||||
|
For more information about an error, try `rustc --explain E0015`.
|
||||||
|
@ -1,19 +1,14 @@
|
|||||||
error[E0277]: the trait bound `(): ~const Tr` is not satisfied
|
error[E0277]: the trait bound `(): ~const Tr` is not satisfied
|
||||||
--> $DIR/default-method-body-is-const-body-checking.rs:12:15
|
--> $DIR/default-method-body-is-const-body-checking.rs:12:9
|
||||||
|
|
|
|
||||||
LL | foo::<()>();
|
LL | foo::<()>();
|
||||||
| ^^ the trait `~const Tr` is not implemented for `()`
|
| ^^^^^^^^^^^ the trait `~const Tr` is not implemented for `()`
|
||||||
|
|
|
|
||||||
note: the trait `Tr` is implemented for `()`, but that implementation is not `const`
|
note: the trait `Tr` is implemented for `()`, but that implementation is not `const`
|
||||||
--> $DIR/default-method-body-is-const-body-checking.rs:12:15
|
--> $DIR/default-method-body-is-const-body-checking.rs:12:9
|
||||||
|
|
|
|
||||||
LL | foo::<()>();
|
LL | foo::<()>();
|
||||||
| ^^
|
| ^^^^^^^^^^^
|
||||||
note: required by a bound in `foo`
|
|
||||||
--> $DIR/default-method-body-is-const-body-checking.rs:7:28
|
|
||||||
|
|
|
||||||
LL | const fn foo<T>() where T: ~const Tr {}
|
|
||||||
| ^^^^^^^^^ required by this bound in `foo`
|
|
||||||
|
|
||||||
error: aborting due to previous error
|
error: aborting due to previous error
|
||||||
|
|
||||||
|
@ -0,0 +1,15 @@
|
|||||||
|
// check-pass
|
||||||
|
#![feature(const_trait_impl)]
|
||||||
|
|
||||||
|
#[const_trait]
|
||||||
|
pub trait Test {}
|
||||||
|
|
||||||
|
impl Test for () {}
|
||||||
|
|
||||||
|
pub const fn test<T: ~const Test>() {}
|
||||||
|
|
||||||
|
pub const fn min_by_i32() -> fn() {
|
||||||
|
test::<()>
|
||||||
|
}
|
||||||
|
|
||||||
|
fn main() {}
|
Loading…
Reference in New Issue
Block a user