add test for Compiler panic using fn_traits #81974
Fixes https://github.com/rust-lang/rust/issues/81974
This commit is contained in:
parent
60b5ca6275
commit
5f95fc1dff
59
tests/ui/layout/rust-call-abi-not-a-tuple-ice-81974.rs
Normal file
59
tests/ui/layout/rust-call-abi-not-a-tuple-ice-81974.rs
Normal file
@ -0,0 +1,59 @@
|
||||
// ICE argument to function with "rust-call" ABI is not a tuple
|
||||
// issue: rust-lang/rust#81974
|
||||
|
||||
#![feature(unboxed_closures)]
|
||||
#![feature(fn_traits)]
|
||||
|
||||
use std::collections::HashMap;
|
||||
use std::hash::Hash;
|
||||
|
||||
struct CachedFun<A, B> {
|
||||
cache: HashMap<A, B>,
|
||||
fun: fn(&mut CachedFun<A, B>, A) -> B,
|
||||
}
|
||||
|
||||
impl<A: Eq + Hash, B> CachedFun<A, B> {
|
||||
fn new(fun: fn(&mut Self, A) -> B) -> Self {
|
||||
CachedFun {
|
||||
cache: HashMap::new(),
|
||||
fun,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<A, B> FnOnce<A> for CachedFun<A, B>
|
||||
//~^ ERROR type parameter to bare `FnOnce` trait must be a tuple
|
||||
where
|
||||
A: Eq + Hash + Clone,
|
||||
B: Clone,
|
||||
{
|
||||
type Output = B;
|
||||
extern "rust-call" fn call_once(mut self, a: A) -> Self::Output {
|
||||
//~^ ERROR functions with the "rust-call" ABI must take a single non-self tuple argument
|
||||
self.call_mut(a)
|
||||
//~^ ERROR `A` is not a tuple
|
||||
}
|
||||
}
|
||||
|
||||
impl<A, B> FnMut<A> for CachedFun<A, B>
|
||||
//~^ ERROR type parameter to bare `FnMut` trait must be a tuple
|
||||
where
|
||||
A: Eq + Hash + Clone,
|
||||
B: Clone,
|
||||
{
|
||||
extern "rust-call" fn call_mut(&mut self, a: A) -> Self::Output {
|
||||
//~^ ERROR functions with the "rust-call" ABI must take a single non-self tuple argument
|
||||
self.cache.get(&a).map(|a| a.clone()).unwrap_or_else(|| {
|
||||
let b = (self.fun)(self, a.clone());
|
||||
self.cache.insert(a, b.clone());
|
||||
b
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
fn main() -> () {
|
||||
let pesce = |y: &mut CachedFun<i32, i32>, x| x + 1;
|
||||
let cachedcoso = CachedFun::new(pesce);
|
||||
cachedcoso.call_once(1);
|
||||
//~^ ERROR `i32` is not a tuple
|
||||
}
|
78
tests/ui/layout/rust-call-abi-not-a-tuple-ice-81974.stderr
Normal file
78
tests/ui/layout/rust-call-abi-not-a-tuple-ice-81974.stderr
Normal file
@ -0,0 +1,78 @@
|
||||
error[E0059]: type parameter to bare `FnOnce` trait must be a tuple
|
||||
--> $DIR/rust-call-abi-not-a-tuple-ice-81974.rs:24:12
|
||||
|
|
||||
LL | impl<A, B> FnOnce<A> for CachedFun<A, B>
|
||||
| ^^^^^^^^^ the trait `Tuple` is not implemented for `A`
|
||||
|
|
||||
note: required by a bound in `FnOnce`
|
||||
--> $SRC_DIR/core/src/ops/function.rs:LL:COL
|
||||
help: consider further restricting this bound
|
||||
|
|
||||
LL | A: Eq + Hash + Clone + std::marker::Tuple,
|
||||
| ++++++++++++++++++++
|
||||
|
||||
error[E0059]: type parameter to bare `FnMut` trait must be a tuple
|
||||
--> $DIR/rust-call-abi-not-a-tuple-ice-81974.rs:38:12
|
||||
|
|
||||
LL | impl<A, B> FnMut<A> for CachedFun<A, B>
|
||||
| ^^^^^^^^ the trait `Tuple` is not implemented for `A`
|
||||
|
|
||||
note: required by a bound in `FnMut`
|
||||
--> $SRC_DIR/core/src/ops/function.rs:LL:COL
|
||||
help: consider further restricting this bound
|
||||
|
|
||||
LL | A: Eq + Hash + Clone + std::marker::Tuple,
|
||||
| ++++++++++++++++++++
|
||||
|
||||
error[E0277]: functions with the "rust-call" ABI must take a single non-self tuple argument
|
||||
--> $DIR/rust-call-abi-not-a-tuple-ice-81974.rs:31:5
|
||||
|
|
||||
LL | extern "rust-call" fn call_once(mut self, a: A) -> Self::Output {
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Tuple` is not implemented for `A`
|
||||
|
|
||||
help: consider further restricting this bound
|
||||
|
|
||||
LL | A: Eq + Hash + Clone + std::marker::Tuple,
|
||||
| ++++++++++++++++++++
|
||||
|
||||
error[E0277]: functions with the "rust-call" ABI must take a single non-self tuple argument
|
||||
--> $DIR/rust-call-abi-not-a-tuple-ice-81974.rs:44:5
|
||||
|
|
||||
LL | extern "rust-call" fn call_mut(&mut self, a: A) -> Self::Output {
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Tuple` is not implemented for `A`
|
||||
|
|
||||
help: consider further restricting this bound
|
||||
|
|
||||
LL | A: Eq + Hash + Clone + std::marker::Tuple,
|
||||
| ++++++++++++++++++++
|
||||
|
||||
error[E0277]: `A` is not a tuple
|
||||
--> $DIR/rust-call-abi-not-a-tuple-ice-81974.rs:33:23
|
||||
|
|
||||
LL | self.call_mut(a)
|
||||
| -------- ^ the trait `Tuple` is not implemented for `A`
|
||||
| |
|
||||
| required by a bound introduced by this call
|
||||
|
|
||||
note: required by a bound in `call_mut`
|
||||
--> $SRC_DIR/core/src/ops/function.rs:LL:COL
|
||||
help: consider further restricting this bound
|
||||
|
|
||||
LL | A: Eq + Hash + Clone + std::marker::Tuple,
|
||||
| ++++++++++++++++++++
|
||||
|
||||
error[E0277]: `i32` is not a tuple
|
||||
--> $DIR/rust-call-abi-not-a-tuple-ice-81974.rs:57:26
|
||||
|
|
||||
LL | cachedcoso.call_once(1);
|
||||
| --------- ^ the trait `Tuple` is not implemented for `i32`
|
||||
| |
|
||||
| required by a bound introduced by this call
|
||||
|
|
||||
note: required by a bound in `call_once`
|
||||
--> $SRC_DIR/core/src/ops/function.rs:LL:COL
|
||||
|
||||
error: aborting due to 6 previous errors
|
||||
|
||||
Some errors have detailed explanations: E0059, E0277.
|
||||
For more information about an error, try `rustc --explain E0059`.
|
Loading…
Reference in New Issue
Block a user