Branch data Line data Source code
1 : : // Copyright (C) 2020-2025 Free Software Foundation, Inc.
2 : :
3 : : // This file is part of GCC.
4 : :
5 : : // GCC is free software; you can redistribute it and/or modify it under
6 : : // the terms of the GNU General Public License as published by the Free
7 : : // Software Foundation; either version 3, or (at your option) any later
8 : : // version.
9 : :
10 : : // GCC is distributed in the hope that it will be useful, but WITHOUT ANY
11 : : // WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 : : // FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
13 : : // for more details.
14 : :
15 : : // You should have received a copy of the GNU General Public License
16 : : // along with GCC; see the file COPYING3. If not see
17 : : // <http://www.gnu.org/licenses/>.
18 : :
19 : : #include "rust-const-checker.h"
20 : : #include "rust-hir.h"
21 : : #include "rust-hir-expr.h"
22 : : #include "rust-hir-stmt.h"
23 : : #include "rust-hir-item.h"
24 : : #include "rust-system.h"
25 : : #include "rust-immutable-name-resolution-context.h"
26 : :
27 : : // for flag_name_resolution_2_0
28 : : #include "options.h"
29 : :
30 : : namespace Rust {
31 : : namespace HIR {
32 : :
33 : 4070 : ConstChecker::ConstChecker ()
34 : 4070 : : resolver (*Resolver::Resolver::get ()),
35 : 4070 : mappings (Analysis::Mappings::get ())
36 : 4070 : {}
37 : :
38 : : void
39 : 4070 : ConstChecker::go (HIR::Crate &crate)
40 : : {
41 : 20961 : for (auto &item : crate.get_items ())
42 : 16891 : item->accept_vis (*this);
43 : 4070 : }
44 : :
45 : : bool
46 : 544 : ConstChecker::is_const_extern_fn (HIR::ExternalFunctionItem &fn)
47 : : {
48 : : // FIXME: Is it really how we want to handle `rustc_const_stable`
49 : : // and `rustc_const_unstable`?
50 : : // TODO: Add these attributes to the attribute check and handle
51 : : // `stable` and `unstable` as well
52 : 1088 : return std::any_of (
53 : 544 : fn.get_outer_attrs ().begin (), fn.get_outer_attrs ().end (),
54 : 532 : [] (const AST::Attribute &attr) {
55 : : // `starts_with` in C++11...
56 : 532 : return attr.get_path ().as_string ().rfind ("rustc_const_", 0) == 0;
57 : 544 : });
58 : : }
59 : :
60 : : const char *
61 : 0 : ConstChecker::ctx_to_str (ConstGenericCtx ctx)
62 : : {
63 : 0 : switch (ctx)
64 : : {
65 : : case ConstGenericCtx::Function:
66 : : return "function";
67 : 0 : case ConstGenericCtx::TypeAlias:
68 : 0 : return "type alias";
69 : 0 : case ConstGenericCtx::Struct:
70 : 0 : return "struct";
71 : 0 : case ConstGenericCtx::Enum:
72 : 0 : return "enum";
73 : 0 : case ConstGenericCtx::Union:
74 : 0 : return "union";
75 : 0 : case ConstGenericCtx::Trait:
76 : 0 : return "trait";
77 : 0 : case ConstGenericCtx::Impl:
78 : 0 : return "impl";
79 : 0 : default:
80 : 0 : rust_unreachable ();
81 : : }
82 : : }
83 : :
84 : : bool
85 : 25993 : ConstChecker::ctx_allows_default (ConstGenericCtx ctx)
86 : : {
87 : 25993 : switch (ctx)
88 : : {
89 : : case ConstGenericCtx::TypeAlias:
90 : : case ConstGenericCtx::Struct:
91 : : case ConstGenericCtx::Enum:
92 : : case ConstGenericCtx::Trait:
93 : : return true;
94 : 18452 : default:
95 : 18452 : return false;
96 : : }
97 : : }
98 : :
99 : : void
100 : 25993 : ConstChecker::check_default_const_generics (
101 : : std::vector<std::unique_ptr<GenericParam>> ¶ms, ConstGenericCtx context)
102 : : {
103 : 25993 : if (ctx_allows_default (context))
104 : : return;
105 : :
106 : 20333 : for (auto ¶m : params)
107 : : {
108 : 1881 : if (param->get_kind () == GenericParam::GenericKind::CONST)
109 : : {
110 : 29 : auto const_param = static_cast<ConstGenericParam *> (param.get ());
111 : 29 : if (const_param->has_default_expression ())
112 : 0 : rust_error_at (
113 : 0 : param->get_locus (),
114 : : "default values for const generic parameters are not "
115 : : "allowed in %qs items",
116 : : ctx_to_str (context));
117 : : }
118 : : }
119 : : }
120 : :
121 : : void
122 : 0 : ConstChecker::visit (Lifetime &)
123 : 0 : {}
124 : :
125 : : void
126 : 0 : ConstChecker::visit (LifetimeParam &)
127 : 0 : {}
128 : :
129 : : void
130 : 33883 : ConstChecker::visit (PathInExpression &)
131 : 33883 : {}
132 : :
133 : : void
134 : 0 : ConstChecker::visit (TypePathSegment &)
135 : 0 : {}
136 : :
137 : : void
138 : 0 : ConstChecker::visit (TypePathSegmentGeneric &)
139 : 0 : {}
140 : :
141 : : void
142 : 0 : ConstChecker::visit (TypePathSegmentFunction &)
143 : 0 : {}
144 : :
145 : : void
146 : 3538 : ConstChecker::visit (TypePath &)
147 : 3538 : {}
148 : :
149 : : void
150 : 15 : ConstChecker::visit (QualifiedPathInExpression &)
151 : 15 : {}
152 : :
153 : : void
154 : 0 : ConstChecker::visit (QualifiedPathInType &)
155 : 0 : {}
156 : :
157 : : void
158 : 17745 : ConstChecker::visit (LiteralExpr &)
159 : 17745 : {}
160 : :
161 : : void
162 : 1934 : ConstChecker::visit (BorrowExpr &expr)
163 : : {
164 : 1934 : expr.get_expr ().accept_vis (*this);
165 : 1934 : }
166 : :
167 : : void
168 : 3898 : ConstChecker::visit (DereferenceExpr &expr)
169 : : {
170 : 3898 : expr.get_expr ().accept_vis (*this);
171 : 3898 : }
172 : :
173 : : void
174 : 0 : ConstChecker::visit (ErrorPropagationExpr &expr)
175 : : {
176 : 0 : expr.get_expr ().accept_vis (*this);
177 : 0 : }
178 : :
179 : : void
180 : 515 : ConstChecker::visit (NegationExpr &expr)
181 : : {
182 : 515 : expr.get_expr ().accept_vis (*this);
183 : 515 : }
184 : :
185 : : void
186 : 3273 : ConstChecker::visit (ArithmeticOrLogicalExpr &expr)
187 : : {
188 : 3273 : expr.get_lhs ().accept_vis (*this);
189 : 3273 : expr.get_rhs ().accept_vis (*this);
190 : 3273 : }
191 : :
192 : : void
193 : 2697 : ConstChecker::visit (ComparisonExpr &expr)
194 : : {
195 : 2697 : expr.get_lhs ().accept_vis (*this);
196 : 2697 : expr.get_rhs ().accept_vis (*this);
197 : 2697 : }
198 : :
199 : : void
200 : 384 : ConstChecker::visit (LazyBooleanExpr &expr)
201 : : {
202 : 384 : expr.get_lhs ().accept_vis (*this);
203 : 384 : expr.get_rhs ().accept_vis (*this);
204 : 384 : }
205 : :
206 : : void
207 : 5076 : ConstChecker::visit (TypeCastExpr &expr)
208 : : {
209 : 5076 : expr.get_expr ().accept_vis (*this);
210 : 5076 : }
211 : :
212 : : void
213 : 2456 : ConstChecker::visit (AssignmentExpr &expr)
214 : : {
215 : 2456 : expr.get_lhs ().accept_vis (*this);
216 : 2456 : expr.get_rhs ().accept_vis (*this);
217 : 2456 : }
218 : :
219 : : void
220 : 666 : ConstChecker::visit (CompoundAssignmentExpr &expr)
221 : : {
222 : 666 : expr.get_lhs ().accept_vis (*this);
223 : 666 : expr.get_rhs ().accept_vis (*this);
224 : 666 : }
225 : :
226 : : void
227 : 280 : ConstChecker::visit (GroupedExpr &expr)
228 : : {
229 : 280 : expr.get_expr_in_parens ().accept_vis (*this);
230 : 280 : }
231 : :
232 : : void
233 : 283 : ConstChecker::visit (ArrayElemsValues &elems)
234 : : {
235 : 1699 : for (auto &elem : elems.get_values ())
236 : 1416 : elem->accept_vis (*this);
237 : 283 : }
238 : :
239 : : void
240 : 113 : ConstChecker::visit (ArrayElemsCopied &elems)
241 : : {
242 : 113 : elems.get_elem_to_copy ().accept_vis (*this);
243 : :
244 : 113 : const_context.enter (elems.get_mappings ().get_hirid ());
245 : :
246 : 113 : elems.get_num_copies_expr ().accept_vis (*this);
247 : :
248 : 113 : const_context.exit ();
249 : 113 : }
250 : :
251 : : void
252 : 396 : ConstChecker::visit (ArrayExpr &expr)
253 : : {
254 : 396 : expr.get_internal_elements ().accept_vis (*this);
255 : 396 : }
256 : :
257 : : void
258 : 239 : ConstChecker::visit (ArrayIndexExpr &expr)
259 : : {
260 : 239 : expr.get_array_expr ().accept_vis (*this);
261 : 239 : expr.get_index_expr ().accept_vis (*this);
262 : 239 : }
263 : :
264 : : void
265 : 536 : ConstChecker::visit (TupleExpr &expr)
266 : : {
267 : 1466 : for (auto &elem : expr.get_tuple_elems ())
268 : 930 : elem->accept_vis (*this);
269 : 536 : }
270 : :
271 : : void
272 : 884 : ConstChecker::visit (TupleIndexExpr &expr)
273 : : {
274 : 884 : expr.get_tuple_expr ().accept_vis (*this);
275 : 884 : }
276 : :
277 : : void
278 : 76 : ConstChecker::visit (StructExprStruct &)
279 : 76 : {}
280 : :
281 : : void
282 : 215 : ConstChecker::visit (StructExprFieldIdentifier &)
283 : 215 : {}
284 : :
285 : : void
286 : 2602 : ConstChecker::visit (StructExprFieldIdentifierValue &field)
287 : : {
288 : 2602 : field.get_value ().accept_vis (*this);
289 : 2602 : }
290 : :
291 : : void
292 : 42 : ConstChecker::visit (StructExprFieldIndexValue &field)
293 : : {
294 : 42 : field.get_value ().accept_vis (*this);
295 : 42 : }
296 : :
297 : : void
298 : 1295 : ConstChecker::visit (StructExprStructFields &expr)
299 : : {
300 : 4154 : for (auto &field : expr.get_fields ())
301 : 2859 : field->accept_vis (*this);
302 : 1295 : }
303 : :
304 : : void
305 : 0 : ConstChecker::visit (StructExprStructBase &)
306 : 0 : {}
307 : :
308 : : void
309 : 10872 : ConstChecker::check_function_call (HirId fn_id, location_t locus)
310 : : {
311 : 10872 : if (!const_context.is_in_context ())
312 : 9991 : return;
313 : :
314 : 890 : auto maybe_fn = mappings.lookup_hir_item (fn_id);
315 : 890 : if (maybe_fn
316 : 890 : && maybe_fn.value ()->get_item_kind () != Item::ItemKind::Function)
317 : : return;
318 : :
319 : : // There are const extern functions (intrinsics)
320 : : // TODO: Should we check the ABI is only "rust intrinsics"? Is that handled
321 : : // elsewhere?
322 : 881 : auto maybe_extern_item = mappings.lookup_hir_extern_item (fn_id);
323 : 881 : if (maybe_extern_item
324 : 881 : && maybe_extern_item->first->get_extern_kind ()
325 : : != ExternalItem::ExternKind::Function)
326 : : return;
327 : :
328 : 881 : auto is_error = false;
329 : 881 : if (maybe_fn)
330 : : {
331 : 23 : auto fn = static_cast<Function *> (*maybe_fn);
332 : 23 : if (!fn->get_qualifiers ().is_const ())
333 : 881 : is_error = true;
334 : : }
335 : :
336 : 881 : if (maybe_extern_item)
337 : : {
338 : 544 : {
339 : 544 : auto fn
340 : 544 : = static_cast<ExternalFunctionItem *> (maybe_extern_item->first);
341 : 544 : if (!is_const_extern_fn (*fn))
342 : : is_error = true;
343 : : }
344 : : }
345 : :
346 : 869 : if (is_error)
347 : 15 : rust_error_at (locus, ErrorCode::E0015,
348 : : "only functions marked as %<const%> are allowed to be "
349 : : "called from constant contexts");
350 : : }
351 : :
352 : : void
353 : 10886 : ConstChecker::visit (CallExpr &expr)
354 : : {
355 : 10886 : if (!expr.has_fnexpr ())
356 : 14 : return;
357 : :
358 : 10886 : NodeId ast_node_id = expr.get_fnexpr ().get_mappings ().get_nodeid ();
359 : 10886 : NodeId ref_node_id;
360 : :
361 : 10886 : if (flag_name_resolution_2_0)
362 : : {
363 : 10886 : auto &nr_ctx
364 : 10886 : = Resolver2_0::ImmutableNameResolutionContext::get ().resolver ();
365 : :
366 : 10886 : if (auto id = nr_ctx.lookup (ast_node_id))
367 : 10872 : ref_node_id = *id;
368 : : else
369 : 14 : return;
370 : : }
371 : : // We don't care about types here
372 : 0 : else if (!resolver.lookup_resolved_name (ast_node_id, &ref_node_id))
373 : : return;
374 : :
375 : 10872 : if (auto definition_id = mappings.lookup_node_to_hir (ref_node_id))
376 : : {
377 : 10872 : check_function_call (*definition_id, expr.get_locus ());
378 : :
379 : 23825 : for (auto &arg : expr.get_arguments ())
380 : 12953 : arg->accept_vis (*this);
381 : : }
382 : : else
383 : : {
384 : 0 : rust_unreachable ();
385 : : }
386 : : }
387 : :
388 : : void
389 : 2955 : ConstChecker::visit (MethodCallExpr &expr)
390 : : {
391 : 2955 : expr.get_receiver ().accept_vis (*this);
392 : :
393 : 4986 : for (auto &arg : expr.get_arguments ())
394 : 2031 : arg->accept_vis (*this);
395 : 2955 : }
396 : :
397 : : void
398 : 5527 : ConstChecker::visit (FieldAccessExpr &expr)
399 : : {
400 : 5527 : expr.get_receiver_expr ().accept_vis (*this);
401 : 5527 : }
402 : :
403 : : void
404 : 53 : ConstChecker::visit (ClosureExpr &expr)
405 : : {
406 : 53 : expr.get_expr ().accept_vis (*this);
407 : 53 : }
408 : :
409 : : void
410 : 21362 : ConstChecker::visit (BlockExpr &expr)
411 : : {
412 : 43299 : for (auto &stmt : expr.get_statements ())
413 : 21937 : stmt->accept_vis (*this);
414 : :
415 : 21362 : if (expr.has_expr ())
416 : 15735 : expr.get_final_expr ().accept_vis (*this);
417 : 21362 : }
418 : :
419 : : void
420 : 377 : ConstChecker::visit (AnonConst &expr)
421 : : {
422 : 377 : const_context.enter (expr.get_mappings ().get_hirid ());
423 : :
424 : 377 : expr.get_inner_expr ().accept_vis (*this);
425 : :
426 : 377 : const_context.exit ();
427 : 377 : }
428 : :
429 : : void
430 : 15 : ConstChecker::visit (ConstBlock &expr)
431 : : {
432 : 15 : const_context.enter (expr.get_mappings ().get_hirid ());
433 : :
434 : 15 : expr.get_const_expr ().accept_vis (*this);
435 : :
436 : 15 : const_context.exit ();
437 : 15 : }
438 : :
439 : : void
440 : 8 : ConstChecker::visit (ContinueExpr &)
441 : 8 : {}
442 : :
443 : : void
444 : 75 : ConstChecker::visit (BreakExpr &expr)
445 : : {
446 : 75 : if (expr.has_break_expr ())
447 : 15 : expr.get_expr ().accept_vis (*this);
448 : 75 : }
449 : :
450 : : void
451 : 66 : ConstChecker::visit (RangeFromToExpr &expr)
452 : : {
453 : 66 : expr.get_from_expr ().accept_vis (*this);
454 : 66 : expr.get_to_expr ().accept_vis (*this);
455 : 66 : }
456 : :
457 : : void
458 : 7 : ConstChecker::visit (RangeFromExpr &expr)
459 : : {
460 : 7 : expr.get_from_expr ().accept_vis (*this);
461 : 7 : }
462 : :
463 : : void
464 : 7 : ConstChecker::visit (RangeToExpr &expr)
465 : : {
466 : 7 : expr.get_to_expr ().accept_vis (*this);
467 : 7 : }
468 : :
469 : : void
470 : 0 : ConstChecker::visit (RangeFullExpr &)
471 : 0 : {}
472 : :
473 : : void
474 : 7 : ConstChecker::visit (RangeFromToInclExpr &expr)
475 : : {
476 : 7 : expr.get_from_expr ().accept_vis (*this);
477 : 7 : expr.get_to_expr ().accept_vis (*this);
478 : 7 : }
479 : :
480 : : void
481 : 0 : ConstChecker::visit (RangeToInclExpr &)
482 : : {
483 : : // FIXME: Visit to_expr
484 : 0 : }
485 : :
486 : : void
487 : 509 : ConstChecker::visit (ReturnExpr &expr)
488 : : {
489 : 509 : if (expr.has_return_expr ())
490 : 479 : expr.get_expr ().accept_vis (*this);
491 : 509 : }
492 : :
493 : : void
494 : 3510 : ConstChecker::visit (UnsafeBlockExpr &expr)
495 : : {
496 : 3510 : expr.get_block_expr ().accept_vis (*this);
497 : 3510 : }
498 : :
499 : : void
500 : 111 : ConstChecker::visit (LoopExpr &expr)
501 : : {
502 : 111 : expr.get_loop_block ().accept_vis (*this);
503 : 111 : }
504 : :
505 : : void
506 : 66 : ConstChecker::visit (WhileLoopExpr &expr)
507 : : {
508 : 66 : expr.get_predicate_expr ().accept_vis (*this);
509 : 66 : expr.get_loop_block ().accept_vis (*this);
510 : 66 : }
511 : :
512 : : void
513 : 0 : ConstChecker::visit (WhileLetLoopExpr &expr)
514 : : {
515 : 0 : expr.get_cond ().accept_vis (*this);
516 : 0 : expr.get_loop_block ().accept_vis (*this);
517 : 0 : }
518 : :
519 : : void
520 : 463 : ConstChecker::visit (IfExpr &expr)
521 : : {
522 : 463 : expr.get_if_condition ().accept_vis (*this);
523 : 463 : expr.get_if_block ().accept_vis (*this);
524 : 463 : }
525 : :
526 : : void
527 : 1200 : ConstChecker::visit (IfExprConseqElse &expr)
528 : : {
529 : 1200 : expr.get_if_condition ().accept_vis (*this);
530 : 1200 : expr.get_if_block ().accept_vis (*this);
531 : 1200 : expr.get_else_block ().accept_vis (*this);
532 : 1200 : }
533 : :
534 : : void
535 : 1050 : ConstChecker::visit (MatchExpr &expr)
536 : : {
537 : 1050 : expr.get_scrutinee_expr ().accept_vis (*this);
538 : :
539 : 3473 : for (auto &match_arm : expr.get_match_cases ())
540 : 2423 : match_arm.get_expr ().accept_vis (*this);
541 : 1050 : }
542 : :
543 : : void
544 : 0 : ConstChecker::visit (AwaitExpr &)
545 : : {
546 : : // TODO: Visit expression
547 : 0 : }
548 : :
549 : : void
550 : 0 : ConstChecker::visit (AsyncBlockExpr &)
551 : : {
552 : : // TODO: Visit block expression
553 : 0 : }
554 : :
555 : : void
556 : 27 : ConstChecker::visit (InlineAsm &)
557 : 27 : {}
558 : :
559 : : void
560 : 2 : ConstChecker::visit (LlvmInlineAsm &)
561 : 2 : {}
562 : :
563 : : void
564 : 15 : ConstChecker::visit (OffsetOf &)
565 : 15 : {}
566 : :
567 : : void
568 : 0 : ConstChecker::visit (TypeParam &)
569 : 0 : {}
570 : :
571 : : void
572 : 0 : ConstChecker::visit (ConstGenericParam &)
573 : 0 : {}
574 : :
575 : : void
576 : 0 : ConstChecker::visit (LifetimeWhereClauseItem &)
577 : 0 : {}
578 : :
579 : : void
580 : 0 : ConstChecker::visit (TypeBoundWhereClauseItem &)
581 : 0 : {}
582 : :
583 : : void
584 : 1173 : ConstChecker::visit (Module &module)
585 : : {
586 : 5056 : for (auto &item : module.get_items ())
587 : 3883 : item->accept_vis (*this);
588 : 1173 : }
589 : :
590 : : void
591 : 0 : ConstChecker::visit (ExternCrate &)
592 : 0 : {}
593 : :
594 : : void
595 : 0 : ConstChecker::visit (UseTreeGlob &)
596 : 0 : {}
597 : :
598 : : void
599 : 0 : ConstChecker::visit (UseTreeList &)
600 : 0 : {}
601 : :
602 : : void
603 : 0 : ConstChecker::visit (UseTreeRebind &)
604 : 0 : {}
605 : :
606 : : void
607 : 0 : ConstChecker::visit (UseDeclaration &)
608 : 0 : {}
609 : :
610 : : void
611 : 12821 : ConstChecker::visit (Function &function)
612 : : {
613 : 12821 : auto const_fn = function.get_qualifiers ().is_const ();
614 : 12821 : if (const_fn)
615 : 852 : const_context.enter (function.get_mappings ().get_hirid ());
616 : :
617 : 12821 : check_default_const_generics (function.get_generic_params (),
618 : : ConstGenericCtx::Function);
619 : :
620 : 19009 : for (auto ¶m : function.get_function_params ())
621 : 6188 : param.get_type ().accept_vis (*this);
622 : :
623 : 12821 : function.get_definition ().accept_vis (*this);
624 : :
625 : 12821 : if (const_fn)
626 : 852 : const_context.exit ();
627 : 12821 : }
628 : :
629 : : void
630 : 1198 : ConstChecker::visit (TypeAlias &type_alias)
631 : : {
632 : 1198 : check_default_const_generics (type_alias.get_generic_params (),
633 : : ConstGenericCtx::TypeAlias);
634 : 1198 : }
635 : :
636 : : void
637 : 1425 : ConstChecker::visit (StructStruct &struct_item)
638 : : {
639 : 1425 : check_default_const_generics (struct_item.get_generic_params (),
640 : : ConstGenericCtx::Struct);
641 : 1425 : }
642 : :
643 : : void
644 : 921 : ConstChecker::visit (TupleStruct &tuple_struct)
645 : : {
646 : 921 : check_default_const_generics (tuple_struct.get_generic_params (),
647 : : ConstGenericCtx::Struct);
648 : 921 : }
649 : :
650 : : void
651 : 401 : ConstChecker::visit (EnumItem &)
652 : 401 : {}
653 : :
654 : : void
655 : 387 : ConstChecker::visit (EnumItemTuple &)
656 : 387 : {}
657 : :
658 : : void
659 : 76 : ConstChecker::visit (EnumItemStruct &)
660 : 76 : {}
661 : :
662 : : void
663 : 269 : ConstChecker::visit (EnumItemDiscriminant &item)
664 : : {
665 : 269 : const_context.enter (item.get_mappings ().get_hirid ());
666 : :
667 : 269 : item.get_discriminant_expression ().accept_vis (*this);
668 : :
669 : 269 : const_context.exit ();
670 : 269 : }
671 : :
672 : : void
673 : 479 : ConstChecker::visit (Enum &enum_item)
674 : : {
675 : 479 : check_default_const_generics (enum_item.get_generic_params (),
676 : : ConstGenericCtx::Enum);
677 : :
678 : 1612 : for (auto &item : enum_item.get_variants ())
679 : 1133 : item->accept_vis (*this);
680 : 479 : }
681 : :
682 : : void
683 : 97 : ConstChecker::visit (Union &union_item)
684 : : {
685 : 97 : check_default_const_generics (union_item.get_generic_params (),
686 : : ConstGenericCtx::Union);
687 : 97 : }
688 : :
689 : : void
690 : 505 : ConstChecker::visit (ConstantItem &const_item)
691 : : {
692 : 505 : const_context.enter (const_item.get_mappings ().get_hirid ());
693 : :
694 : 505 : const_item.get_expr ().accept_vis (*this);
695 : :
696 : 505 : const_context.exit ();
697 : 505 : }
698 : :
699 : : void
700 : 50 : ConstChecker::visit (StaticItem &static_item)
701 : : {
702 : 50 : const_context.enter (static_item.get_mappings ().get_hirid ());
703 : :
704 : 50 : static_item.get_expr ().accept_vis (*this);
705 : :
706 : 50 : const_context.exit ();
707 : 50 : }
708 : :
709 : : void
710 : 2472 : ConstChecker::visit (TraitItemFunc &item)
711 : : {
712 : 2472 : if (item.has_definition ())
713 : 847 : item.get_block_expr ().accept_vis (*this);
714 : 2472 : }
715 : :
716 : : void
717 : 31 : ConstChecker::visit (TraitItemConst &item)
718 : : {
719 : 31 : if (item.has_expr ())
720 : 7 : item.get_expr ().accept_vis (*this);
721 : 31 : }
722 : :
723 : : void
724 : 700 : ConstChecker::visit (TraitItemType &)
725 : 700 : {}
726 : :
727 : : void
728 : 3518 : ConstChecker::visit (Trait &trait)
729 : : {
730 : 3518 : check_default_const_generics (trait.get_generic_params (),
731 : : ConstGenericCtx::Trait);
732 : :
733 : 6721 : for (auto &item : trait.get_trait_items ())
734 : 3203 : item->accept_vis (*this);
735 : 3518 : }
736 : :
737 : : void
738 : 5534 : ConstChecker::visit (ImplBlock &impl)
739 : : {
740 : 5534 : check_default_const_generics (impl.get_generic_params (),
741 : : ConstGenericCtx::Impl);
742 : :
743 : 13558 : for (auto &item : impl.get_impl_items ())
744 : 8024 : item->accept_vis (*this);
745 : 5534 : }
746 : :
747 : : void
748 : 1 : ConstChecker::visit (ExternalStaticItem &)
749 : 1 : {}
750 : :
751 : : void
752 : 2198 : ConstChecker::visit (ExternalFunctionItem &)
753 : 2198 : {}
754 : :
755 : : void
756 : 0 : ConstChecker::visit (ExternalTypeItem &)
757 : 0 : {}
758 : :
759 : : void
760 : 1454 : ConstChecker::visit (ExternBlock &block)
761 : : {
762 : : // FIXME: Do we need to do this?
763 : 3653 : for (auto &item : block.get_extern_items ())
764 : 2199 : item->accept_vis (*this);
765 : 1454 : }
766 : :
767 : : void
768 : 0 : ConstChecker::visit (LiteralPattern &)
769 : 0 : {}
770 : :
771 : : void
772 : 0 : ConstChecker::visit (IdentifierPattern &)
773 : 0 : {}
774 : :
775 : : void
776 : 0 : ConstChecker::visit (WildcardPattern &)
777 : 0 : {}
778 : :
779 : : void
780 : 0 : ConstChecker::visit (RangePatternBoundLiteral &)
781 : 0 : {}
782 : :
783 : : void
784 : 0 : ConstChecker::visit (RangePatternBoundPath &)
785 : 0 : {}
786 : :
787 : : void
788 : 0 : ConstChecker::visit (RangePatternBoundQualPath &)
789 : 0 : {}
790 : :
791 : : void
792 : 0 : ConstChecker::visit (RangePattern &)
793 : 0 : {}
794 : :
795 : : void
796 : 0 : ConstChecker::visit (ReferencePattern &)
797 : 0 : {}
798 : :
799 : : void
800 : 0 : ConstChecker::visit (StructPatternFieldTuplePat &)
801 : 0 : {}
802 : :
803 : : void
804 : 0 : ConstChecker::visit (StructPatternFieldIdentPat &)
805 : 0 : {}
806 : :
807 : : void
808 : 0 : ConstChecker::visit (StructPatternFieldIdent &)
809 : 0 : {}
810 : :
811 : : void
812 : 0 : ConstChecker::visit (StructPattern &)
813 : 0 : {}
814 : :
815 : : void
816 : 0 : ConstChecker::visit (TupleStructItemsNoRest &)
817 : 0 : {}
818 : :
819 : : void
820 : 0 : ConstChecker::visit (TupleStructItemsHasRest &)
821 : 0 : {}
822 : :
823 : : void
824 : 0 : ConstChecker::visit (TupleStructPattern &)
825 : 0 : {}
826 : :
827 : : void
828 : 0 : ConstChecker::visit (TuplePatternItemsNoRest &)
829 : 0 : {}
830 : :
831 : : void
832 : 0 : ConstChecker::visit (TuplePatternItemsHasRest &)
833 : 0 : {}
834 : :
835 : : void
836 : 0 : ConstChecker::visit (TuplePattern &)
837 : 0 : {}
838 : :
839 : : void
840 : 0 : ConstChecker::visit (SlicePatternItemsNoRest &)
841 : 0 : {}
842 : :
843 : : void
844 : 0 : ConstChecker::visit (SlicePatternItemsHasRest &)
845 : 0 : {}
846 : :
847 : : void
848 : 0 : ConstChecker::visit (SlicePattern &)
849 : 0 : {}
850 : :
851 : : void
852 : 0 : ConstChecker::visit (AltPattern &)
853 : 0 : {}
854 : :
855 : : void
856 : 44 : ConstChecker::visit (EmptyStmt &)
857 : 44 : {}
858 : :
859 : : void
860 : 12414 : ConstChecker::visit (LetStmt &stmt)
861 : : {
862 : 12414 : if (stmt.has_init_expr ())
863 : 11298 : stmt.get_init_expr ().accept_vis (*this);
864 : 12414 : }
865 : :
866 : : void
867 : 9102 : ConstChecker::visit (ExprStmt &stmt)
868 : : {
869 : 9102 : stmt.get_expr ().accept_vis (*this);
870 : 9102 : }
871 : :
872 : : void
873 : 0 : ConstChecker::visit (TraitBound &)
874 : 0 : {}
875 : :
876 : : void
877 : 0 : ConstChecker::visit (ImplTraitType &)
878 : 0 : {}
879 : :
880 : : void
881 : 0 : ConstChecker::visit (TraitObjectType &)
882 : 0 : {}
883 : :
884 : : void
885 : 0 : ConstChecker::visit (ParenthesisedType &)
886 : 0 : {}
887 : :
888 : : void
889 : 24 : ConstChecker::visit (TupleType &)
890 : 24 : {}
891 : :
892 : : void
893 : 0 : ConstChecker::visit (NeverType &)
894 : 0 : {}
895 : :
896 : : void
897 : 326 : ConstChecker::visit (RawPointerType &)
898 : 326 : {}
899 : :
900 : : void
901 : 1929 : ConstChecker::visit (ReferenceType &type)
902 : : {
903 : 1929 : if (const_context.is_in_context () && type.is_mut ())
904 : 1 : rust_error_at (type.get_locus (), ErrorCode::E0658,
905 : : "mutable references are not allowed in constant functions");
906 : 1929 : }
907 : :
908 : : void
909 : 362 : ConstChecker::visit (ArrayType &type)
910 : : {
911 : 362 : const_context.enter (type.get_mappings ().get_hirid ());
912 : :
913 : 362 : type.get_size_expr ().accept_vis (*this);
914 : :
915 : 362 : const_context.exit ();
916 : 362 : }
917 : :
918 : : void
919 : 1 : ConstChecker::visit (SliceType &)
920 : 1 : {}
921 : :
922 : : void
923 : 0 : ConstChecker::visit (InferredType &)
924 : 0 : {}
925 : :
926 : : void
927 : 8 : ConstChecker::visit (BareFunctionType &)
928 : 8 : {}
929 : :
930 : : } // namespace HIR
931 : : } // namespace Rust
|