Skip to content

Commit c354524

Browse files
authored
Rollup merge of rust-lang#74392 - lcnr:const-generics-update, r=varkor
const generics triage I went through all const generics issues and closed all issues which are already fixed. Some issues already have a regression test but were not closed. Also doing this as part of this PR. uff r? @eddyb @varkor closes rust-lang#61936 closes rust-lang#62878 closes rust-lang#63695 closes rust-lang#67144 closes rust-lang#68596 closes rust-lang#69816 closes rust-lang#70217 closes rust-lang#70507 closes rust-lang#70586 closes rust-lang#71348 closes rust-lang#71805 closes rust-lang#73120 closes rust-lang#73508 closes rust-lang#73730 closes rust-lang#74255
2 parents 8f3b0ec + 8faeb0e commit c354524

13 files changed

+273
-0
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
#![feature(const_generics)]
2+
3+
// All of these three items must be in `lib2` to reproduce the error
4+
5+
pub trait TypeFn {
6+
type Output;
7+
}
8+
9+
pub struct GenericType<const B: i8>;
10+
11+
// Removing the braces around `42` resolves the crash
12+
impl TypeFn for GenericType<{ 42 }> {
13+
type Output = ();
14+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
// check-pass
2+
#![feature(const_generics)]
3+
#![allow(incomplete_features)]
4+
5+
pub struct S(u8);
6+
7+
impl S {
8+
pub fn get<const A: u8>(&self) -> &u8 {
9+
&self.0
10+
}
11+
}
12+
13+
fn main() {
14+
const A: u8 = 5;
15+
let s = S(0);
16+
17+
s.get::<A>();
18+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
// check-pass
2+
// aux-build:const_generic_issues_lib.rs
3+
extern crate const_generic_issues_lib as lib2;
4+
fn unused_function(
5+
_: <lib2::GenericType<42> as lib2::TypeFn>::Output
6+
) {}
7+
8+
fn main() {}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
#![feature(const_generics)] //~ WARN the feature `const_generics` is incomplete
2+
3+
pub const fn func_name<const X: *const u32>() {}
4+
//~^ ERROR using raw pointers
5+
6+
fn main() {}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
warning: the feature `const_generics` is incomplete and may not be safe to use and/or cause compiler crashes
2+
--> $DIR/issue-73508.rs:1:12
3+
|
4+
LL | #![feature(const_generics)]
5+
| ^^^^^^^^^^^^^^
6+
|
7+
= note: `#[warn(incomplete_features)]` on by default
8+
= note: see issue #44580 <https://github.com/rust-lang/rust/issues/44580> for more information
9+
10+
error: using raw pointers as const generic parameters is forbidden
11+
--> $DIR/issue-73508.rs:3:33
12+
|
13+
LL | pub const fn func_name<const X: *const u32>() {}
14+
| ^^^^^^^^^^
15+
16+
error: aborting due to previous error; 1 warning emitted
17+
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
// check-pass
2+
#![feature(const_generics)]
3+
#![allow(dead_code, incomplete_features)]
4+
5+
#[derive(PartialEq, Eq)]
6+
enum IceEnum {
7+
Variant
8+
}
9+
10+
struct IceStruct;
11+
12+
impl IceStruct {
13+
fn ice_struct_fn<const I: IceEnum>() {}
14+
}
15+
16+
fn main() {
17+
IceStruct::ice_struct_fn::<{IceEnum::Variant}>();
18+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
// check-pass
2+
#![feature(const_generics)]
3+
#![allow(incomplete_features)]
4+
5+
struct X;
6+
7+
impl X {
8+
pub fn getn<const N: usize>(&self) -> [u8; N] {
9+
getn::<N>()
10+
}
11+
}
12+
13+
fn getn<const N: usize>() -> [u8; N] {
14+
unsafe {
15+
std::mem::zeroed()
16+
}
17+
}
18+
19+
fn main() {
20+
// works
21+
let [a,b,c] = getn::<3>();
22+
23+
// cannot pattern-match on an array without a fixed length
24+
let [a,b,c] = X.getn::<3>();
25+
26+
// mismatched types, expected array `[u8; 3]` found array `[u8; _]`
27+
let arr: [u8; 3] = X.getn::<3>();
28+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
// check-pass
2+
#![feature(const_generics)]
3+
#![allow(incomplete_features)]
4+
5+
struct A<const N: usize>;
6+
7+
struct X;
8+
9+
impl X {
10+
fn inner<const N: usize>() -> A<N> {
11+
outer::<N>()
12+
}
13+
}
14+
15+
fn outer<const N: usize>() -> A<N> {
16+
A
17+
}
18+
19+
fn main() {
20+
let i: A<3usize> = outer::<3usize>();
21+
let o: A<3usize> = X::inner::<3usize>();
22+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
// check-pass
2+
#![feature(const_generics)]
3+
#![allow(incomplete_features)]
4+
5+
struct Struct<const N: usize>;
6+
7+
impl<const N: usize> Struct<N> {
8+
fn method<const M: usize>(&self) {}
9+
}
10+
11+
fn test<const N: usize, const M: usize>(x: Struct<N>) {
12+
Struct::<N>::method::<M>(&x);
13+
x.method::<N>();
14+
}
15+
16+
fn main() {}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
// check-pass
2+
#![feature(const_generics)]
3+
#![allow(incomplete_features)]
4+
5+
use std::marker::PhantomData;
6+
7+
// This namespace is necessary for the ICE to trigger
8+
struct Namespace;
9+
10+
impl Namespace {
11+
pub fn const_chunks_exact<T, const N: usize>() -> ConstChunksExact<'static, T, N> {
12+
ConstChunksExact { inner: PhantomData }
13+
}
14+
}
15+
16+
17+
#[derive(Debug)]
18+
pub struct ConstChunksExact<'a, T, const N: usize> {
19+
inner: PhantomData<&'a T>
20+
}
21+
22+
impl <'a, T, const N: usize> Iterator for ConstChunksExact<'a, T, { N }> {
23+
type Item = &'a [T; N];
24+
25+
fn next(&mut self) -> Option<Self::Item> {
26+
unreachable!()
27+
}
28+
}
29+
30+
fn main() {
31+
let mut chunks = Namespace::const_chunks_exact::<i32, 3usize>();
32+
let _next: &[i32; 3] = chunks.next().unwrap();
33+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
// run-pass
2+
#![feature(const_generics)]
3+
#![allow(incomplete_features)]
4+
5+
struct Foo {
6+
i: i32,
7+
}
8+
9+
trait Get<'a, const N: &'static str> {
10+
type Target: 'a;
11+
12+
fn get(&'a self) -> &'a Self::Target;
13+
}
14+
15+
impl Foo {
16+
fn ask<'a, const N: &'static str>(&'a self) -> &'a <Self as Get<N>>::Target
17+
where
18+
Self: Get<'a, N>,
19+
{
20+
self.get()
21+
}
22+
}
23+
24+
impl<'a> Get<'a, "int"> for Foo {
25+
type Target = i32;
26+
27+
fn get(&'a self) -> &'a Self::Target {
28+
&self.i
29+
}
30+
}
31+
32+
fn main() {
33+
let foo = Foo { i: 123 };
34+
assert_eq!(foo.ask::<"int">(), &123);
35+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
// run-pass
2+
#![feature(const_generics)]
3+
#![allow(incomplete_features)]
4+
5+
use std::mem::MaybeUninit;
6+
7+
trait CollectSlice<'a>: Iterator {
8+
fn inner_array<const N: usize>(&mut self) -> [Self::Item; N];
9+
10+
fn collect_array<const N: usize>(&mut self) -> [Self::Item; N] {
11+
let result = self.inner_array();
12+
assert!(self.next().is_none());
13+
result
14+
}
15+
}
16+
17+
impl<'a, I: ?Sized> CollectSlice<'a> for I
18+
where
19+
I: Iterator,
20+
{
21+
fn inner_array<const N: usize>(&mut self) -> [Self::Item; N] {
22+
let mut result: [MaybeUninit<Self::Item>; N] =
23+
unsafe { MaybeUninit::uninit().assume_init() };
24+
25+
let mut count = 0;
26+
for (dest, item) in result.iter_mut().zip(self) {
27+
*dest = MaybeUninit::new(item);
28+
count += 1;
29+
}
30+
31+
assert_eq!(N, count);
32+
33+
let temp_ptr: *const [MaybeUninit<Self::Item>; N] = &result;
34+
unsafe { std::ptr::read(temp_ptr as *const [Self::Item; N]) }
35+
}
36+
}
37+
38+
fn main() {
39+
let mut foos = [0u64; 9].iter().cloned();
40+
let _bar: [u64; 9] = foos.collect_array::<9_usize>();
41+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
// check-pass
2+
#![feature(const_generics)]
3+
#![allow(incomplete_features)]
4+
5+
trait Foo<'a, A>: Iterator<Item=A> {
6+
fn bar<const N: usize>(&mut self) -> *const [A; N];
7+
}
8+
9+
impl<'a, A, I: ?Sized> Foo<'a, A> for I where I: Iterator<Item=A> {
10+
fn bar<const N: usize>(&mut self) -> *const [A; N] {
11+
std::ptr::null()
12+
}
13+
}
14+
15+
fn main() {
16+
(0_u8 .. 10).bar::<10_usize>();
17+
}

0 commit comments

Comments
 (0)