1 // ok
foo1()2 const fn foo1() {}
foo2(x: i32) -> i323 const fn foo2(x: i32) -> i32 { x }
foo3<T>(x: T) -> T4 const fn foo3<T>(x: T) -> T { x }
foo7()5 const fn foo7() {
6     (
7         foo1(),
8         foo2(420),
9         foo3(69),
10     ).0
11 }
foo12<T: Sized>(t: T) -> T12 const fn foo12<T: Sized>(t: T) -> T { t }
foo13<T: ?Sized>(t: &T) -> &T13 const fn foo13<T: ?Sized>(t: &T) -> &T { t }
foo14<'a, T: 'a>(t: &'a T) -> &'a T14 const fn foo14<'a, T: 'a>(t: &'a T) -> &'a T { t }
foo15<T>(t: T) -> T where T: Sized15 const fn foo15<T>(t: T) -> T where T: Sized { t }
foo15_2<T>(t: &T) -> &T where T: ?Sized16 const fn foo15_2<T>(t: &T) -> &T where T: ?Sized { t }
foo16(f: f32) -> f3217 const fn foo16(f: f32) -> f32 { f }
foo17(f: f32) -> u3218 const fn foo17(f: f32) -> u32 { f as u32 }
foo18(i: i32) -> i3219 const fn foo18(i: i32) -> i32 { i * 3 }
foo20(b: bool) -> bool20 const fn foo20(b: bool) -> bool { !b }
foo21<T, U>(t: T, u: U) -> (T, U)21 const fn foo21<T, U>(t: T, u: U) -> (T, U) { (t, u) }
foo22(s: &[u8], i: usize) -> u822 const fn foo22(s: &[u8], i: usize) -> u8 { s[i] }
23 const FOO: u32 = 42;
foo23() -> u3224 const fn foo23() -> u32 { FOO }
foo24() -> &'static u3225 const fn foo24() -> &'static u32 { &FOO }
foo27(x: &u32) -> u3226 const fn foo27(x: &u32) -> u32 { *x }
foo28(x: u32) -> u3227 const fn foo28(x: u32) -> u32 { *&x }
foo29(x: u32) -> i3228 const fn foo29(x: u32) -> i32 { x as i32 }
foo31(a: bool, b: bool) -> bool29 const fn foo31(a: bool, b: bool) -> bool { a & b }
foo32(a: bool, b: bool) -> bool30 const fn foo32(a: bool, b: bool) -> bool { a | b }
foo33(a: bool, b: bool) -> bool31 const fn foo33(a: bool, b: bool) -> bool { a & b }
foo34(a: bool, b: bool) -> bool32 const fn foo34(a: bool, b: bool) -> bool { a | b }
foo35(a: bool, b: bool) -> bool33 const fn foo35(a: bool, b: bool) -> bool { a ^ b }
34 struct Foo<T: ?Sized>(T);
35 impl<T> Foo<T> {
new(t: T) -> Self36     const fn new(t: T) -> Self { Foo(t) }
into_inner(self) -> T37     const fn into_inner(self) -> T { self.0 } //~ destructors cannot be evaluated
get(&self) -> &T38     const fn get(&self) -> &T { &self.0 }
get_mut(&mut self) -> &mut T39     const fn get_mut(&mut self) -> &mut T { &mut self.0 }
40     //~^ mutable references
41     //~| mutable references
42     //~| mutable references
43 }
44 impl<'a, T> Foo<T> {
new_lt(t: T) -> Self45     const fn new_lt(t: T) -> Self { Foo(t) }
into_inner_lt(self) -> T46     const fn into_inner_lt(self) -> T { self.0 } //~ destructors cannot be evaluated
get_lt(&'a self) -> &T47     const fn get_lt(&'a self) -> &T { &self.0 }
get_mut_lt(&'a mut self) -> &mut T48     const fn get_mut_lt(&'a mut self) -> &mut T { &mut self.0 }
49     //~^ mutable references
50     //~| mutable references
51     //~| mutable references
52 }
53 impl<T: Sized> Foo<T> {
new_s(t: T) -> Self54     const fn new_s(t: T) -> Self { Foo(t) }
into_inner_s(self) -> T55     const fn into_inner_s(self) -> T { self.0 } //~ ERROR destructors
get_s(&self) -> &T56     const fn get_s(&self) -> &T { &self.0 }
get_mut_s(&mut self) -> &mut T57     const fn get_mut_s(&mut self) -> &mut T { &mut self.0 }
58     //~^ mutable references
59     //~| mutable references
60     //~| mutable references
61 }
62 impl<T: ?Sized> Foo<T> {
get_sq(&self) -> &T63     const fn get_sq(&self) -> &T { &self.0 }
get_mut_sq(&mut self) -> &mut T64     const fn get_mut_sq(&mut self) -> &mut T { &mut self.0 }
65     //~^ mutable references
66     //~| mutable references
67     //~| mutable references
68 }
69 
70 
char_ops(c: char, d: char) -> bool71 const fn char_ops(c: char, d: char) -> bool { c == d }
char_ops2(c: char, d: char) -> bool72 const fn char_ops2(c: char, d: char) -> bool { c < d }
char_ops3(c: char, d: char) -> bool73 const fn char_ops3(c: char, d: char) -> bool { c != d }
i32_ops(c: i32, d: i32) -> bool74 const fn i32_ops(c: i32, d: i32) -> bool { c == d }
i32_ops2(c: i32, d: i32) -> bool75 const fn i32_ops2(c: i32, d: i32) -> bool { c < d }
i32_ops3(c: i32, d: i32) -> bool76 const fn i32_ops3(c: i32, d: i32) -> bool { c != d }
i32_ops4(c: i32, d: i32) -> i3277 const fn i32_ops4(c: i32, d: i32) -> i32 { c + d }
char_cast(u: u8) -> char78 const fn char_cast(u: u8) -> char { u as char }
ret_i32_no_unsafe() -> i3279 const unsafe fn ret_i32_no_unsafe() -> i32 { 42 }
ret_null_ptr_no_unsafe<T>() -> *const T80 const unsafe fn ret_null_ptr_no_unsafe<T>() -> *const T { core::ptr::null() }
ret_null_mut_ptr_no_unsafe<T>() -> *mut T81 const unsafe fn ret_null_mut_ptr_no_unsafe<T>() -> *mut T { core::ptr::null_mut() }
82 
83 // not ok
foo11<T: std::fmt::Display>(t: T) -> T84 const fn foo11<T: std::fmt::Display>(t: T) -> T { t }
85 //~^ ERROR trait bounds other than `Sized` on const fn parameters are unstable
foo11_2<T: Send>(t: T) -> T86 const fn foo11_2<T: Send>(t: T) -> T { t }
87 //~^ ERROR trait bounds other than `Sized` on const fn parameters are unstable
88 
89 static BAR: u32 = 42;
foo25() -> u3290 const fn foo25() -> u32 { BAR } //~ ERROR cannot refer to statics
foo26() -> &'static u3291 const fn foo26() -> &'static u32 { &BAR } //~ ERROR cannot refer to statics
foo30(x: *const u32) -> usize92 const fn foo30(x: *const u32) -> usize { x as usize }
93 //~^ ERROR pointers cannot be cast to integers
foo30_with_unsafe(x: *const u32) -> usize94 const fn foo30_with_unsafe(x: *const u32) -> usize { unsafe { x as usize } }
95 //~^ ERROR pointers cannot be cast to integers
foo30_2(x: *mut u32) -> usize96 const fn foo30_2(x: *mut u32) -> usize { x as usize }
97 //~^ ERROR pointers cannot be cast to integers
foo30_2_with_unsafe(x: *mut u32) -> usize98 const fn foo30_2_with_unsafe(x: *mut u32) -> usize { unsafe { x as usize } }
99 //~^ ERROR pointers cannot be cast to integers
foo30_6() -> bool100 const fn foo30_6() -> bool { let x = true; x }
inc(x: &mut i32)101 const fn inc(x: &mut i32) { *x += 1 }
102 //~^ ERROR mutable references
103 
104 // ok
foo36(a: bool, b: bool) -> bool105 const fn foo36(a: bool, b: bool) -> bool { a && b }
foo37(a: bool, b: bool) -> bool106 const fn foo37(a: bool, b: bool) -> bool { a || b }
107 
main()108 fn main() {}
109 
110 impl<T: std::fmt::Debug> Foo<T> {
111 //~^ ERROR trait bounds other than `Sized` on const fn parameters are unstable
foo(&self)112     const fn foo(&self) {}
113 }
114 
115 impl<T: std::fmt::Debug + Sized> Foo<T> {
116 //~^ ERROR trait bounds other than `Sized` on const fn parameters are unstable
foo2(&self)117     const fn foo2(&self) {}
118 }
119 
120 impl<T: Sync + Sized> Foo<T> {
121 //~^ ERROR trait bounds other than `Sized` on const fn parameters are unstable
foo3(&self)122     const fn foo3(&self) {}
123 }
124 
125 struct AlanTuring<T>(T);
no_apit2(_x: AlanTuring<impl std::fmt::Debug>)126 const fn no_apit2(_x: AlanTuring<impl std::fmt::Debug>) {}
127 //~^ ERROR trait bounds other than `Sized`
128 //~| ERROR destructor
no_apit(_x: impl std::fmt::Debug)129 const fn no_apit(_x: impl std::fmt::Debug) {}
130 //~^ ERROR trait bounds other than `Sized`
131 //~| ERROR destructor
no_dyn_trait(_x: &dyn std::fmt::Debug)132 const fn no_dyn_trait(_x: &dyn std::fmt::Debug) {}
133 //~^ ERROR trait objects in const fn are unstable
no_dyn_trait_ret() -> &'static dyn std::fmt::Debug134 const fn no_dyn_trait_ret() -> &'static dyn std::fmt::Debug { &() }
135 //~^ ERROR trait objects in const fn are unstable
136 
no_unsafe()137 const fn no_unsafe() { unsafe {} }
138 
really_no_traits_i_mean_it()139 const fn really_no_traits_i_mean_it() { (&() as &dyn std::fmt::Debug, ()).1 }
140 //~^ ERROR trait objects in const fn are unstable
141 //~| ERROR trait objects in const fn are unstable
142 //~| ERROR trait objects in const fn are unstable
143 
no_fn_ptrs(_x: fn())144 const fn no_fn_ptrs(_x: fn()) {}
145 //~^ ERROR function pointer
no_fn_ptrs2() -> fn()146 const fn no_fn_ptrs2() -> fn() { fn foo() {} foo }
147 //~^ ERROR function pointer
148 //~| ERROR function pointer cast
149