]> git.lizzy.rs Git - rust.git/blob - tests/ui/consts/const_let_eq_float.rs
Auto merge of #105102 - compiler-errors:copy-impl-considering-regions, r=lcnr
[rust.git] / tests / ui / consts / const_let_eq_float.rs
1 // run-pass
2
3 #![feature(const_fn_floating_point_arithmetic)]
4
5 struct Foo<T>(T);
6 struct Bar<T> { x: T }
7 struct W(f32);
8 struct A { a: f32 }
9
10 #[allow(redundant_semicolons)]
11 const fn basics((a,): (f32,)) -> f32 {
12     // Deferred assignment:
13     let b: f32;
14     b = a + 1.0;
15
16     // Immediate assignment:
17     let c: f32 = b + 1.0;
18
19     // Mutables:
20     let mut d: f32 = c + 1.0;
21     d = d + 1.0;
22     // +4 so far.
23
24     // No effect statements work:
25     ; ;
26     1;
27
28     // Array projection
29     let mut arr: [f32; 1] = [0.0];
30     arr[0] = 1.0;
31     d = d + arr[0];
32     // +5
33
34     // Field projection:
35     let mut foo: Foo<f32> = Foo(0.0);
36     let mut bar: Bar<f32> = Bar { x: 0.0 };
37     foo.0 = 1.0;
38     bar.x = 1.0;
39     d = d + foo.0 + bar.x;
40     // +7
41
42     // Array + Field projection:
43     let mut arr: [Foo<f32>; 1] = [Foo(0.0)];
44     arr[0].0 = 1.0;
45     d = d + arr[0].0;
46     let mut arr: [Bar<f32>; 1] = [Bar { x: 0.0 }];
47     arr[0].x = 1.0;
48     d = d + arr[0].x;
49     // +9
50
51     // Field + Array projection:
52     let mut arr: Foo<[f32; 1]> = Foo([0.0]);
53     (arr.0)[0] = 1.0;
54     d = d + (arr.0)[0];
55     let mut arr: Bar<[f32; 1]> = Bar { x: [0.0] };
56     arr.x[0] = 1.0;
57     d = d + arr.x[0];
58     // +11
59
60     d
61 }
62
63 const fn add_assign(W(a): W) -> f32 {
64     // Mutables:
65     let mut d: f32 = a + 1.0;
66     d += 1.0;
67     // +2 so far.
68
69     // Array projection
70     let mut arr: [f32; 1] = [0.0];
71     arr[0] += 1.0;
72     d += arr[0];
73     // +3
74
75     // Field projection:
76     let mut foo: Foo<f32> = Foo(0.0);
77     let mut bar: Bar<f32> = Bar { x: 0.0 };
78     foo.0 += 1.0;
79     bar.x += 1.0;
80     d += foo.0 + bar.x;
81     // +5
82
83     // Array + Field projection:
84     let mut arr: [Foo<f32>; 1] = [Foo(0.0)];
85     arr[0].0 += 1.0;
86     d += arr[0].0;
87     let mut arr: [Bar<f32>; 1] = [Bar { x: 0.0 }];
88     arr[0].x += 1.0;
89     d += arr[0].x;
90     // +7
91
92     // Field + Array projection:
93     let mut arr: Foo<[f32; 1]> = Foo([0.0]);
94     (arr.0)[0] += 1.0;
95     d += (arr.0)[0];
96     let mut arr: Bar<[f32; 1]> = Bar { x: [0.0] };
97     arr.x[0] += 1.0;
98     d += arr.x[0];
99     // +9
100
101     d
102 }
103
104 const fn mul_assign(A { a }: A) -> f32 {
105     // Mutables:
106     let mut d: f32 = a + 1.0;
107     d *= 2.0;
108     // 2^1 * (a + 1)
109
110     // Array projection
111     let mut arr: [f32; 1] = [1.0];
112     arr[0] *= 2.0;
113     d *= arr[0];
114     // 2^2 * (a + 1)
115
116     // Field projection:
117     let mut foo: Foo<f32> = Foo(1.0);
118     let mut bar: Bar<f32> = Bar { x: 1.0 };
119     foo.0 *= 2.0;
120     bar.x *= 2.0;
121     d *= foo.0 + bar.x;
122     // 2^4 * (a + 1)
123
124     // Array + Field projection:
125     let mut arr: [Foo<f32>; 1] = [Foo(1.0)];
126     arr[0].0 *= 2.0;
127     d *= arr[0].0;
128     let mut arr: [Bar<f32>; 1] = [Bar { x: 1.0 }];
129     arr[0].x *= 2.0;
130     d *= arr[0].x;
131     // 2^6 * (a + 1)
132
133     // Field + Array projection:
134     let mut arr: Foo<[f32; 1]> = Foo([1.0]);
135     (arr.0)[0] *= 2.0;
136     d *= (arr.0)[0];
137     let mut arr: Bar<[f32; 1]> = Bar { x: [1.0] };
138     arr.x[0] *= 2.0;
139     d *= arr.x[0];
140     // 2^8 * (a + 1)
141
142     d
143 }
144
145 const fn div_assign(a: [f32; 1]) -> f32 {
146     let a = a[0];
147     // Mutables:
148     let mut d: f32 = 1024.0 * a;
149     d /= 2.0;
150     // 512
151
152     // Array projection
153     let mut arr: [f32; 1] = [4.0];
154     arr[0] /= 2.0;
155     d /= arr[0];
156     // 256
157
158     // Field projection:
159     let mut foo: Foo<f32> = Foo(4.0);
160     let mut bar: Bar<f32> = Bar { x: 4.0 };
161     foo.0 /= 2.0;
162     bar.x /= 2.0;
163     d /= foo.0;
164     d /= bar.x;
165     // 64
166
167     // Array + Field projection:
168     let mut arr: [Foo<f32>; 1] = [Foo(4.0)];
169     arr[0].0 /= 2.0;
170     d /= arr[0].0;
171     let mut arr: [Bar<f32>; 1] = [Bar { x: 4.0 }];
172     arr[0].x /= 2.0;
173     d /= arr[0].x;
174     // 16
175
176     // Field + Array projection:
177     let mut arr: Foo<[f32; 1]> = Foo([4.0]);
178     (arr.0)[0] /= 2.0;
179     d /= (arr.0)[0];
180     let mut arr: Bar<[f32; 1]> = Bar { x: [4.0] };
181     arr.x[0] /= 2.0;
182     d /= arr.x[0];
183     // 4
184
185     d
186 }
187
188 const fn rem_assign(W(a): W) -> f32 {
189     // Mutables:
190     let mut d: f32 = a;
191     d %= 10.0;
192     d += 10.0;
193
194     // Array projection
195     let mut arr: [f32; 1] = [3.0];
196     arr[0] %= 2.0;
197     d %= 9.0 + arr[0];
198     d += 10.0;
199
200     // Field projection:
201     let mut foo: Foo<f32> = Foo(5.0);
202     let mut bar: Bar<f32> = Bar { x: 7.0 };
203     foo.0 %= 2.0;
204     bar.x %= 2.0;
205     d %= 8.0 + foo.0 + bar.x;
206     d += 10.0;
207
208     // Array + Field projection:
209     let mut arr: [Foo<f32>; 1] = [Foo(4.0)];
210     arr[0].0 %= 3.0;
211     d %= 9.0 + arr[0].0;
212     d += 10.0;
213     let mut arr: [Bar<f32>; 1] = [Bar { x: 7.0 }];
214     arr[0].x %= 3.0;
215     d %= 9.0 + arr[0].x;
216     d += 10.0;
217
218     // Field + Array projection:
219     let mut arr: Foo<[f32; 1]> = Foo([6.0]);
220     (arr.0)[0] %= 5.0;
221     d %= 9.0 + (arr.0)[0];
222     let mut arr: Bar<[f32; 1]> = Bar { x: [11.0] };
223     arr.x[0] %= 5.0;
224     d %= 9.0 + arr.x[0];
225
226     d
227 }
228
229 const fn sub_assign(W(a): W) -> f32 {
230     // Mutables:
231     let mut d: f32 = a;
232     d -= 1.0;
233
234     // Array projection
235     let mut arr: [f32; 1] = [2.0];
236     arr[0] -= 1.0;
237     d -= arr[0];
238
239     // Field projection:
240     let mut foo: Foo<f32> = Foo(2.0);
241     let mut bar: Bar<f32> = Bar { x: 2.0 };
242     foo.0 -= 1.0;
243     bar.x -= 1.0;
244     d -= foo.0 + bar.x;
245
246     // Array + Field projection:
247     let mut arr: [Foo<f32>; 1] = [Foo(2.0)];
248     arr[0].0 -= 1.0;
249     d -= arr[0].0;
250     let mut arr: [Bar<f32>; 1] = [Bar { x: 2.0 }];
251     arr[0].x -= 1.0;
252     d -= arr[0].x;
253
254     // Field + Array projection:
255     let mut arr: Foo<[f32; 1]> = Foo([2.0]);
256     (arr.0)[0] -= 1.0;
257     d -= (arr.0)[0];
258     let mut arr: Bar<[f32; 1]> = Bar { x: [2.0] };
259     arr.x[0] -= 1.0;
260     d -= arr.x[0];
261
262     d
263 }
264
265 macro_rules! test {
266     ($c:ident, $e:expr, $r:expr) => {
267         const $c: f32 = $e;
268         assert_eq!($c, $r);
269         assert_eq!($e, $r);
270     }
271 }
272
273 fn main() {
274     test!(BASICS, basics((2.0,)), 13.0);
275     test!(ADD, add_assign(W(1.0)), 10.0);
276     test!(MUL, mul_assign(A { a: 0.0 }), 256.0);
277     test!(DIV, div_assign([1.0]), 4.0);
278     test!(REM, rem_assign(W(5.0)), 5.0);
279     test!(SUB, sub_assign(W(8.0)), 0.0);
280 }