]> git.ipfire.org Git - thirdparty/gcc.git/blob - gcc/ada/sem_elab.adb
[Ada] Diagnostics in Elaboration order v4.0
[thirdparty/gcc.git] / gcc / ada / sem_elab.adb
1 ------------------------------------------------------------------------------
2 -- --
3 -- GNAT COMPILER COMPONENTS --
4 -- --
5 -- S E M _ E L A B --
6 -- --
7 -- B o d y --
8 -- --
9 -- Copyright (C) 1997-2019, Free Software Foundation, Inc. --
10 -- --
11 -- GNAT is free software; you can redistribute it and/or modify it under --
12 -- terms of the GNU General Public License as published by the Free Soft- --
13 -- ware Foundation; either version 3, or (at your option) any later ver- --
14 -- sion. GNAT is distributed in the hope that it will be useful, but WITH- --
15 -- OUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY --
16 -- or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License --
17 -- for more details. You should have received a copy of the GNU General --
18 -- Public License distributed with GNAT; see file COPYING3. If not, go to --
19 -- http://www.gnu.org/licenses for a complete copy of the license. --
20 -- --
21 -- GNAT was originally developed by the GNAT team at New York University. --
22 -- Extensive contributions were provided by Ada Core Technologies Inc. --
23 -- --
24 ------------------------------------------------------------------------------
25
26 with ALI; use ALI;
27 with Atree; use Atree;
28 with Checks; use Checks;
29 with Debug; use Debug;
30 with Einfo; use Einfo;
31 with Elists; use Elists;
32 with Errout; use Errout;
33 with Exp_Ch11; use Exp_Ch11;
34 with Exp_Tss; use Exp_Tss;
35 with Exp_Util; use Exp_Util;
36 with Expander; use Expander;
37 with Lib; use Lib;
38 with Lib.Load; use Lib.Load;
39 with Namet; use Namet;
40 with Nlists; use Nlists;
41 with Nmake; use Nmake;
42 with Opt; use Opt;
43 with Output; use Output;
44 with Restrict; use Restrict;
45 with Rident; use Rident;
46 with Rtsfind; use Rtsfind;
47 with Sem; use Sem;
48 with Sem_Aux; use Sem_Aux;
49 with Sem_Cat; use Sem_Cat;
50 with Sem_Ch7; use Sem_Ch7;
51 with Sem_Ch8; use Sem_Ch8;
52 with Sem_Prag; use Sem_Prag;
53 with Sem_Util; use Sem_Util;
54 with Sinfo; use Sinfo;
55 with Sinput; use Sinput;
56 with Snames; use Snames;
57 with Stand; use Stand;
58 with Table;
59 with Tbuild; use Tbuild;
60 with Uintp; use Uintp;
61 with Uname; use Uname;
62
63 with GNAT; use GNAT;
64 with GNAT.Dynamic_HTables; use GNAT.Dynamic_HTables;
65 with GNAT.Lists; use GNAT.Lists;
66 with GNAT.Sets; use GNAT.Sets;
67
68 package body Sem_Elab is
69
70 -----------------------------------------
71 -- Access-before-elaboration mechanism --
72 -----------------------------------------
73
74 -- The access-before-elaboration (ABE) mechanism implemented in this unit
75 -- has the following objectives:
76 --
77 -- * Diagnose at compile-time or install run-time checks to prevent ABE
78 -- access to data and behaviour.
79 --
80 -- The high-level idea is to accurately diagnose ABE issues within a
81 -- single unit because the ABE mechanism can inspect the whole unit.
82 -- As soon as the elaboration graph extends to an external unit, the
83 -- diagnostics stop because the body of the unit may not be available.
84 -- Due to control and data flow, the ABE mechanism cannot accurately
85 -- determine whether a particular scenario will be elaborated or not.
86 -- Conditional ABE checks are therefore used to verify the elaboration
87 -- status of local and external targets at run time.
88 --
89 -- * Supply implicit elaboration dependencies for a unit to binde
90 --
91 -- The ABE mechanism creates implicit dependencies in the form of with
92 -- clauses subject to pragma Elaborate[_All] when the elaboration graph
93 -- reaches into an external unit. The implicit dependencies are encoded
94 -- in the ALI file of the main unit. GNATbind and binde then use these
95 -- dependencies to augment the library item graph and determine the
96 -- elaboration order of all units in the compilation.
97 --
98 -- * Supply pieces of the invocation graph for a unit to bindo
99 --
100 -- The ABE mechanism captures paths starting from elaboration code or
101 -- top level constructs that reach into an external unit. The paths are
102 -- encoded in the ALI file of the main unit in the form of declarations
103 -- which represent nodes, and relations which represent edges. GNATbind
104 -- and bindo then build the full invocation graph in order to augment
105 -- the library item graph and determine the elaboration order of all
106 -- units in the compilation.
107 --
108 -- The ABE mechanism supports three models of elaboration:
109 --
110 -- * Dynamic model - This is the most permissive of the three models.
111 -- When the dynamic model is in effect, the mechanism diagnoses and
112 -- installs run-time checks to detect ABE issues in the main unit.
113 -- The behaviour of this model is identical to that specified by the
114 -- Ada RM. This model is enabled with switch -gnatE.
115 --
116 -- Static model - This is the middle ground of the three models. When
117 -- the static model is in effect, the mechanism diagnoses and installs
118 -- run-time checks to detect ABE issues in the main unit. In addition,
119 -- the mechanism generates implicit dependencies between units in the
120 -- form of with clauses subject to pragma Elaborate[_All] to ensure
121 -- the prior elaboration of withed units. This is the default model.
122 --
123 -- * SPARK model - This is the most conservative of the three models and
124 -- impelements the semantics defined in SPARK RM 7.7. The SPARK model
125 -- is in effect only when a context resides in a SPARK_Mode On region,
126 -- otherwise the mechanism falls back to one of the previous models.
127 --
128 -- The ABE mechanism consists of a "recording" phase and a "processing"
129 -- phase.
130
131 -----------------
132 -- Terminology --
133 -----------------
134
135 -- * ABE - An attempt to invoke a scenario which has not been elaborated
136 -- yet.
137 --
138 -- * Bridge target - A type of target. A bridge target is a link between
139 -- scenarios. It is usually a byproduct of expansion and does not have
140 -- any direct ABE ramifications.
141 --
142 -- * Call marker - A special node used to indicate the presence of a call
143 -- in the tree in case expansion transforms or eliminates the original
144 -- call. N_Call_Marker nodes do not have static and run-time semantics.
145 --
146 -- * Conditional ABE - A type of ABE. A conditional ABE occurs when the
147 -- invocation of a target by a scenario within the main unit causes an
148 -- ABE, but does not cause an ABE for another scenarios within the main
149 -- unit.
150 --
151 -- * Declaration level - A type of enclosing level. A scenario or target is
152 -- at the declaration level when it appears within the declarations of a
153 -- block statement, entry body, subprogram body, or task body, ignoring
154 -- enclosing packages.
155 --
156 -- * Early call region - A section of code which ends at a subprogram body
157 -- and starts from the nearest non-preelaborable construct which precedes
158 -- the subprogram body. The early call region extends from a package body
159 -- to a package spec when the spec carries pragma Elaborate_Body.
160 --
161 -- * Generic library level - A type of enclosing level. A scenario or
162 -- target is at the generic library level if it appears in a generic
163 -- package library unit, ignoring enclosing packages.
164 --
165 -- * Guaranteed ABE - A type of ABE. A guaranteed ABE occurs when the
166 -- invocation of a target by all scenarios within the main unit causes
167 -- an ABE.
168 --
169 -- * Instantiation library level - A type of enclosing level. A scenario
170 -- or target is at the instantiation library level if it appears in an
171 -- instantiation library unit, ignoring enclosing packages.
172 --
173 -- * Invocation - The act of activating a task, calling a subprogram, or
174 -- instantiating a generic.
175 --
176 -- * Invocation construct - An entry declaration, [single] protected type,
177 -- subprogram declaration, subprogram instantiation, or a [single] task
178 -- type declared in the visible, private, or body declarations of the
179 -- main unit.
180 --
181 -- * Invocation relation - A flow link between two invocation constructs
182 --
183 -- * Invocation signature - A set of attributes that uniquely identify an
184 -- invocation construct within the namespace of all ALI files.
185 --
186 -- * Library level - A type of enclosing level. A scenario or target is at
187 -- the library level if it appears in a package library unit, ignoring
188 -- enclosng packages.
189 --
190 -- * Non-library-level encapsulator - A construct that cannot be elaborated
191 -- on its own and requires elaboration by a top-level scenario.
192 --
193 -- * Scenario - A construct or context which is invoked by elaboration code
194 -- or invocation construct. The scenarios recognized by the ABE mechanism
195 -- are as follows:
196 --
197 -- - '[Unrestricted_]Access of entries, operators, and subprograms
198 --
199 -- - Assignments to variables
200 --
201 -- - Calls to entries, operators, and subprograms
202 --
203 -- - Derived type declarations
204 --
205 -- - Instantiations
206 --
207 -- - Pragma Refined_State
208 --
209 -- - Reads of variables
210 --
211 -- - Task activation
212 --
213 -- * Target - A construct invoked by a scenario. The targets recognized by
214 -- the ABE mechanism are as follows:
215 --
216 -- - For '[Unrestricted_]Access of entries, operators, and subprograms,
217 -- the target is the entry, operator, or subprogram.
218 --
219 -- - For assignments to variables, the target is the variable
220 --
221 -- - For calls, the target is the entry, operator, or subprogram
222 --
223 -- - For derived type declarations, the target is the derived type
224 --
225 -- - For instantiations, the target is the generic template
226 --
227 -- - For pragma Refined_State, the targets are the constituents
228 --
229 -- - For reads of variables, the target is the variable
230 --
231 -- - For task activation, the target is the task body
232
233 ------------------
234 -- Architecture --
235 ------------------
236
237 -- Analysis/Resolution
238 -- |
239 -- +- Build_Call_Marker
240 -- |
241 -- +- Build_Variable_Reference_Marker
242 -- |
243 -- +- | -------------------- Recording phase ---------------------------+
244 -- | v |
245 -- | Record_Elaboration_Scenario |
246 -- | | |
247 -- | +--> Check_Preelaborated_Call |
248 -- | | |
249 -- | +--> Process_Guaranteed_ABE |
250 -- | | | |
251 -- | | +--> Process_Guaranteed_ABE_Activation |
252 -- | | +--> Process_Guaranteed_ABE_Call |
253 -- | | +--> Process_Guaranteed_ABE_Instantiation |
254 -- | | |
255 -- +- | ----------------------------------------------------------------+
256 -- |
257 -- |
258 -- +--> Internal_Representation
259 -- |
260 -- +--> Scenario_Storage
261 -- |
262 -- End of Compilation
263 -- |
264 -- +- | --------------------- Processing phase -------------------------+
265 -- | v |
266 -- | Check_Elaboration_Scenarios |
267 -- | | |
268 -- | +--> Check_Conditional_ABE_Scenarios |
269 -- | | | |
270 -- | | +--> Process_Conditional_ABE <----------------------+ |
271 -- | | | | |
272 -- | | +--> Process_Conditional_ABE_Activation | |
273 -- | | | | | |
274 -- | | | +-----------------------------+ | |
275 -- | | | | | |
276 -- | | +--> Process_Conditional_ABE_Call +---> Traverse_Body |
277 -- | | | | | |
278 -- | | | +-----------------------------+ |
279 -- | | | |
280 -- | | +--> Process_Conditional_ABE_Access_Taken |
281 -- | | +--> Process_Conditional_ABE_Instantiation |
282 -- | | +--> Process_Conditional_ABE_Variable_Assignment |
283 -- | | +--> Process_Conditional_ABE_Variable_Reference |
284 -- | | |
285 -- | +--> Check_SPARK_Scenario |
286 -- | | | |
287 -- | | +--> Process_SPARK_Scenario |
288 -- | | | |
289 -- | | +--> Process_SPARK_Derived_Type |
290 -- | | +--> Process_SPARK_Instantiation |
291 -- | | +--> Process_SPARK_Refined_State_Pragma |
292 -- | | |
293 -- | +--> Record_Invocation_Graph |
294 -- | | |
295 -- | +--> Process_Invocation_Body_Scenarios |
296 -- | +--> Process_Invocation_Spec_Scenarios |
297 -- | +--> Process_Main_Unit |
298 -- | | |
299 -- | +--> Process_Invocation_Scenario <-------------+ |
300 -- | | | |
301 -- | +--> Process_Invocation_Activation | |
302 -- | | | | |
303 -- | | +------------------------+ | |
304 -- | | | | |
305 -- | +--> Process_Invocation_Call +---> Traverse_Body |
306 -- | | | |
307 -- | +------------------------+ |
308 -- | |
309 -- +--------------------------------------------------------------------+
310
311 ---------------------
312 -- Recording phase --
313 ---------------------
314
315 -- The Recording phase coincides with the analysis/resolution phase of the
316 -- compiler. It has the following objectives:
317 --
318 -- * Record all suitable scenarios for examination by the Processing
319 -- phase.
320 --
321 -- Saving only a certain number of nodes improves the performance of
322 -- the ABE mechanism. This eliminates the need to examine the whole
323 -- tree in a separate pass.
324 --
325 -- * Record certain SPARK scenarios which are not necessarily invoked
326 -- during elaboration, but still require elaboration-related checks.
327 --
328 -- Saving only a certain number of nodes improves the performance of
329 -- the ABE mechanism. This eliminates the need to examine the whole
330 -- tree in a separate pass.
331 --
332 -- * Detect and diagnose calls in preelaborable or pure units, including
333 -- generic bodies.
334 --
335 -- This diagnostic is carried out during the Recording phase because it
336 -- does not need the heavy recursive traversal done by the Processing
337 -- phase.
338 --
339 -- * Detect and diagnose guaranteed ABEs caused by instantiations, calls,
340 -- and task activation.
341 --
342 -- The issues detected by the ABE mechanism are reported as warnings
343 -- because they do not violate Ada semantics. Forward instantiations
344 -- may thus reach gigi, however gigi cannot handle certain kinds of
345 -- premature instantiations and may crash. To avoid this limitation,
346 -- the ABE mechanism must identify forward instantiations as early as
347 -- possible and suppress their bodies. Calls and task activations are
348 -- included in this category for completeness.
349
350 ----------------------
351 -- Processing phase --
352 ----------------------
353
354 -- The Processing phase is a separate pass which starts after instantiating
355 -- and/or inlining of bodies, but before the removal of Ghost code. It has
356 -- the following objectives:
357 --
358 -- * Examine all scenarios saved during the Recording phase, and perform
359 -- the following actions:
360 --
361 -- - Dynamic model
362 --
363 -- Diagnose conditional ABEs, and install run-time conditional ABE
364 -- checks for all scenarios.
365 --
366 -- - SPARK model
367 --
368 -- Enforce the SPARK elaboration rules
369 --
370 -- - Static model
371 --
372 -- Diagnose conditional ABEs, install run-time conditional ABE
373 -- checks only for scenarios are reachable from elaboration code,
374 -- and guarantee the elaboration of external units by creating
375 -- implicit with clauses subject to pragma Elaborate[_All].
376 --
377 -- * Examine library-level scenarios and invocation constructs, and
378 -- perform the following actions:
379 --
380 -- - Determine whether the flow of execution reaches into an external
381 -- unit. If this is the case, encode the path in the ALI file of
382 -- the main unit.
383 --
384 -- - Create declarations for invocation constructs in the ALI file of
385 -- the main unit.
386
387 ----------------------
388 -- Important points --
389 ----------------------
390
391 -- The Processing phase starts after the analysis, resolution, expansion
392 -- phase has completed. As a result, no current semantic information is
393 -- available. The scope stack is empty, global flags such as In_Instance
394 -- or Inside_A_Generic become useless. To remedy this, the ABE mechanism
395 -- must either save or recompute semantic information.
396 --
397 -- Expansion heavily transforms calls and to some extent instantiations. To
398 -- remedy this, the ABE mechanism generates N_Call_Marker nodes in order to
399 -- capture the target and relevant attributes of the original call.
400 --
401 -- The diagnostics of the ABE mechanism depend on accurate source locations
402 -- to determine the spacial relation of nodes.
403
404 -----------------------------------------
405 -- Suppression of elaboration warnings --
406 -----------------------------------------
407
408 -- Elaboration warnings along multiple traversal paths rooted at a scenario
409 -- are suppressed when the scenario has elaboration warnings suppressed.
410 --
411 -- Root scenario
412 -- |
413 -- +-- Child scenario 1
414 -- | |
415 -- | +-- Grandchild scenario 1
416 -- | |
417 -- | +-- Grandchild scenario N
418 -- |
419 -- +-- Child scenario N
420 --
421 -- If the root scenario has elaboration warnings suppressed, then all its
422 -- child, grandchild, etc. scenarios will have their elaboration warnings
423 -- suppressed.
424 --
425 -- In addition to switch -gnatwL, pragma Warnings may be used to suppress
426 -- elaboration-related warnings when used in the following manner:
427 --
428 -- pragma Warnings ("L");
429 -- <scenario-or-target>
430 --
431 -- <target>
432 -- pragma Warnings (Off, target);
433 --
434 -- pragma Warnings (Off);
435 -- <scenario-or-target>
436 --
437 -- * To suppress elaboration warnings for '[Unrestricted_]Access of
438 -- entries, operators, and subprograms, either:
439 --
440 -- - Suppress the entry, operator, or subprogram, or
441 -- - Suppress the attribute, or
442 -- - Use switch -gnatw.f
443 --
444 -- * To suppress elaboration warnings for calls to entries, operators,
445 -- and subprograms, either:
446 --
447 -- - Suppress the entry, operator, or subprogram, or
448 -- - Suppress the call
449 --
450 -- * To suppress elaboration warnings for instantiations, suppress the
451 -- instantiation.
452 --
453 -- * To suppress elaboration warnings for task activations, either:
454 --
455 -- - Suppress the task object, or
456 -- - Suppress the task type, or
457 -- - Suppress the activation call
458
459 --------------
460 -- Switches --
461 --------------
462
463 -- The following switches may be used to control the behavior of the ABE
464 -- mechanism.
465 --
466 -- -gnatd_a stop elaboration checks on accept or select statement
467 --
468 -- The ABE mechanism stops the traversal of a task body when it
469 -- encounters an accept or a select statement. This behavior is
470 -- equivalent to restriction No_Entry_Calls_In_Elaboration_Code,
471 -- but without penalizing actual entry calls during elaboration.
472 --
473 -- -gnatd_e ignore entry calls and requeue statements for elaboration
474 --
475 -- The ABE mechanism does not generate N_Call_Marker nodes for
476 -- protected or task entry calls as well as requeue statements.
477 -- As a result, the calls and requeues are not recorded or
478 -- processed.
479 --
480 -- -gnatdE elaboration checks on predefined units
481 --
482 -- The ABE mechanism considers scenarios which appear in internal
483 -- units (Ada, GNAT, Interfaces, System).
484 --
485 -- -gnatd_F encode full invocation paths in ALI files
486 --
487 -- The ABE mechanism encodes the full path from an elaboration
488 -- procedure or invocable construct to an external target. The
489 -- path contains all intermediate activations, instantiations,
490 -- and calls.
491 --
492 -- -gnatd.G ignore calls through generic formal parameters for elaboration
493 --
494 -- The ABE mechanism does not generate N_Call_Marker nodes for
495 -- calls which occur in expanded instances, and invoke generic
496 -- actual subprograms through generic formal subprograms. As a
497 -- result, the calls are not recorded or processed.
498 --
499 -- -gnatd_G encode invocation graph in ALI files
500 --
501 -- The ABE mechanism encodes the invocation graph of the main
502 -- unit. This includes elaboration code, as well as invocation
503 -- constructs.
504 --
505 -- -gnatd_i ignore activations and calls to instances for elaboration
506 --
507 -- The ABE mechanism ignores calls and task activations when they
508 -- target a subprogram or task type defined an external instance.
509 -- As a result, the calls and task activations are not processed.
510 --
511 -- -gnatdL ignore external calls from instances for elaboration
512 --
513 -- The ABE mechanism does not generate N_Call_Marker nodes for
514 -- calls which occur in expanded instances, do not invoke generic
515 -- actual subprograms through formal subprograms, and the target
516 -- is external to the instance. As a result, the calls are not
517 -- recorded or processed.
518 --
519 -- -gnatd.o conservative elaboration order for indirect calls
520 --
521 -- The ABE mechanism treats '[Unrestricted_]Access of an entry,
522 -- operator, or subprogram as an immediate invocation of the
523 -- target. As a result, it performs ABE checks and diagnostics on
524 -- the immediate call.
525 --
526 -- -gnatd_p ignore assertion pragmas for elaboration
527 --
528 -- The ABE mechanism does not generate N_Call_Marker nodes for
529 -- calls to subprograms which verify the run-time semantics of
530 -- the following assertion pragmas:
531 --
532 -- Default_Initial_Condition
533 -- Initial_Condition
534 -- Invariant
535 -- Invariant'Class
536 -- Post
537 -- Post'Class
538 -- Postcondition
539 -- Type_Invariant
540 -- Type_Invariant_Class
541 --
542 -- As a result, the assertion expressions of the pragmas are not
543 -- processed.
544 --
545 -- -gnatd_s stop elaboration checks on synchronous suspension
546 --
547 -- The ABE mechanism stops the traversal of a task body when it
548 -- encounters a call to one of the following routines:
549 --
550 -- Ada.Synchronous_Barriers.Wait_For_Release
551 -- Ada.Synchronous_Task_Control.Suspend_Until_True
552 --
553 -- -gnatd_T output trace information on invocation relation construction
554 --
555 -- The ABE mechanism outputs text information concerning relation
556 -- construction to standard output.
557 --
558 -- -gnatd.U ignore indirect calls for static elaboration
559 --
560 -- The ABE mechanism does not consider '[Unrestricted_]Access of
561 -- entries, operators, and subprograms. As a result, the scenarios
562 -- are not recorder or processed.
563 --
564 -- -gnatd.v enforce SPARK elaboration rules in SPARK code
565 --
566 -- The ABE mechanism applies some of the SPARK elaboration rules
567 -- defined in the SPARK reference manual, chapter 7.7. Note that
568 -- certain rules are always enforced, regardless of whether the
569 -- switch is active.
570 --
571 -- -gnatd.y disable implicit pragma Elaborate_All on task bodies
572 --
573 -- The ABE mechanism does not generate implicit Elaborate_All when
574 -- the need for the pragma came from a task body.
575 --
576 -- -gnatE dynamic elaboration checking mode enabled
577 --
578 -- The ABE mechanism assumes that any scenario is elaborated or
579 -- invoked by elaboration code. The ABE mechanism performs very
580 -- little diagnostics and generates condintional ABE checks to
581 -- detect ABE issues at run-time.
582 --
583 -- -gnatel turn on info messages on generated Elaborate[_All] pragmas
584 --
585 -- The ABE mechanism produces information messages on generated
586 -- implicit Elabote[_All] pragmas along with traceback showing
587 -- why the pragma was generated. In addition, the ABE mechanism
588 -- produces information messages for each scenario elaborated or
589 -- invoked by elaboration code.
590 --
591 -- -gnateL turn off info messages on generated Elaborate[_All] pragmas
592 --
593 -- The complementary switch for -gnatel.
594 --
595 -- -gnatH legacy elaboration checking mode enabled
596 --
597 -- When this switch is in effect, the pre-18.x ABE model becomes
598 -- the defacto ABE model. This ammounts to cutting off all entry
599 -- points into the new ABE mechanism, and giving full control to
600 -- the old ABE mechanism.
601 --
602 -- -gnatJ permissive elaboration checking mode enabled
603 --
604 -- This switch activates the following switches:
605 --
606 -- -gnatd_a
607 -- -gnatd_e
608 -- -gnatd.G
609 -- -gnatd_i
610 -- -gnatdL
611 -- -gnatd_p
612 -- -gnatd_s
613 -- -gnatd.U
614 -- -gnatd.y
615 --
616 -- IMPORTANT: The behavior of the ABE mechanism becomes more
617 -- permissive at the cost of accurate diagnostics and runtime
618 -- ABE checks.
619 --
620 -- -gnatw.f turn on warnings for suspicious Subp'Access
621 --
622 -- The ABE mechanism treats '[Unrestricted_]Access of an entry,
623 -- operator, or subprogram as a pseudo invocation of the target.
624 -- As a result, it performs ABE diagnostics on the pseudo call.
625 --
626 -- -gnatw.F turn off warnings for suspicious Subp'Access
627 --
628 -- The complementary switch for -gnatw.f.
629 --
630 -- -gnatwl turn on warnings for elaboration problems
631 --
632 -- The ABE mechanism produces warnings on detected ABEs along with
633 -- a traceback showing the graph of the ABE.
634 --
635 -- -gnatwL turn off warnings for elaboration problems
636 --
637 -- The complementary switch for -gnatwl.
638
639 --------------------------
640 -- Debugging ABE issues --
641 --------------------------
642
643 -- * If the issue involves a call, ensure that the call is eligible for ABE
644 -- processing and receives a corresponding call marker. The routines of
645 -- interest are
646 --
647 -- Build_Call_Marker
648 -- Record_Elaboration_Scenario
649 --
650 -- * If the issue involves an arbitrary scenario, ensure that the scenario
651 -- is either recorded, or is successfully recognized while traversing a
652 -- body. The routines of interest are
653 --
654 -- Record_Elaboration_Scenario
655 -- Process_Conditional_ABE
656 -- Process_Guaranteed_ABE
657 -- Traverse_Body
658 --
659 -- * If the issue involves a circularity in the elaboration order, examine
660 -- the ALI files and look for the following encodings next to units:
661 --
662 -- E indicates a source Elaborate
663 --
664 -- EA indicates a source Elaborate_All
665 --
666 -- AD indicates an implicit Elaborate_All
667 --
668 -- ED indicates an implicit Elaborate
669 --
670 -- If possible, compare these encodings with those generated by the old
671 -- ABE mechanism. The routines of interest are
672 --
673 -- Ensure_Prior_Elaboration
674
675 -----------
676 -- Kinds --
677 -----------
678
679 -- The following type enumerates all possible elaboration phase statutes
680
681 type Elaboration_Phase_Status is
682 (Inactive,
683 -- The elaboration phase of the compiler has not started yet
684
685 Active,
686 -- The elaboration phase of the compiler is currently in progress
687
688 Completed);
689 -- The elaboration phase of the compiler has finished
690
691 Elaboration_Phase : Elaboration_Phase_Status := Inactive;
692 -- The status of the elaboration phase. Use routine Set_Elaboration_Phase
693 -- to alter its value.
694
695 -- The following type enumerates all subprogram body traversal modes
696
697 type Body_Traversal_Kind is
698 (Deep_Traversal,
699 -- The traversal examines the internals of a subprogram
700
701 No_Traversal);
702
703 -- The following type enumerates all operation modes
704
705 type Processing_Kind is
706 (Conditional_ABE_Processing,
707 -- The ABE mechanism detects and diagnoses conditional ABEs for library
708 -- and declaration-level scenarios.
709
710 Dynamic_Model_Processing,
711 -- The ABE mechanism installs conditional ABE checks for all eligible
712 -- scenarios when the dynamic model is in effect.
713
714 Guaranteed_ABE_Processing,
715 -- The ABE mechanism detects and diagnoses guaranteed ABEs caused by
716 -- calls, instantiations, and task activations.
717
718 Invocation_Construct_Processing,
719 -- The ABE mechanism locates all invocation constructs within the main
720 -- unit and utilizes them as roots of miltiple DFS traversals aimed at
721 -- detecting transitions from the main unit to an external unit.
722
723 Invocation_Body_Processing,
724 -- The ABE mechanism utilizes all library-level body scenarios as roots
725 -- of miltiple DFS traversals aimed at detecting transitions from the
726 -- main unit to an external unit.
727
728 Invocation_Spec_Processing,
729 -- The ABE mechanism utilizes all library-level spec scenarios as roots
730 -- of miltiple DFS traversals aimed at detecting transitions from the
731 -- main unit to an external unit.
732
733 SPARK_Processing,
734 -- The ABE mechanism detects and diagnoses violations of the SPARK
735 -- elaboration rules for SPARK-specific scenarios.
736
737 No_Processing);
738
739 -- The following type enumerates all possible scenario kinds
740
741 type Scenario_Kind is
742 (Access_Taken_Scenario,
743 -- An attribute reference which takes 'Access or 'Unrestricted_Access of
744 -- an entry, operator, or subprogram.
745
746 Call_Scenario,
747 -- A call which invokes an entry, operator, or subprogram
748
749 Derived_Type_Scenario,
750 -- A declaration of a derived type. This is a SPARK-specific scenario.
751
752 Instantiation_Scenario,
753 -- An instantiation which instantiates a generic package or subprogram.
754 -- This scenario is also subject to SPARK-specific rules.
755
756 Refined_State_Pragma_Scenario,
757 -- A Refined_State pragma. This is a SPARK-specific scenario.
758
759 Task_Activation_Scenario,
760 -- A call which activates objects of various task types
761
762 Variable_Assignment_Scenario,
763 -- An assignment statement which modifies the value of some variable
764
765 Variable_Reference_Scenario,
766 -- A reference to a variable. This is a SPARK-specific scenario.
767
768 No_Scenario);
769
770 -- The following type enumerates all possible consistency models of target
771 -- and scenario representations.
772
773 type Representation_Kind is
774 (Inconsistent_Representation,
775 -- A representation is said to be "inconsistent" when it is created from
776 -- a partially analyzed tree. In such an environment, certain attributes
777 -- such as a completing body may not be available yet.
778
779 Consistent_Representation,
780 -- A representation is said to be "consistent" when it is created from a
781 -- fully analyzed tree, where all attributes are available.
782
783 No_Representation);
784
785 -- The following type enumerates all possible target kinds
786
787 type Target_Kind is
788 (Generic_Target,
789 -- A generic unit being instantiated
790
791 Subprogram_Target,
792 -- An entry, operator, or subprogram being invoked, or aliased through
793 -- 'Access or 'Unrestricted_Access.
794
795 Task_Target,
796 -- A task being activated by an activation call
797
798 Variable_Target,
799 -- A variable being updated through an assignment statement, or read
800 -- through a variable reference.
801
802 No_Target);
803
804 -----------
805 -- Types --
806 -----------
807
808 procedure Destroy (NE : in out Node_Or_Entity_Id);
809 pragma Inline (Destroy);
810 -- Destroy node or entity NE
811
812 function Hash (NE : Node_Or_Entity_Id) return Bucket_Range_Type;
813 pragma Inline (Hash);
814 -- Obtain the hash value of key NE
815
816 -- The following is a general purpose list for nodes and entities
817
818 package NE_List is new Doubly_Linked_Lists
819 (Element_Type => Node_Or_Entity_Id,
820 "=" => "=",
821 Destroy_Element => Destroy);
822
823 -- The following is a general purpose map which relates nodes and entities
824 -- to lists of nodes and entities.
825
826 package NE_List_Map is new Dynamic_Hash_Tables
827 (Key_Type => Node_Or_Entity_Id,
828 Value_Type => NE_List.Doubly_Linked_List,
829 No_Value => NE_List.Nil,
830 Expansion_Threshold => 1.5,
831 Expansion_Factor => 2,
832 Compression_Threshold => 0.3,
833 Compression_Factor => 2,
834 "=" => "=",
835 Destroy_Value => NE_List.Destroy,
836 Hash => Hash);
837
838 -- The following is a general purpose membership set for nodes and entities
839
840 package NE_Set is new Membership_Sets
841 (Element_Type => Node_Or_Entity_Id,
842 "=" => "=",
843 Hash => Hash);
844
845 -- The following type captures relevant attributes which pertain to the
846 -- in state of the Processing phase.
847
848 type Processing_In_State is record
849 Processing : Processing_Kind := No_Processing;
850 -- Operation mode of the Processing phase. Once set, this value should
851 -- not be changed.
852
853 Representation : Representation_Kind := No_Representation;
854 -- Required level of scenario and target representation. Once set, this
855 -- value should not be changed.
856
857 Suppress_Checks : Boolean := False;
858 -- This flag is set when the Processing phase must not generate any ABE
859 -- checks.
860
861 Suppress_Implicit_Pragmas : Boolean := False;
862 -- This flag is set when the Processing phase must not generate any
863 -- implicit Elaborate[_All] pragmas.
864
865 Suppress_Info_Messages : Boolean := False;
866 -- This flag is set when the Processing phase must not emit any info
867 -- messages.
868
869 Suppress_Up_Level_Targets : Boolean := False;
870 -- This flag is set when the Processing phase must ignore up-level
871 -- targets.
872
873 Suppress_Warnings : Boolean := False;
874 -- This flag is set when the Processing phase must not emit any warnings
875 -- on elaboration problems.
876
877 Traversal : Body_Traversal_Kind := No_Traversal;
878 -- The subprogram body traversal mode. Once set, this value should not
879 -- be changed.
880
881 Within_Generic : Boolean := False;
882 -- This flag is set when the Processing phase is currently within a
883 -- generic unit.
884
885 Within_Initial_Condition : Boolean := False;
886 -- This flag is set when the Processing phase is currently examining a
887 -- scenario which was reached from an initial condition procedure.
888
889 Within_Partial_Finalization : Boolean := False;
890 -- This flag is set when the Processing phase is currently examining a
891 -- scenario which was reached from a partial finalization procedure.
892
893 Within_Task_Body : Boolean := False;
894 -- This flag is set when the Processing phase is currently examining a
895 -- scenario which was reached from a task body.
896 end record;
897
898 -- The following constants define the various operational states of the
899 -- Processing phase.
900
901 -- The conditional ABE state is used when processing scenarios that appear
902 -- at the declaration, instantiation, and library levels to detect errors
903 -- and install conditional ABE checks.
904
905 Conditional_ABE_State : constant Processing_In_State :=
906 (Processing => Conditional_ABE_Processing,
907 Representation => Consistent_Representation,
908 Traversal => Deep_Traversal,
909 others => False);
910
911 -- The dynamic model state is used to install conditional ABE checks when
912 -- switch -gnatE (dynamic elaboration checking mode enabled) is in effect.
913
914 Dynamic_Model_State : constant Processing_In_State :=
915 (Processing => Dynamic_Model_Processing,
916 Representation => Consistent_Representation,
917 Suppress_Implicit_Pragmas => True,
918 Suppress_Info_Messages => True,
919 Suppress_Up_Level_Targets => True,
920 Suppress_Warnings => True,
921 Traversal => No_Traversal,
922 others => False);
923
924 -- The guaranteed ABE state is used when processing scenarios that appear
925 -- at the declaration, instantiation, and library levels to detect errors
926 -- and install guarateed ABE failures.
927
928 Guaranteed_ABE_State : constant Processing_In_State :=
929 (Processing => Guaranteed_ABE_Processing,
930 Representation => Inconsistent_Representation,
931 Suppress_Implicit_Pragmas => True,
932 Traversal => No_Traversal,
933 others => False);
934
935 -- The invocation body state is used when processing scenarios that appear
936 -- at the body library level to encode paths that start from elaboration
937 -- code and ultimately reach into external units.
938
939 Invocation_Body_State : constant Processing_In_State :=
940 (Processing => Invocation_Body_Processing,
941 Representation => Consistent_Representation,
942 Suppress_Checks => True,
943 Suppress_Implicit_Pragmas => True,
944 Suppress_Info_Messages => True,
945 Suppress_Up_Level_Targets => True,
946 Suppress_Warnings => True,
947 Traversal => Deep_Traversal,
948 others => False);
949
950 -- The invocation construct state is used when processing constructs that
951 -- appear within the spec and body of the main unit and eventually reach
952 -- into external units.
953
954 Invocation_Construct_State : constant Processing_In_State :=
955 (Processing => Invocation_Construct_Processing,
956 Representation => Consistent_Representation,
957 Suppress_Checks => True,
958 Suppress_Implicit_Pragmas => True,
959 Suppress_Info_Messages => True,
960 Suppress_Up_Level_Targets => True,
961 Suppress_Warnings => True,
962 Traversal => Deep_Traversal,
963 others => False);
964
965 -- The invocation spec state is used when processing scenarios that appear
966 -- at the spec library level to encode paths that start from elaboration
967 -- code and ultimately reach into external units.
968
969 Invocation_Spec_State : constant Processing_In_State :=
970 (Processing => Invocation_Spec_Processing,
971 Representation => Consistent_Representation,
972 Suppress_Checks => True,
973 Suppress_Implicit_Pragmas => True,
974 Suppress_Info_Messages => True,
975 Suppress_Up_Level_Targets => True,
976 Suppress_Warnings => True,
977 Traversal => Deep_Traversal,
978 others => False);
979
980 -- The SPARK state is used when verying SPARK-specific semantics of certain
981 -- scenarios.
982
983 SPARK_State : constant Processing_In_State :=
984 (Processing => SPARK_Processing,
985 Representation => Consistent_Representation,
986 Traversal => No_Traversal,
987 others => False);
988
989 -- The following type identifies a scenario representation
990
991 type Scenario_Rep_Id is new Natural;
992
993 No_Scenario_Rep : constant Scenario_Rep_Id := Scenario_Rep_Id'First;
994 First_Scenario_Rep : constant Scenario_Rep_Id := No_Scenario_Rep + 1;
995
996 -- The following type identifies a target representation
997
998 type Target_Rep_Id is new Natural;
999
1000 No_Target_Rep : constant Target_Rep_Id := Target_Rep_Id'First;
1001 First_Target_Rep : constant Target_Rep_Id := No_Target_Rep + 1;
1002
1003 --------------
1004 -- Services --
1005 --------------
1006
1007 -- The following package keeps track of all active scenarios during a DFS
1008 -- traversal.
1009
1010 package Active_Scenarios is
1011
1012 -----------
1013 -- Types --
1014 -----------
1015
1016 -- The following type defines the position within the active scenario
1017 -- stack.
1018
1019 type Active_Scenario_Pos is new Natural;
1020
1021 ---------------------
1022 -- Data structures --
1023 ---------------------
1024
1025 -- The following table stores all active scenarios in a DFS traversal.
1026 -- This table must be maintained in a FIFO fashion.
1027
1028 package Active_Scenario_Stack is new Table.Table
1029 (Table_Index_Type => Active_Scenario_Pos,
1030 Table_Component_Type => Node_Id,
1031 Table_Low_Bound => 1,
1032 Table_Initial => 50,
1033 Table_Increment => 200,
1034 Table_Name => "Active_Scenario_Stack");
1035
1036 ---------
1037 -- API --
1038 ---------
1039
1040 procedure Output_Active_Scenarios
1041 (Error_Nod : Node_Id;
1042 In_State : Processing_In_State);
1043 pragma Inline (Output_Active_Scenarios);
1044 -- Output the contents of the active scenario stack from earliest to
1045 -- latest to supplement an earlier error emitted for node Error_Nod.
1046 -- In_State denotes the current state of the Processing phase.
1047
1048 procedure Pop_Active_Scenario (N : Node_Id);
1049 pragma Inline (Pop_Active_Scenario);
1050 -- Pop the top of the scenario stack. A check is made to ensure that the
1051 -- scenario being removed is the same as N.
1052
1053 procedure Push_Active_Scenario (N : Node_Id);
1054 pragma Inline (Push_Active_Scenario);
1055 -- Push scenario N on top of the scenario stack
1056
1057 function Root_Scenario return Node_Id;
1058 pragma Inline (Root_Scenario);
1059 -- Return the scenario which started a DFS traversal
1060
1061 end Active_Scenarios;
1062 use Active_Scenarios;
1063
1064 -- The following package provides the main entry point for task activation
1065 -- processing.
1066
1067 package Activation_Processor is
1068
1069 -----------
1070 -- Types --
1071 -----------
1072
1073 type Activation_Processor_Ptr is access procedure
1074 (Call : Node_Id;
1075 Call_Rep : Scenario_Rep_Id;
1076 Obj_Id : Entity_Id;
1077 Obj_Rep : Target_Rep_Id;
1078 Task_Typ : Entity_Id;
1079 Task_Rep : Target_Rep_Id;
1080 In_State : Processing_In_State);
1081 -- Reference to a procedure that takes all attributes of an activation
1082 -- and performs a desired action. Call is the activation call. Call_Rep
1083 -- is the representation of the call. Obj_Id is the task object being
1084 -- activated. Obj_Rep is the representation of the object. Task_Typ is
1085 -- the task type whose body is being activated. Task_Rep denotes the
1086 -- representation of the task type. In_State is the current state of
1087 -- the Processing phase.
1088
1089 ---------
1090 -- API --
1091 ---------
1092
1093 procedure Process_Activation
1094 (Call : Node_Id;
1095 Call_Rep : Scenario_Rep_Id;
1096 Processor : Activation_Processor_Ptr;
1097 In_State : Processing_In_State);
1098 -- Find all task objects activated by activation call Call and invoke
1099 -- Processor on them. Call_Rep denotes the representation of the call.
1100 -- In_State is the current state of the Processing phase.
1101
1102 end Activation_Processor;
1103 use Activation_Processor;
1104
1105 -- The following package profides functionality for traversing subprogram
1106 -- bodies in DFS manner and processing of eligible scenarios within.
1107
1108 package Body_Processor is
1109
1110 -----------
1111 -- Types --
1112 -----------
1113
1114 type Scenario_Predicate_Ptr is access function
1115 (N : Node_Id) return Boolean;
1116 -- Reference to a function which determines whether arbitrary node N
1117 -- denotes a suitable scenario for processing.
1118
1119 type Scenario_Processor_Ptr is access procedure
1120 (N : Node_Id; In_State : Processing_In_State);
1121 -- Reference to a procedure which processes scenario N. In_State is the
1122 -- current state of the Processing phase.
1123
1124 ---------
1125 -- API --
1126 ---------
1127
1128 procedure Traverse_Body
1129 (N : Node_Id;
1130 Requires_Processing : Scenario_Predicate_Ptr;
1131 Processor : Scenario_Processor_Ptr;
1132 In_State : Processing_In_State);
1133 pragma Inline (Traverse_Body);
1134 -- Traverse the declarations and handled statements of subprogram body
1135 -- N, looking for scenarios that satisfy predicate Requires_Processing.
1136 -- Routine Processor is invoked for each such scenario.
1137
1138 procedure Reset_Traversed_Bodies;
1139 pragma Inline (Reset_Traversed_Bodies);
1140 -- Reset the visited status of all subprogram bodies that have already
1141 -- been processed by routine Traverse_Body.
1142
1143 -----------------
1144 -- Maintenance --
1145 -----------------
1146
1147 procedure Finalize_Body_Processor;
1148 pragma Inline (Finalize_Body_Processor);
1149 -- Finalize all internal data structures
1150
1151 procedure Initialize_Body_Processor;
1152 pragma Inline (Initialize_Body_Processor);
1153 -- Initialize all internal data structures
1154
1155 end Body_Processor;
1156 use Body_Processor;
1157
1158 -- The following package provides functionality for installing ABE-related
1159 -- checks and failures.
1160
1161 package Check_Installer is
1162
1163 ---------
1164 -- API --
1165 ---------
1166
1167 function Check_Or_Failure_Generation_OK return Boolean;
1168 pragma Inline (Check_Or_Failure_Generation_OK);
1169 -- Determine whether a conditional ABE check or guaranteed ABE failure
1170 -- can be generated.
1171
1172 procedure Install_Dynamic_ABE_Checks;
1173 pragma Inline (Install_Dynamic_ABE_Checks);
1174 -- Install conditional ABE checks for all saved scenarios when the
1175 -- dynamic model is in effect.
1176
1177 procedure Install_Scenario_ABE_Check
1178 (N : Node_Id;
1179 Targ_Id : Entity_Id;
1180 Targ_Rep : Target_Rep_Id;
1181 Disable : Scenario_Rep_Id);
1182 pragma Inline (Install_Scenario_ABE_Check);
1183 -- Install a conditional ABE check for scenario N to ensure that target
1184 -- Targ_Id is properly elaborated. Targ_Rep is the representation of the
1185 -- target. If the check is installed, disable the elaboration checks of
1186 -- scenario Disable.
1187
1188 procedure Install_Scenario_ABE_Check
1189 (N : Node_Id;
1190 Targ_Id : Entity_Id;
1191 Targ_Rep : Target_Rep_Id;
1192 Disable : Target_Rep_Id);
1193 pragma Inline (Install_Scenario_ABE_Check);
1194 -- Install a conditional ABE check for scenario N to ensure that target
1195 -- Targ_Id is properly elaborated. Targ_Rep is the representation of the
1196 -- target. If the check is installed, disable the elaboration checks of
1197 -- target Disable.
1198
1199 procedure Install_Scenario_ABE_Failure
1200 (N : Node_Id;
1201 Targ_Id : Entity_Id;
1202 Targ_Rep : Target_Rep_Id;
1203 Disable : Scenario_Rep_Id);
1204 pragma Inline (Install_Scenario_ABE_Failure);
1205 -- Install a guaranteed ABE failure for scenario N with target Targ_Id.
1206 -- Targ_Rep denotes the representation of the target. If the failure is
1207 -- installed, disable the elaboration checks of scenario Disable.
1208
1209 procedure Install_Scenario_ABE_Failure
1210 (N : Node_Id;
1211 Targ_Id : Entity_Id;
1212 Targ_Rep : Target_Rep_Id;
1213 Disable : Target_Rep_Id);
1214 pragma Inline (Install_Scenario_ABE_Failure);
1215 -- Install a guaranteed ABE failure for scenario N with target Targ_Id.
1216 -- Targ_Rep denotes the representation of the target. If the failure is
1217 -- installed, disable the elaboration checks of target Disable.
1218
1219 procedure Install_Unit_ABE_Check
1220 (N : Node_Id;
1221 Unit_Id : Entity_Id;
1222 Disable : Scenario_Rep_Id);
1223 pragma Inline (Install_Unit_ABE_Check);
1224 -- Install a conditional ABE check for scenario N to ensure that unit
1225 -- Unit_Id is properly elaborated. If the check is installed, disable
1226 -- the elaboration checks of scenario Disable.
1227
1228 procedure Install_Unit_ABE_Check
1229 (N : Node_Id;
1230 Unit_Id : Entity_Id;
1231 Disable : Target_Rep_Id);
1232 pragma Inline (Install_Unit_ABE_Check);
1233 -- Install a conditional ABE check for scenario N to ensure that unit
1234 -- Unit_Id is properly elaborated. If the check is installed, disable
1235 -- the elaboration checks of target Disable.
1236
1237 end Check_Installer;
1238 use Check_Installer;
1239
1240 -- The following package provides the main entry point for conditional ABE
1241 -- checks and diagnostics.
1242
1243 package Conditional_ABE_Processor is
1244
1245 ---------
1246 -- API --
1247 ---------
1248
1249 procedure Check_Conditional_ABE_Scenarios
1250 (Iter : in out NE_Set.Iterator);
1251 pragma Inline (Check_Conditional_ABE_Scenarios);
1252 -- Perform conditional ABE checks and diagnostics for all scenarios
1253 -- available through iterator Iter.
1254
1255 procedure Process_Conditional_ABE
1256 (N : Node_Id;
1257 In_State : Processing_In_State);
1258 pragma Inline (Process_Conditional_ABE);
1259 -- Perform conditional ABE checks and diagnostics for scenario N.
1260 -- In_State denotes the current state of the Processing phase.
1261
1262 end Conditional_ABE_Processor;
1263 use Conditional_ABE_Processor;
1264
1265 -- The following package provides functionality to emit errors, information
1266 -- messages, and warnings.
1267
1268 package Diagnostics is
1269
1270 ---------
1271 -- API --
1272 ---------
1273
1274 procedure Elab_Msg_NE
1275 (Msg : String;
1276 N : Node_Id;
1277 Id : Entity_Id;
1278 Info_Msg : Boolean;
1279 In_SPARK : Boolean);
1280 pragma Inline (Elab_Msg_NE);
1281 -- Wrapper around Error_Msg_NE. Emit message Msg concerning arbitrary
1282 -- node N and entity. If flag Info_Msg is set, the routine emits an
1283 -- information message, otherwise it emits an error. If flag In_SPARK
1284 -- is set, then string " in SPARK" is added to the end of the message.
1285
1286 procedure Info_Call
1287 (Call : Node_Id;
1288 Subp_Id : Entity_Id;
1289 Info_Msg : Boolean;
1290 In_SPARK : Boolean);
1291 pragma Inline (Info_Call);
1292 -- Output information concerning call Call that invokes subprogram
1293 -- Subp_Id. When flag Info_Msg is set, the routine emits an information
1294 -- message, otherwise it emits an error. When flag In_SPARK is set, " in
1295 -- SPARK" is added to the end of the message.
1296
1297 procedure Info_Instantiation
1298 (Inst : Node_Id;
1299 Gen_Id : Entity_Id;
1300 Info_Msg : Boolean;
1301 In_SPARK : Boolean);
1302 pragma Inline (Info_Instantiation);
1303 -- Output information concerning instantiation Inst which instantiates
1304 -- generic unit Gen_Id. If flag Info_Msg is set, the routine emits an
1305 -- information message, otherwise it emits an error. If flag In_SPARK
1306 -- is set, then string " in SPARK" is added to the end of the message.
1307
1308 procedure Info_Variable_Reference
1309 (Ref : Node_Id;
1310 Var_Id : Entity_Id;
1311 Info_Msg : Boolean;
1312 In_SPARK : Boolean);
1313 pragma Inline (Info_Variable_Reference);
1314 -- Output information concerning reference Ref which mentions variable
1315 -- Var_Id. If flag Info_Msg is set, the routine emits an information
1316 -- message, otherwise it emits an error. If flag In_SPARK is set, then
1317 -- string " in SPARK" is added to the end of the message.
1318
1319 end Diagnostics;
1320 use Diagnostics;
1321
1322 -- The following package provides functionality to locate the early call
1323 -- region of a subprogram body.
1324
1325 package Early_Call_Region_Processor is
1326
1327 ---------
1328 -- API --
1329 ---------
1330
1331 function Find_Early_Call_Region
1332 (Body_Decl : Node_Id;
1333 Assume_Elab_Body : Boolean := False;
1334 Skip_Memoization : Boolean := False) return Node_Id;
1335 pragma Inline (Find_Early_Call_Region);
1336 -- Find the start of the early call region that belongs to subprogram
1337 -- body Body_Decl as defined in SPARK RM 7.7. This routine finds the
1338 -- early call region, memoizes it, and returns it, but this behavior
1339 -- can be altered. Flag Assume_Elab_Body should be set when a package
1340 -- spec may lack pragma Elaborate_Body, but the routine must still
1341 -- examine that spec. Flag Skip_Memoization should be set when the
1342 -- routine must avoid memoizing the region.
1343
1344 -----------------
1345 -- Maintenance --
1346 -----------------
1347
1348 procedure Finalize_Early_Call_Region_Processor;
1349 pragma Inline (Finalize_Early_Call_Region_Processor);
1350 -- Finalize all internal data structures
1351
1352 procedure Initialize_Early_Call_Region_Processor;
1353 pragma Inline (Initialize_Early_Call_Region_Processor);
1354 -- Initialize all internal data structures
1355
1356 end Early_Call_Region_Processor;
1357 use Early_Call_Region_Processor;
1358
1359 -- The following package provides access to the elaboration statuses of all
1360 -- units withed by the main unit.
1361
1362 package Elaborated_Units is
1363
1364 ---------
1365 -- API --
1366 ---------
1367
1368 procedure Collect_Elaborated_Units;
1369 pragma Inline (Collect_Elaborated_Units);
1370 -- Save the elaboration statuses of all units withed by the main unit
1371
1372 procedure Ensure_Prior_Elaboration
1373 (N : Node_Id;
1374 Unit_Id : Entity_Id;
1375 Prag_Nam : Name_Id;
1376 In_State : Processing_In_State);
1377 pragma Inline (Ensure_Prior_Elaboration);
1378 -- Guarantee the elaboration of unit Unit_Id with respect to the main
1379 -- unit by either suggesting or installing an Elaborate[_All] pragma
1380 -- denoted by Prag_Nam. N denotes the related scenario. In_State is the
1381 -- current state of the Processing phase.
1382
1383 function Has_Prior_Elaboration
1384 (Unit_Id : Entity_Id;
1385 Context_OK : Boolean := False;
1386 Elab_Body_OK : Boolean := False;
1387 Same_Unit_OK : Boolean := False) return Boolean;
1388 pragma Inline (Has_Prior_Elaboration);
1389 -- Determine whether unit Unit_Id is elaborated prior to the main unit.
1390 -- If flag Context_OK is set, the routine considers the following case
1391 -- as valid prior elaboration:
1392 --
1393 -- * Unit_Id is in the elaboration context of the main unit
1394 --
1395 -- If flag Elab_Body_OK is set, the routine considers the following case
1396 -- as valid prior elaboration:
1397 --
1398 -- * Unit_Id has pragma Elaborate_Body and is not the main unit
1399 --
1400 -- If flag Same_Unit_OK is set, the routine considers the following
1401 -- cases as valid prior elaboration:
1402 --
1403 -- * Unit_Id is the main unit
1404 --
1405 -- * Unit_Id denotes the spec of the main unit body
1406
1407 procedure Meet_Elaboration_Requirement
1408 (N : Node_Id;
1409 Targ_Id : Entity_Id;
1410 Req_Nam : Name_Id;
1411 In_State : Processing_In_State);
1412 pragma Inline (Meet_Elaboration_Requirement);
1413 -- Determine whether elaboration requirement Req_Nam for scenario N with
1414 -- target Targ_Id is met by the context of the main unit using the SPARK
1415 -- rules. Req_Nam must denote either Elaborate or Elaborate_All. Emit an
1416 -- error if this is not the case. In_State denotes the current state of
1417 -- the Processing phase.
1418
1419 -----------------
1420 -- Maintenance --
1421 -----------------
1422
1423 procedure Finalize_Elaborated_Units;
1424 pragma Inline (Finalize_Elaborated_Units);
1425 -- Finalize all internal data structures
1426
1427 procedure Initialize_Elaborated_Units;
1428 pragma Inline (Initialize_Elaborated_Units);
1429 -- Initialize all internal data structures
1430
1431 end Elaborated_Units;
1432 use Elaborated_Units;
1433
1434 -- The following package provides the main entry point for guaranteed ABE
1435 -- checks and diagnostics.
1436
1437 package Guaranteed_ABE_Processor is
1438
1439 ---------
1440 -- API --
1441 ---------
1442
1443 procedure Process_Guaranteed_ABE
1444 (N : Node_Id;
1445 In_State : Processing_In_State);
1446 pragma Inline (Process_Guaranteed_ABE);
1447 -- Perform guaranteed ABE checks and diagnostics for scenario N.
1448 -- In_State is the current state of the Processing phase.
1449
1450 end Guaranteed_ABE_Processor;
1451 use Guaranteed_ABE_Processor;
1452
1453 -- The following package provides access to the internal representation of
1454 -- scenarios and targets.
1455
1456 package Internal_Representation is
1457
1458 -----------
1459 -- Types --
1460 -----------
1461
1462 -- The following type enumerates all possible Ghost mode mode kinds
1463
1464 type Extended_Ghost_Mode is
1465 (Is_Ignored,
1466 Is_Checked_Or_Not_Specified);
1467
1468 -- The following type enumerates all possible SPARK mode kinds
1469
1470 type Extended_SPARK_Mode is
1471 (Is_On,
1472 Is_Off_Or_Not_Specified);
1473
1474 --------------
1475 -- Builders --
1476 --------------
1477
1478 function Scenario_Representation_Of
1479 (N : Node_Id;
1480 In_State : Processing_In_State) return Scenario_Rep_Id;
1481 pragma Inline (Scenario_Representation_Of);
1482 -- Obtain the id of elaboration scenario N's representation. The routine
1483 -- constructs the representation if it is not available. In_State is the
1484 -- current state of the Processing phase.
1485
1486 function Target_Representation_Of
1487 (Id : Entity_Id;
1488 In_State : Processing_In_State) return Target_Rep_Id;
1489 pragma Inline (Target_Representation_Of);
1490 -- Obtain the id of elaboration target Id's representation. The routine
1491 -- constructs the representation if it is not available. In_State is the
1492 -- current state of the Processing phase.
1493
1494 -------------------------
1495 -- Scenario attributes --
1496 -------------------------
1497
1498 function Activated_Task_Objects
1499 (S_Id : Scenario_Rep_Id) return NE_List.Doubly_Linked_List;
1500 pragma Inline (Activated_Task_Objects);
1501 -- For Task_Activation_Scenario S_Id, obtain the list of task objects
1502 -- the scenario is activating.
1503
1504 function Activated_Task_Type (S_Id : Scenario_Rep_Id) return Entity_Id;
1505 pragma Inline (Activated_Task_Type);
1506 -- For Task_Activation_Scenario S_Id, obtain the currently activated
1507 -- task type.
1508
1509 procedure Disable_Elaboration_Checks (S_Id : Scenario_Rep_Id);
1510 pragma Inline (Disable_Elaboration_Checks);
1511 -- Disable elaboration checks of scenario S_Id
1512
1513 function Elaboration_Checks_OK (S_Id : Scenario_Rep_Id) return Boolean;
1514 pragma Inline (Elaboration_Checks_OK);
1515 -- Determine whether scenario S_Id may be subjected to elaboration
1516 -- checks.
1517
1518 function Elaboration_Warnings_OK (S_Id : Scenario_Rep_Id) return Boolean;
1519 pragma Inline (Elaboration_Warnings_OK);
1520 -- Determine whether scenario S_Id may be subjected to elaboration
1521 -- warnings.
1522
1523 function Ghost_Mode_Of
1524 (S_Id : Scenario_Rep_Id) return Extended_Ghost_Mode;
1525 pragma Inline (Ghost_Mode_Of);
1526 -- Obtain the Ghost mode of scenario S_Id
1527
1528 function Is_Dispatching_Call (S_Id : Scenario_Rep_Id) return Boolean;
1529 pragma Inline (Is_Dispatching_Call);
1530 -- For Call_Scenario S_Id, determine whether the call is dispatching
1531
1532 function Is_Read_Reference (S_Id : Scenario_Rep_Id) return Boolean;
1533 pragma Inline (Is_Read_Reference);
1534 -- For Variable_Reference_Scenario S_Id, determine whether the reference
1535 -- is a read.
1536
1537 function Kind (S_Id : Scenario_Rep_Id) return Scenario_Kind;
1538 pragma Inline (Kind);
1539 -- Obtain the nature of scenario S_Id
1540
1541 function Level (S_Id : Scenario_Rep_Id) return Enclosing_Level_Kind;
1542 pragma Inline (Level);
1543 -- Obtain the enclosing level of scenario S_Id
1544
1545 procedure Set_Activated_Task_Objects
1546 (S_Id : Scenario_Rep_Id;
1547 Task_Objs : NE_List.Doubly_Linked_List);
1548 pragma Inline (Set_Activated_Task_Objects);
1549 -- For Task_Activation_Scenario S_Id, set the list of task objects
1550 -- activated by the scenario to Task_Objs.
1551
1552 procedure Set_Activated_Task_Type
1553 (S_Id : Scenario_Rep_Id;
1554 Task_Typ : Entity_Id);
1555 pragma Inline (Set_Activated_Task_Type);
1556 -- For Task_Activation_Scenario S_Id, set the currently activated task
1557 -- type to Task_Typ.
1558
1559 function SPARK_Mode_Of
1560 (S_Id : Scenario_Rep_Id) return Extended_SPARK_Mode;
1561 pragma Inline (SPARK_Mode_Of);
1562 -- Obtain the SPARK mode of scenario S_Id
1563
1564 function Target (S_Id : Scenario_Rep_Id) return Entity_Id;
1565 pragma Inline (Target);
1566 -- Obtain the target of scenario S_Id
1567
1568 -----------------------
1569 -- Target attributes --
1570 -----------------------
1571
1572 function Barrier_Body_Declaration (T_Id : Target_Rep_Id) return Node_Id;
1573 pragma Inline (Barrier_Body_Declaration);
1574 -- For Subprogram_Target T_Id, obtain the declaration of the barrier
1575 -- function's body.
1576
1577 function Body_Declaration (T_Id : Target_Rep_Id) return Node_Id;
1578 pragma Inline (Body_Declaration);
1579 -- Obtain the declaration of the body which belongs to target T_Id
1580
1581 procedure Disable_Elaboration_Checks (T_Id : Target_Rep_Id);
1582 pragma Inline (Disable_Elaboration_Checks);
1583 -- Disable elaboration checks of target T_Id
1584
1585 function Elaboration_Checks_OK (T_Id : Target_Rep_Id) return Boolean;
1586 pragma Inline (Elaboration_Checks_OK);
1587 -- Determine whether target T_Id may be subjected to elaboration checks
1588
1589 function Elaboration_Warnings_OK (T_Id : Target_Rep_Id) return Boolean;
1590 pragma Inline (Elaboration_Warnings_OK);
1591 -- Determine whether target T_Id may be subjected to elaboration
1592 -- warnings.
1593
1594 function Ghost_Mode_Of (T_Id : Target_Rep_Id) return Extended_Ghost_Mode;
1595 pragma Inline (Ghost_Mode_Of);
1596 -- Obtain the Ghost mode of target T_Id
1597
1598 function Kind (T_Id : Target_Rep_Id) return Target_Kind;
1599 pragma Inline (Kind);
1600 -- Obtain the nature of target T_Id
1601
1602 function SPARK_Mode_Of (T_Id : Target_Rep_Id) return Extended_SPARK_Mode;
1603 pragma Inline (SPARK_Mode_Of);
1604 -- Obtain the SPARK mode of target T_Id
1605
1606 function Spec_Declaration (T_Id : Target_Rep_Id) return Node_Id;
1607 pragma Inline (Spec_Declaration);
1608 -- Obtain the declaration of the spec which belongs to target T_Id
1609
1610 function Unit (T_Id : Target_Rep_Id) return Entity_Id;
1611 pragma Inline (Unit);
1612 -- Obtain the unit where the target is defined
1613
1614 function Variable_Declaration (T_Id : Target_Rep_Id) return Node_Id;
1615 pragma Inline (Variable_Declaration);
1616 -- For Variable_Target T_Id, obtain the declaration of the variable
1617
1618 -----------------
1619 -- Maintenance --
1620 -----------------
1621
1622 procedure Finalize_Internal_Representation;
1623 pragma Inline (Finalize_Internal_Representation);
1624 -- Finalize all internal data structures
1625
1626 procedure Initialize_Internal_Representation;
1627 pragma Inline (Initialize_Internal_Representation);
1628 -- Initialize all internal data structures
1629
1630 end Internal_Representation;
1631 use Internal_Representation;
1632
1633 -- The following package provides functionality for recording pieces of the
1634 -- invocation graph in the ALI file of the main unit.
1635
1636 package Invocation_Graph is
1637
1638 ---------
1639 -- API --
1640 ---------
1641
1642 procedure Record_Invocation_Graph;
1643 pragma Inline (Record_Invocation_Graph);
1644 -- Process all declaration, instantiation, and library level scenarios,
1645 -- along with invocation construct within the spec and body of the main
1646 -- unit to determine whether any of these reach into an external unit.
1647 -- If such a path exists, encode in the ALI file of the main unit.
1648
1649 -----------------
1650 -- Maintenance --
1651 -----------------
1652
1653 procedure Finalize_Invocation_Graph;
1654 pragma Inline (Finalize_Invocation_Graph);
1655 -- Finalize all internal data structures
1656
1657 procedure Initialize_Invocation_Graph;
1658 pragma Inline (Initialize_Invocation_Graph);
1659 -- Initialize all internal data structures
1660
1661 end Invocation_Graph;
1662 use Invocation_Graph;
1663
1664 -- The following package stores scenarios
1665
1666 package Scenario_Storage is
1667
1668 ---------
1669 -- API --
1670 ---------
1671
1672 procedure Add_Declaration_Scenario (N : Node_Id);
1673 pragma Inline (Add_Declaration_Scenario);
1674 -- Save declaration level scenario N
1675
1676 procedure Add_Dynamic_ABE_Check_Scenario (N : Node_Id);
1677 pragma Inline (Add_Dynamic_ABE_Check_Scenario);
1678 -- Save scenario N for conditional ABE check installation purposes when
1679 -- the dynamic model is in effect.
1680
1681 procedure Add_Library_Body_Scenario (N : Node_Id);
1682 pragma Inline (Add_Library_Body_Scenario);
1683 -- Save library-level body scenario N
1684
1685 procedure Add_Library_Spec_Scenario (N : Node_Id);
1686 pragma Inline (Add_Library_Spec_Scenario);
1687 -- Save library-level spec scenario N
1688
1689 procedure Add_SPARK_Scenario (N : Node_Id);
1690 pragma Inline (Add_SPARK_Scenario);
1691 -- Save SPARK scenario N
1692
1693 procedure Delete_Scenario (N : Node_Id);
1694 pragma Inline (Delete_Scenario);
1695 -- Delete arbitrary scenario N
1696
1697 function Iterate_Declaration_Scenarios return NE_Set.Iterator;
1698 pragma Inline (Iterate_Declaration_Scenarios);
1699 -- Obtain an iterator over all declaration level scenarios
1700
1701 function Iterate_Dynamic_ABE_Check_Scenarios return NE_Set.Iterator;
1702 pragma Inline (Iterate_Dynamic_ABE_Check_Scenarios);
1703 -- Obtain an iterator over all scenarios that require a conditional ABE
1704 -- check when the dynamic model is in effect.
1705
1706 function Iterate_Library_Body_Scenarios return NE_Set.Iterator;
1707 pragma Inline (Iterate_Library_Body_Scenarios);
1708 -- Obtain an iterator over all library level body scenarios
1709
1710 function Iterate_Library_Spec_Scenarios return NE_Set.Iterator;
1711 pragma Inline (Iterate_Library_Spec_Scenarios);
1712 -- Obtain an iterator over all library level spec scenarios
1713
1714 function Iterate_SPARK_Scenarios return NE_Set.Iterator;
1715 pragma Inline (Iterate_SPARK_Scenarios);
1716 -- Obtain an iterator over all SPARK scenarios
1717
1718 procedure Replace_Scenario (Old_N : Node_Id; New_N : Node_Id);
1719 pragma Inline (Replace_Scenario);
1720 -- Replace scenario Old_N with scenario New_N
1721
1722 -----------------
1723 -- Maintenance --
1724 -----------------
1725
1726 procedure Finalize_Scenario_Storage;
1727 pragma Inline (Finalize_Scenario_Storage);
1728 -- Finalize all internal data structures
1729
1730 procedure Initialize_Scenario_Storage;
1731 pragma Inline (Initialize_Scenario_Storage);
1732 -- Initialize all internal data structures
1733
1734 end Scenario_Storage;
1735 use Scenario_Storage;
1736
1737 -- The following package provides various semantic predicates
1738
1739 package Semantics is
1740
1741 ---------
1742 -- API --
1743 ---------
1744
1745 function Is_Accept_Alternative_Proc (Id : Entity_Id) return Boolean;
1746 pragma Inline (Is_Accept_Alternative_Proc);
1747 -- Determine whether arbitrary entity Id denotes an internally generated
1748 -- procedure which encapsulates the statements of an accept alternative.
1749
1750 function Is_Activation_Proc (Id : Entity_Id) return Boolean;
1751 pragma Inline (Is_Activation_Proc);
1752 -- Determine whether arbitrary entity Id denotes a runtime procedure in
1753 -- charge with activating tasks.
1754
1755 function Is_Ada_Semantic_Target (Id : Entity_Id) return Boolean;
1756 pragma Inline (Is_Ada_Semantic_Target);
1757 -- Determine whether arbitrary entity Id denodes a source or internally
1758 -- generated subprogram which emulates Ada semantics.
1759
1760 function Is_Assertion_Pragma_Target (Id : Entity_Id) return Boolean;
1761 pragma Inline (Is_Assertion_Pragma_Target);
1762 -- Determine whether arbitrary entity Id denotes a procedure which
1763 -- varifies the run-time semantics of an assertion pragma.
1764
1765 function Is_Bodiless_Subprogram (Subp_Id : Entity_Id) return Boolean;
1766 pragma Inline (Is_Bodiless_Subprogram);
1767 -- Determine whether subprogram Subp_Id will never have a body
1768
1769 function Is_Bridge_Target (Id : Entity_Id) return Boolean;
1770 pragma Inline (Is_Bridge_Target);
1771 -- Determine whether arbitrary entity Id denotes a bridge target
1772
1773 function Is_Controlled_Proc
1774 (Subp_Id : Entity_Id;
1775 Subp_Nam : Name_Id) return Boolean;
1776 pragma Inline (Is_Controlled_Proc);
1777 -- Determine whether subprogram Subp_Id denotes controlled type
1778 -- primitives Adjust, Finalize, or Initialize as denoted by name
1779 -- Subp_Nam.
1780
1781 function Is_Default_Initial_Condition_Proc
1782 (Id : Entity_Id) return Boolean;
1783 pragma Inline (Is_Default_Initial_Condition_Proc);
1784 -- Determine whether arbitrary entity Id denotes internally generated
1785 -- routine Default_Initial_Condition.
1786
1787 function Is_Finalizer_Proc (Id : Entity_Id) return Boolean;
1788 pragma Inline (Is_Finalizer_Proc);
1789 -- Determine whether arbitrary entity Id denotes internally generated
1790 -- routine _Finalizer.
1791
1792 function Is_Initial_Condition_Proc (Id : Entity_Id) return Boolean;
1793 pragma Inline (Is_Initial_Condition_Proc);
1794 -- Determine whether arbitrary entity Id denotes internally generated
1795 -- routine Initial_Condition.
1796
1797 function Is_Initialized (Obj_Decl : Node_Id) return Boolean;
1798 pragma Inline (Is_Initialized);
1799 -- Determine whether object declaration Obj_Decl is initialized
1800
1801 function Is_Invariant_Proc (Id : Entity_Id) return Boolean;
1802 pragma Inline (Is_Invariant_Proc);
1803 -- Determine whether arbitrary entity Id denotes an invariant procedure
1804
1805 function Is_Non_Library_Level_Encapsulator (N : Node_Id) return Boolean;
1806 pragma Inline (Is_Non_Library_Level_Encapsulator);
1807 -- Determine whether arbitrary node N is a non-library encapsulator
1808
1809 function Is_Partial_Invariant_Proc (Id : Entity_Id) return Boolean;
1810 pragma Inline (Is_Partial_Invariant_Proc);
1811 -- Determine whether arbitrary entity Id denotes a partial invariant
1812 -- procedure.
1813
1814 function Is_Postconditions_Proc (Id : Entity_Id) return Boolean;
1815 pragma Inline (Is_Postconditions_Proc);
1816 -- Determine whether arbitrary entity Id denotes internally generated
1817 -- routine _Postconditions.
1818
1819 function Is_Preelaborated_Unit (Id : Entity_Id) return Boolean;
1820 pragma Inline (Is_Preelaborated_Unit);
1821 -- Determine whether arbitrary entity Id denotes a unit which is subject
1822 -- to one of the following pragmas:
1823 --
1824 -- * Preelaborable
1825 -- * Pure
1826 -- * Remote_Call_Interface
1827 -- * Remote_Types
1828 -- * Shared_Passive
1829
1830 function Is_Protected_Entry (Id : Entity_Id) return Boolean;
1831 pragma Inline (Is_Protected_Entry);
1832 -- Determine whether arbitrary entity Id denotes a protected entry
1833
1834 function Is_Protected_Subp (Id : Entity_Id) return Boolean;
1835 pragma Inline (Is_Protected_Subp);
1836 -- Determine whether entity Id denotes a protected subprogram
1837
1838 function Is_Protected_Body_Subp (Id : Entity_Id) return Boolean;
1839 pragma Inline (Is_Protected_Body_Subp);
1840 -- Determine whether entity Id denotes the protected or unprotected
1841 -- version of a protected subprogram.
1842
1843 function Is_Scenario (N : Node_Id) return Boolean;
1844 pragma Inline (Is_Scenario);
1845 -- Determine whether attribute node N denotes a scenario. The scenario
1846 -- may not necessarily be eligible for ABE processing.
1847
1848 function Is_SPARK_Semantic_Target (Id : Entity_Id) return Boolean;
1849 pragma Inline (Is_SPARK_Semantic_Target);
1850 -- Determine whether arbitrary entity Id nodes a source or internally
1851 -- generated subprogram which emulates SPARK semantics.
1852
1853 function Is_Subprogram_Inst (Id : Entity_Id) return Boolean;
1854 pragma Inline (Is_Subprogram_Inst);
1855 -- Determine whether arbitrary entity Id denotes a subprogram instance
1856
1857 function Is_Suitable_Access_Taken (N : Node_Id) return Boolean;
1858 pragma Inline (Is_Suitable_Access_Taken);
1859 -- Determine whether arbitrary node N denotes a suitable attribute for
1860 -- ABE processing.
1861
1862 function Is_Suitable_Call (N : Node_Id) return Boolean;
1863 pragma Inline (Is_Suitable_Call);
1864 -- Determine whether arbitrary node N denotes a suitable call for ABE
1865 -- processing.
1866
1867 function Is_Suitable_Instantiation (N : Node_Id) return Boolean;
1868 pragma Inline (Is_Suitable_Instantiation);
1869 -- Determine whether arbitrary node N is a suitable instantiation for
1870 -- ABE processing.
1871
1872 function Is_Suitable_SPARK_Derived_Type (N : Node_Id) return Boolean;
1873 pragma Inline (Is_Suitable_SPARK_Derived_Type);
1874 -- Determine whether arbitrary node N denotes a suitable derived type
1875 -- declaration for ABE processing using the SPARK rules.
1876
1877 function Is_Suitable_SPARK_Instantiation (N : Node_Id) return Boolean;
1878 pragma Inline (Is_Suitable_SPARK_Instantiation);
1879 -- Determine whether arbitrary node N denotes a suitable instantiation
1880 -- for ABE processing using the SPARK rules.
1881
1882 function Is_Suitable_SPARK_Refined_State_Pragma
1883 (N : Node_Id) return Boolean;
1884 pragma Inline (Is_Suitable_SPARK_Refined_State_Pragma);
1885 -- Determine whether arbitrary node N denotes a suitable Refined_State
1886 -- pragma for ABE processing using the SPARK rules.
1887
1888 function Is_Suitable_Variable_Assignment (N : Node_Id) return Boolean;
1889 pragma Inline (Is_Suitable_Variable_Assignment);
1890 -- Determine whether arbitrary node N denotes a suitable assignment for
1891 -- ABE processing.
1892
1893 function Is_Suitable_Variable_Reference (N : Node_Id) return Boolean;
1894 pragma Inline (Is_Suitable_Variable_Reference);
1895 -- Determine whether arbitrary node N is a suitable variable reference
1896 -- for ABE processing.
1897
1898 function Is_Task_Entry (Id : Entity_Id) return Boolean;
1899 pragma Inline (Is_Task_Entry);
1900 -- Determine whether arbitrary entity Id denotes a task entry
1901
1902 function Is_Up_Level_Target
1903 (Targ_Decl : Node_Id;
1904 In_State : Processing_In_State) return Boolean;
1905 pragma Inline (Is_Up_Level_Target);
1906 -- Determine whether the current root resides at the declaration level.
1907 -- If this is the case, determine whether a target with by declaration
1908 -- Target_Decl is within a context which encloses the current root or is
1909 -- in a different unit. In_State is the current state of the Processing
1910 -- phase.
1911
1912 end Semantics;
1913 use Semantics;
1914
1915 -- The following package provides the main entry point for SPARK-related
1916 -- checks and diagnostics.
1917
1918 package SPARK_Processor is
1919
1920 ---------
1921 -- API --
1922 ---------
1923
1924 procedure Check_SPARK_Model_In_Effect;
1925 pragma Inline (Check_SPARK_Model_In_Effect);
1926 -- Determine whether a suitable elaboration model is currently in effect
1927 -- for verifying SPARK rules. Emit a warning if this is not the case.
1928
1929 procedure Check_SPARK_Scenarios;
1930 pragma Inline (Check_SPARK_Scenarios);
1931 -- Examine SPARK scenarios which are not necessarily executable during
1932 -- elaboration, but still requires elaboration-related checks.
1933
1934 end SPARK_Processor;
1935 use SPARK_Processor;
1936
1937 -----------------------
1938 -- Local subprograms --
1939 -----------------------
1940
1941 function Assignment_Target (Asmt : Node_Id) return Node_Id;
1942 pragma Inline (Assignment_Target);
1943 -- Obtain the target of assignment statement Asmt
1944
1945 function Call_Name (Call : Node_Id) return Node_Id;
1946 pragma Inline (Call_Name);
1947 -- Obtain the name of an entry, operator, or subprogram call Call
1948
1949 function Canonical_Subprogram (Subp_Id : Entity_Id) return Entity_Id;
1950 pragma Inline (Canonical_Subprogram);
1951 -- Obtain the uniform canonical entity of subprogram Subp_Id
1952
1953 function Compilation_Unit (Unit_Id : Entity_Id) return Node_Id;
1954 pragma Inline (Compilation_Unit);
1955 -- Return the N_Compilation_Unit node of unit Unit_Id
1956
1957 function Find_Enclosing_Instance (N : Node_Id) return Node_Id;
1958 pragma Inline (Find_Enclosing_Instance);
1959 -- Find the declaration or body of the nearest expanded instance which
1960 -- encloses arbitrary node N. Return Empty if no such instance exists.
1961
1962 function Find_Top_Unit (N : Node_Or_Entity_Id) return Entity_Id;
1963 pragma Inline (Find_Top_Unit);
1964 -- Return the top unit which contains arbitrary node or entity N. The unit
1965 -- is obtained by logically unwinding instantiations and subunits when N
1966 -- resides within one.
1967
1968 function Find_Unit_Entity (N : Node_Id) return Entity_Id;
1969 pragma Inline (Find_Unit_Entity);
1970 -- Return the entity of unit N
1971
1972 function First_Formal_Type (Subp_Id : Entity_Id) return Entity_Id;
1973 pragma Inline (First_Formal_Type);
1974 -- Return the type of subprogram Subp_Id's first formal parameter. If the
1975 -- subprogram lacks formal parameters, return Empty.
1976
1977 function Elaboration_Phase_Active return Boolean;
1978 pragma Inline (Elaboration_Phase_Active);
1979 -- Determine whether the elaboration phase of the compilation has started
1980
1981 procedure Finalize_All_Data_Structures;
1982 pragma Inline (Finalize_All_Data_Structures);
1983 -- Destroy all internal data structures
1984
1985 function Has_Body (Pack_Decl : Node_Id) return Boolean;
1986 pragma Inline (Has_Body);
1987 -- Determine whether package declaration Pack_Decl has a corresponding body
1988 -- or would eventually have one.
1989
1990 function In_External_Instance
1991 (N : Node_Id;
1992 Target_Decl : Node_Id) return Boolean;
1993 pragma Inline (In_External_Instance);
1994 -- Determine whether a target desctibed by its declaration Target_Decl
1995 -- resides in a package instance which is external to scenario N.
1996
1997 function In_Main_Context (N : Node_Id) return Boolean;
1998 pragma Inline (In_Main_Context);
1999 -- Determine whether arbitrary node N appears within the main compilation
2000 -- unit.
2001
2002 function In_Same_Context
2003 (N1 : Node_Id;
2004 N2 : Node_Id;
2005 Nested_OK : Boolean := False) return Boolean;
2006 pragma Inline (In_Same_Context);
2007 -- Determine whether two arbitrary nodes N1 and N2 appear within the same
2008 -- context ignoring enclosing library levels. Nested_OK should be set when
2009 -- the context of N1 can enclose that of N2.
2010
2011 procedure Initialize_All_Data_Structures;
2012 pragma Inline (Initialize_All_Data_Structures);
2013 -- Create all internal data structures
2014
2015 function Instantiated_Generic (Inst : Node_Id) return Entity_Id;
2016 pragma Inline (Instantiated_Generic);
2017 -- Obtain the generic instantiated by instance Inst
2018
2019 function Is_Safe_Activation
2020 (Call : Node_Id;
2021 Task_Rep : Target_Rep_Id) return Boolean;
2022 pragma Inline (Is_Safe_Activation);
2023 -- Determine whether activation call Call which activates an object of a
2024 -- task type described by representation Task_Rep is always ABE-safe.
2025
2026 function Is_Safe_Call
2027 (Call : Node_Id;
2028 Subp_Id : Entity_Id;
2029 Subp_Rep : Target_Rep_Id) return Boolean;
2030 pragma Inline (Is_Safe_Call);
2031 -- Determine whether call Call which invokes entry, operator, or subprogram
2032 -- Subp_Id is always ABE-safe. Subp_Rep is the representation of the entry,
2033 -- operator, or subprogram.
2034
2035 function Is_Safe_Instantiation
2036 (Inst : Node_Id;
2037 Gen_Id : Entity_Id;
2038 Gen_Rep : Target_Rep_Id) return Boolean;
2039 pragma Inline (Is_Safe_Instantiation);
2040 -- Determine whether instantiation Inst which instantiates generic Gen_Id
2041 -- is always ABE-safe. Gen_Rep is the representation of the generic.
2042
2043 function Is_Same_Unit
2044 (Unit_1 : Entity_Id;
2045 Unit_2 : Entity_Id) return Boolean;
2046 pragma Inline (Is_Same_Unit);
2047 -- Determine whether entities Unit_1 and Unit_2 denote the same unit
2048
2049 function Non_Private_View (Typ : Entity_Id) return Entity_Id;
2050 pragma Inline (Non_Private_View);
2051 -- Return the full view of private type Typ if available, otherwise return
2052 -- type Typ.
2053
2054 function Scenario (N : Node_Id) return Node_Id;
2055 pragma Inline (Scenario);
2056 -- Return the appropriate scenario node for scenario N
2057
2058 procedure Set_Elaboration_Phase (Status : Elaboration_Phase_Status);
2059 pragma Inline (Set_Elaboration_Phase);
2060 -- Change the status of the elaboration phase of the compiler to Status
2061
2062 procedure Spec_And_Body_From_Entity
2063 (Id : Node_Id;
2064 Spec_Decl : out Node_Id;
2065 Body_Decl : out Node_Id);
2066 pragma Inline (Spec_And_Body_From_Entity);
2067 -- Given arbitrary entity Id representing a construct with a spec and body,
2068 -- retrieve declaration of the spec in Spec_Decl and the declaration of the
2069 -- body in Body_Decl.
2070
2071 procedure Spec_And_Body_From_Node
2072 (N : Node_Id;
2073 Spec_Decl : out Node_Id;
2074 Body_Decl : out Node_Id);
2075 pragma Inline (Spec_And_Body_From_Node);
2076 -- Given arbitrary node N representing a construct with a spec and body,
2077 -- retrieve declaration of the spec in Spec_Decl and the declaration of
2078 -- the body in Body_Decl.
2079
2080 function Static_Elaboration_Checks return Boolean;
2081 pragma Inline (Static_Elaboration_Checks);
2082 -- Determine whether the static model is in effect
2083
2084 function Unit_Entity (Unit_Id : Entity_Id) return Entity_Id;
2085 pragma Inline (Unit_Entity);
2086 -- Return the entity of the initial declaration for unit Unit_Id
2087
2088 procedure Update_Elaboration_Scenario (New_N : Node_Id; Old_N : Node_Id);
2089 pragma Inline (Update_Elaboration_Scenario);
2090 -- Update all relevant internal data structures when scenario Old_N is
2091 -- transformed into scenario New_N by Atree.Rewrite.
2092
2093 ----------------------
2094 -- Active_Scenarios --
2095 ----------------------
2096
2097 package body Active_Scenarios is
2098
2099 -----------------------
2100 -- Local subprograms --
2101 -----------------------
2102
2103 procedure Output_Access_Taken
2104 (Attr : Node_Id;
2105 Attr_Rep : Scenario_Rep_Id;
2106 Error_Nod : Node_Id);
2107 pragma Inline (Output_Access_Taken);
2108 -- Emit a specific diagnostic message for 'Access attribute reference
2109 -- Attr with representation Attr_Rep. The message is associated with
2110 -- node Error_Nod.
2111
2112 procedure Output_Active_Scenario
2113 (N : Node_Id;
2114 Error_Nod : Node_Id;
2115 In_State : Processing_In_State);
2116 pragma Inline (Output_Active_Scenario);
2117 -- Top level dispatcher for outputting a scenario. Emit a specific
2118 -- diagnostic message for scenario N. The message is associated with
2119 -- node Error_Nod. In_State is the current state of the Processing
2120 -- phase.
2121
2122 procedure Output_Call
2123 (Call : Node_Id;
2124 Call_Rep : Scenario_Rep_Id;
2125 Error_Nod : Node_Id);
2126 pragma Inline (Output_Call);
2127 -- Emit a diagnostic message for call Call with representation Call_Rep.
2128 -- The message is associated with node Error_Nod.
2129
2130 procedure Output_Header (Error_Nod : Node_Id);
2131 pragma Inline (Output_Header);
2132 -- Emit a specific diagnostic message for the unit of the root scenario.
2133 -- The message is associated with node Error_Nod.
2134
2135 procedure Output_Instantiation
2136 (Inst : Node_Id;
2137 Inst_Rep : Scenario_Rep_Id;
2138 Error_Nod : Node_Id);
2139 pragma Inline (Output_Instantiation);
2140 -- Emit a specific diagnostic message for instantiation Inst with
2141 -- representation Inst_Rep. The message is associated with node
2142 -- Error_Nod.
2143
2144 procedure Output_Refined_State_Pragma
2145 (Prag : Node_Id;
2146 Prag_Rep : Scenario_Rep_Id;
2147 Error_Nod : Node_Id);
2148 pragma Inline (Output_Refined_State_Pragma);
2149 -- Emit a specific diagnostic message for Refined_State pragma Prag
2150 -- with representation Prag_Rep. The message is associated with node
2151 -- Error_Nod.
2152
2153 procedure Output_Task_Activation
2154 (Call : Node_Id;
2155 Call_Rep : Scenario_Rep_Id;
2156 Error_Nod : Node_Id);
2157 pragma Inline (Output_Task_Activation);
2158 -- Emit a specific diagnostic message for activation call Call
2159 -- with representation Call_Rep. The message is associated with
2160 -- node Error_Nod.
2161
2162 procedure Output_Variable_Assignment
2163 (Asmt : Node_Id;
2164 Asmt_Rep : Scenario_Rep_Id;
2165 Error_Nod : Node_Id);
2166 pragma Inline (Output_Variable_Assignment);
2167 -- Emit a specific diagnostic message for assignment statement Asmt
2168 -- with representation Asmt_Rep. The message is associated with node
2169 -- Error_Nod.
2170
2171 procedure Output_Variable_Reference
2172 (Ref : Node_Id;
2173 Ref_Rep : Scenario_Rep_Id;
2174 Error_Nod : Node_Id);
2175 pragma Inline (Output_Variable_Reference);
2176 -- Emit a specific diagnostic message for read reference Ref with
2177 -- representation Ref_Rep. The message is associated with node
2178 -- Error_Nod.
2179
2180 -------------------
2181 -- Output_Access --
2182 -------------------
2183
2184 procedure Output_Access_Taken
2185 (Attr : Node_Id;
2186 Attr_Rep : Scenario_Rep_Id;
2187 Error_Nod : Node_Id)
2188 is
2189 Subp_Id : constant Entity_Id := Target (Attr_Rep);
2190
2191 begin
2192 Error_Msg_Name_1 := Attribute_Name (Attr);
2193 Error_Msg_Sloc := Sloc (Attr);
2194 Error_Msg_NE ("\\ % of & taken #", Error_Nod, Subp_Id);
2195 end Output_Access_Taken;
2196
2197 ----------------------------
2198 -- Output_Active_Scenario --
2199 ----------------------------
2200
2201 procedure Output_Active_Scenario
2202 (N : Node_Id;
2203 Error_Nod : Node_Id;
2204 In_State : Processing_In_State)
2205 is
2206 Scen : constant Node_Id := Scenario (N);
2207 Scen_Rep : Scenario_Rep_Id;
2208
2209 begin
2210 -- 'Access
2211
2212 if Is_Suitable_Access_Taken (Scen) then
2213 Output_Access_Taken
2214 (Attr => Scen,
2215 Attr_Rep => Scenario_Representation_Of (Scen, In_State),
2216 Error_Nod => Error_Nod);
2217
2218 -- Call or task activation
2219
2220 elsif Is_Suitable_Call (Scen) then
2221 Scen_Rep := Scenario_Representation_Of (Scen, In_State);
2222
2223 if Kind (Scen_Rep) = Call_Scenario then
2224 Output_Call
2225 (Call => Scen,
2226 Call_Rep => Scen_Rep,
2227 Error_Nod => Error_Nod);
2228
2229 else
2230 pragma Assert (Kind (Scen_Rep) = Task_Activation_Scenario);
2231
2232 Output_Task_Activation
2233 (Call => Scen,
2234 Call_Rep => Scen_Rep,
2235 Error_Nod => Error_Nod);
2236 end if;
2237
2238 -- Instantiation
2239
2240 elsif Is_Suitable_Instantiation (Scen) then
2241 Output_Instantiation
2242 (Inst => Scen,
2243 Inst_Rep => Scenario_Representation_Of (Scen, In_State),
2244 Error_Nod => Error_Nod);
2245
2246 -- Pragma Refined_State
2247
2248 elsif Is_Suitable_SPARK_Refined_State_Pragma (Scen) then
2249 Output_Refined_State_Pragma
2250 (Prag => Scen,
2251 Prag_Rep => Scenario_Representation_Of (Scen, In_State),
2252 Error_Nod => Error_Nod);
2253
2254 -- Variable assignment
2255
2256 elsif Is_Suitable_Variable_Assignment (Scen) then
2257 Output_Variable_Assignment
2258 (Asmt => Scen,
2259 Asmt_Rep => Scenario_Representation_Of (Scen, In_State),
2260 Error_Nod => Error_Nod);
2261
2262 -- Variable reference
2263
2264 elsif Is_Suitable_Variable_Reference (Scen) then
2265 Output_Variable_Reference
2266 (Ref => Scen,
2267 Ref_Rep => Scenario_Representation_Of (Scen, In_State),
2268 Error_Nod => Error_Nod);
2269 end if;
2270 end Output_Active_Scenario;
2271
2272 -----------------------------
2273 -- Output_Active_Scenarios --
2274 -----------------------------
2275
2276 procedure Output_Active_Scenarios
2277 (Error_Nod : Node_Id;
2278 In_State : Processing_In_State)
2279 is
2280 package Scenarios renames Active_Scenario_Stack;
2281
2282 Header_Posted : Boolean := False;
2283
2284 begin
2285 -- Output the contents of the active scenario stack starting from the
2286 -- bottom, or the least recent scenario.
2287
2288 for Index in Scenarios.First .. Scenarios.Last loop
2289 if not Header_Posted then
2290 Output_Header (Error_Nod);
2291 Header_Posted := True;
2292 end if;
2293
2294 Output_Active_Scenario
2295 (N => Scenarios.Table (Index),
2296 Error_Nod => Error_Nod,
2297 In_State => In_State);
2298 end loop;
2299 end Output_Active_Scenarios;
2300
2301 -----------------
2302 -- Output_Call --
2303 -----------------
2304
2305 procedure Output_Call
2306 (Call : Node_Id;
2307 Call_Rep : Scenario_Rep_Id;
2308 Error_Nod : Node_Id)
2309 is
2310 procedure Output_Accept_Alternative (Alt_Id : Entity_Id);
2311 pragma Inline (Output_Accept_Alternative);
2312 -- Emit a specific diagnostic message concerning accept alternative
2313 -- with entity Alt_Id.
2314
2315 procedure Output_Call (Subp_Id : Entity_Id; Kind : String);
2316 pragma Inline (Output_Call);
2317 -- Emit a specific diagnostic message concerning a call of kind Kind
2318 -- which invokes subprogram Subp_Id.
2319
2320 procedure Output_Type_Actions (Subp_Id : Entity_Id; Action : String);
2321 pragma Inline (Output_Type_Actions);
2322 -- Emit a specific diagnostic message concerning action Action of a
2323 -- type performed by subprogram Subp_Id.
2324
2325 procedure Output_Verification_Call
2326 (Pred : String;
2327 Id : Entity_Id;
2328 Id_Kind : String);
2329 pragma Inline (Output_Verification_Call);
2330 -- Emit a specific diagnostic message concerning the verification of
2331 -- predicate Pred applied to related entity Id with kind Id_Kind.
2332
2333 -------------------------------
2334 -- Output_Accept_Alternative --
2335 -------------------------------
2336
2337 procedure Output_Accept_Alternative (Alt_Id : Entity_Id) is
2338 Entry_Id : constant Entity_Id := Receiving_Entry (Alt_Id);
2339
2340 begin
2341 pragma Assert (Present (Entry_Id));
2342
2343 Error_Msg_NE ("\\ entry & selected #", Error_Nod, Entry_Id);
2344 end Output_Accept_Alternative;
2345
2346 -----------------
2347 -- Output_Call --
2348 -----------------
2349
2350 procedure Output_Call (Subp_Id : Entity_Id; Kind : String) is
2351 begin
2352 Error_Msg_NE ("\\ " & Kind & " & called #", Error_Nod, Subp_Id);
2353 end Output_Call;
2354
2355 -------------------------
2356 -- Output_Type_Actions --
2357 -------------------------
2358
2359 procedure Output_Type_Actions
2360 (Subp_Id : Entity_Id;
2361 Action : String)
2362 is
2363 Typ : constant Entity_Id := First_Formal_Type (Subp_Id);
2364
2365 begin
2366 pragma Assert (Present (Typ));
2367
2368 Error_Msg_NE
2369 ("\\ " & Action & " actions for type & #", Error_Nod, Typ);
2370 end Output_Type_Actions;
2371
2372 ------------------------------
2373 -- Output_Verification_Call --
2374 ------------------------------
2375
2376 procedure Output_Verification_Call
2377 (Pred : String;
2378 Id : Entity_Id;
2379 Id_Kind : String)
2380 is
2381 begin
2382 pragma Assert (Present (Id));
2383
2384 Error_Msg_NE
2385 ("\\ " & Pred & " of " & Id_Kind & " & verified #",
2386 Error_Nod, Id);
2387 end Output_Verification_Call;
2388
2389 -- Local variables
2390
2391 Subp_Id : constant Entity_Id := Target (Call_Rep);
2392
2393 -- Start of processing for Output_Call
2394
2395 begin
2396 Error_Msg_Sloc := Sloc (Call);
2397
2398 -- Accept alternative
2399
2400 if Is_Accept_Alternative_Proc (Subp_Id) then
2401 Output_Accept_Alternative (Subp_Id);
2402
2403 -- Adjustment
2404
2405 elsif Is_TSS (Subp_Id, TSS_Deep_Adjust) then
2406 Output_Type_Actions (Subp_Id, "adjustment");
2407
2408 -- Default_Initial_Condition
2409
2410 elsif Is_Default_Initial_Condition_Proc (Subp_Id) then
2411 Output_Verification_Call
2412 (Pred => "Default_Initial_Condition",
2413 Id => First_Formal_Type (Subp_Id),
2414 Id_Kind => "type");
2415
2416 -- Entries
2417
2418 elsif Is_Protected_Entry (Subp_Id) then
2419 Output_Call (Subp_Id, "entry");
2420
2421 -- Task entry calls are never processed because the entry being
2422 -- invoked does not have a corresponding "body", it has a select. A
2423 -- task entry call appears in the stack of active scenarios for the
2424 -- sole purpose of checking No_Entry_Calls_In_Elaboration_Code and
2425 -- nothing more.
2426
2427 elsif Is_Task_Entry (Subp_Id) then
2428 null;
2429
2430 -- Finalization
2431
2432 elsif Is_TSS (Subp_Id, TSS_Deep_Finalize) then
2433 Output_Type_Actions (Subp_Id, "finalization");
2434
2435 -- Calls to _Finalizer procedures must not appear in the output
2436 -- because this creates confusing noise.
2437
2438 elsif Is_Finalizer_Proc (Subp_Id) then
2439 null;
2440
2441 -- Initial_Condition
2442
2443 elsif Is_Initial_Condition_Proc (Subp_Id) then
2444 Output_Verification_Call
2445 (Pred => "Initial_Condition",
2446 Id => Find_Enclosing_Scope (Call),
2447 Id_Kind => "package");
2448
2449 -- Initialization
2450
2451 elsif Is_Init_Proc (Subp_Id)
2452 or else Is_TSS (Subp_Id, TSS_Deep_Initialize)
2453 then
2454 Output_Type_Actions (Subp_Id, "initialization");
2455
2456 -- Invariant
2457
2458 elsif Is_Invariant_Proc (Subp_Id) then
2459 Output_Verification_Call
2460 (Pred => "invariants",
2461 Id => First_Formal_Type (Subp_Id),
2462 Id_Kind => "type");
2463
2464 -- Partial invariant calls must not appear in the output because this
2465 -- creates confusing noise. Note that a partial invariant is always
2466 -- invoked by the "full" invariant which is already placed on the
2467 -- stack.
2468
2469 elsif Is_Partial_Invariant_Proc (Subp_Id) then
2470 null;
2471
2472 -- _Postconditions
2473
2474 elsif Is_Postconditions_Proc (Subp_Id) then
2475 Output_Verification_Call
2476 (Pred => "postconditions",
2477 Id => Find_Enclosing_Scope (Call),
2478 Id_Kind => "subprogram");
2479
2480 -- Subprograms must come last because some of the previous cases fall
2481 -- under this category.
2482
2483 elsif Ekind (Subp_Id) = E_Function then
2484 Output_Call (Subp_Id, "function");
2485
2486 elsif Ekind (Subp_Id) = E_Procedure then
2487 Output_Call (Subp_Id, "procedure");
2488
2489 else
2490 pragma Assert (False);
2491 return;
2492 end if;
2493 end Output_Call;
2494
2495 -------------------
2496 -- Output_Header --
2497 -------------------
2498
2499 procedure Output_Header (Error_Nod : Node_Id) is
2500 Unit_Id : constant Entity_Id := Find_Top_Unit (Root_Scenario);
2501
2502 begin
2503 if Ekind (Unit_Id) = E_Package then
2504 Error_Msg_NE ("\\ spec of unit & elaborated", Error_Nod, Unit_Id);
2505
2506 elsif Ekind (Unit_Id) = E_Package_Body then
2507 Error_Msg_NE ("\\ body of unit & elaborated", Error_Nod, Unit_Id);
2508
2509 else
2510 Error_Msg_NE ("\\ in body of unit &", Error_Nod, Unit_Id);
2511 end if;
2512 end Output_Header;
2513
2514 --------------------------
2515 -- Output_Instantiation --
2516 --------------------------
2517
2518 procedure Output_Instantiation
2519 (Inst : Node_Id;
2520 Inst_Rep : Scenario_Rep_Id;
2521 Error_Nod : Node_Id)
2522 is
2523 procedure Output_Instantiation (Gen_Id : Entity_Id; Kind : String);
2524 pragma Inline (Output_Instantiation);
2525 -- Emit a specific diagnostic message concerning an instantiation of
2526 -- generic unit Gen_Id. Kind denotes the kind of the instantiation.
2527
2528 --------------------------
2529 -- Output_Instantiation --
2530 --------------------------
2531
2532 procedure Output_Instantiation (Gen_Id : Entity_Id; Kind : String) is
2533 begin
2534 Error_Msg_NE
2535 ("\\ " & Kind & " & instantiated as & #", Error_Nod, Gen_Id);
2536 end Output_Instantiation;
2537
2538 -- Local variables
2539
2540 Gen_Id : constant Entity_Id := Target (Inst_Rep);
2541
2542 -- Start of processing for Output_Instantiation
2543
2544 begin
2545 Error_Msg_Node_2 := Defining_Entity (Inst);
2546 Error_Msg_Sloc := Sloc (Inst);
2547
2548 if Nkind (Inst) = N_Function_Instantiation then
2549 Output_Instantiation (Gen_Id, "function");
2550
2551 elsif Nkind (Inst) = N_Package_Instantiation then
2552 Output_Instantiation (Gen_Id, "package");
2553
2554 elsif Nkind (Inst) = N_Procedure_Instantiation then
2555 Output_Instantiation (Gen_Id, "procedure");
2556
2557 else
2558 pragma Assert (False);
2559 return;
2560 end if;
2561 end Output_Instantiation;
2562
2563 ---------------------------------
2564 -- Output_Refined_State_Pragma --
2565 ---------------------------------
2566
2567 procedure Output_Refined_State_Pragma
2568 (Prag : Node_Id;
2569 Prag_Rep : Scenario_Rep_Id;
2570 Error_Nod : Node_Id)
2571 is
2572 pragma Unreferenced (Prag_Rep);
2573
2574 begin
2575 Error_Msg_Sloc := Sloc (Prag);
2576 Error_Msg_N ("\\ refinement constituents read #", Error_Nod);
2577 end Output_Refined_State_Pragma;
2578
2579 ----------------------------
2580 -- Output_Task_Activation --
2581 ----------------------------
2582
2583 procedure Output_Task_Activation
2584 (Call : Node_Id;
2585 Call_Rep : Scenario_Rep_Id;
2586 Error_Nod : Node_Id)
2587 is
2588 pragma Unreferenced (Call_Rep);
2589
2590 function Find_Activator return Entity_Id;
2591 -- Find the nearest enclosing construct which houses call Call
2592
2593 --------------------
2594 -- Find_Activator --
2595 --------------------
2596
2597 function Find_Activator return Entity_Id is
2598 Par : Node_Id;
2599
2600 begin
2601 -- Climb the parent chain looking for a package [body] or a
2602 -- construct with a statement sequence.
2603
2604 Par := Parent (Call);
2605 while Present (Par) loop
2606 if Nkind_In (Par, N_Package_Body, N_Package_Declaration) then
2607 return Defining_Entity (Par);
2608
2609 elsif Nkind (Par) = N_Handled_Sequence_Of_Statements then
2610 return Defining_Entity (Parent (Par));
2611 end if;
2612
2613 Par := Parent (Par);
2614 end loop;
2615
2616 return Empty;
2617 end Find_Activator;
2618
2619 -- Local variables
2620
2621 Activator : constant Entity_Id := Find_Activator;
2622
2623 -- Start of processing for Output_Task_Activation
2624
2625 begin
2626 pragma Assert (Present (Activator));
2627
2628 Error_Msg_NE ("\\ local tasks of & activated", Error_Nod, Activator);
2629 end Output_Task_Activation;
2630
2631 --------------------------------
2632 -- Output_Variable_Assignment --
2633 --------------------------------
2634
2635 procedure Output_Variable_Assignment
2636 (Asmt : Node_Id;
2637 Asmt_Rep : Scenario_Rep_Id;
2638 Error_Nod : Node_Id)
2639 is
2640 Var_Id : constant Entity_Id := Target (Asmt_Rep);
2641
2642 begin
2643 Error_Msg_Sloc := Sloc (Asmt);
2644 Error_Msg_NE ("\\ variable & assigned #", Error_Nod, Var_Id);
2645 end Output_Variable_Assignment;
2646
2647 -------------------------------
2648 -- Output_Variable_Reference --
2649 -------------------------------
2650
2651 procedure Output_Variable_Reference
2652 (Ref : Node_Id;
2653 Ref_Rep : Scenario_Rep_Id;
2654 Error_Nod : Node_Id)
2655 is
2656 Var_Id : constant Entity_Id := Target (Ref_Rep);
2657
2658 begin
2659 Error_Msg_Sloc := Sloc (Ref);
2660 Error_Msg_NE ("\\ variable & read #", Error_Nod, Var_Id);
2661 end Output_Variable_Reference;
2662
2663 -------------------------
2664 -- Pop_Active_Scenario --
2665 -------------------------
2666
2667 procedure Pop_Active_Scenario (N : Node_Id) is
2668 package Scenarios renames Active_Scenario_Stack;
2669 Top : Node_Id renames Scenarios.Table (Scenarios.Last);
2670
2671 begin
2672 pragma Assert (Top = N);
2673 Scenarios.Decrement_Last;
2674 end Pop_Active_Scenario;
2675
2676 --------------------------
2677 -- Push_Active_Scenario --
2678 --------------------------
2679
2680 procedure Push_Active_Scenario (N : Node_Id) is
2681 begin
2682 Active_Scenario_Stack.Append (N);
2683 end Push_Active_Scenario;
2684
2685 -------------------
2686 -- Root_Scenario --
2687 -------------------
2688
2689 function Root_Scenario return Node_Id is
2690 package Scenarios renames Active_Scenario_Stack;
2691
2692 begin
2693 -- Ensure that the scenario stack has at least one active scenario in
2694 -- it. The one at the bottom (index First) is the root scenario.
2695
2696 pragma Assert (Scenarios.Last >= Scenarios.First);
2697 return Scenarios.Table (Scenarios.First);
2698 end Root_Scenario;
2699 end Active_Scenarios;
2700
2701 --------------------------
2702 -- Activation_Processor --
2703 --------------------------
2704
2705 package body Activation_Processor is
2706
2707 ------------------------
2708 -- Process_Activation --
2709 ------------------------
2710
2711 procedure Process_Activation
2712 (Call : Node_Id;
2713 Call_Rep : Scenario_Rep_Id;
2714 Processor : Activation_Processor_Ptr;
2715 In_State : Processing_In_State)
2716 is
2717 procedure Process_Task_Object (Obj_Id : Entity_Id; Typ : Entity_Id);
2718 pragma Inline (Process_Task_Object);
2719 -- Invoke Processor for task object Obj_Id of type Typ
2720
2721 procedure Process_Task_Objects
2722 (Task_Objs : NE_List.Doubly_Linked_List);
2723 pragma Inline (Process_Task_Objects);
2724 -- Invoke Processor for all task objects found in list Task_Objs
2725
2726 procedure Traverse_List
2727 (List : List_Id;
2728 Task_Objs : NE_List.Doubly_Linked_List);
2729 pragma Inline (Traverse_List);
2730 -- Traverse declarative or statement list List while searching for
2731 -- objects of a task type, or containing task components. If such an
2732 -- object is found, first save it in list Task_Objs and then invoke
2733 -- Processor on it.
2734
2735 -------------------------
2736 -- Process_Task_Object --
2737 -------------------------
2738
2739 procedure Process_Task_Object (Obj_Id : Entity_Id; Typ : Entity_Id) is
2740 Root_Typ : constant Entity_Id :=
2741 Non_Private_View (Root_Type (Typ));
2742 Comp_Id : Entity_Id;
2743 Obj_Rep : Target_Rep_Id;
2744 Root_Rep : Target_Rep_Id;
2745
2746 New_In_State : Processing_In_State := In_State;
2747 -- Each step of the Processing phase constitutes a new state
2748
2749 begin
2750 if Is_Task_Type (Typ) then
2751 Obj_Rep := Target_Representation_Of (Obj_Id, New_In_State);
2752 Root_Rep := Target_Representation_Of (Root_Typ, New_In_State);
2753
2754 -- Warnings are suppressed when a prior scenario is already in
2755 -- that mode, or when the object, activation call, or task type
2756 -- have warnings suppressed. Update the state of the Processing
2757 -- phase to reflect this.
2758
2759 New_In_State.Suppress_Warnings :=
2760 New_In_State.Suppress_Warnings
2761 or else not Elaboration_Warnings_OK (Call_Rep)
2762 or else not Elaboration_Warnings_OK (Obj_Rep)
2763 or else not Elaboration_Warnings_OK (Root_Rep);
2764
2765 -- Update the state of the Processing phase to indicate that
2766 -- any further traversal is now within a task body.
2767
2768 New_In_State.Within_Task_Body := True;
2769
2770 -- Associate the current task type with the activation call
2771
2772 Set_Activated_Task_Type (Call_Rep, Root_Typ);
2773
2774 -- Process the activation of the current task object by calling
2775 -- the supplied processor.
2776
2777 Processor.all
2778 (Call => Call,
2779 Call_Rep => Call_Rep,
2780 Obj_Id => Obj_Id,
2781 Obj_Rep => Obj_Rep,
2782 Task_Typ => Root_Typ,
2783 Task_Rep => Root_Rep,
2784 In_State => New_In_State);
2785
2786 -- Reset the association between the current task and the
2787 -- activtion call.
2788
2789 Set_Activated_Task_Type (Call_Rep, Empty);
2790
2791 -- Examine the component type when the object is an array
2792
2793 elsif Is_Array_Type (Typ) and then Has_Task (Root_Typ) then
2794 Process_Task_Object
2795 (Obj_Id => Obj_Id,
2796 Typ => Component_Type (Typ));
2797
2798 -- Examine individual component types when the object is a record
2799
2800 elsif Is_Record_Type (Typ) and then Has_Task (Root_Typ) then
2801 Comp_Id := First_Component (Typ);
2802 while Present (Comp_Id) loop
2803 Process_Task_Object
2804 (Obj_Id => Obj_Id,
2805 Typ => Etype (Comp_Id));
2806
2807 Next_Component (Comp_Id);
2808 end loop;
2809 end if;
2810 end Process_Task_Object;
2811
2812 --------------------------
2813 -- Process_Task_Objects --
2814 --------------------------
2815
2816 procedure Process_Task_Objects
2817 (Task_Objs : NE_List.Doubly_Linked_List)
2818 is
2819 Iter : NE_List.Iterator;
2820 Obj_Id : Entity_Id;
2821
2822 begin
2823 Iter := NE_List.Iterate (Task_Objs);
2824 while NE_List.Has_Next (Iter) loop
2825 NE_List.Next (Iter, Obj_Id);
2826
2827 Process_Task_Object
2828 (Obj_Id => Obj_Id,
2829 Typ => Etype (Obj_Id));
2830 end loop;
2831 end Process_Task_Objects;
2832
2833 -------------------
2834 -- Traverse_List --
2835 -------------------
2836
2837 procedure Traverse_List
2838 (List : List_Id;
2839 Task_Objs : NE_List.Doubly_Linked_List)
2840 is
2841 Item : Node_Id;
2842 Item_Id : Entity_Id;
2843 Item_Typ : Entity_Id;
2844
2845 begin
2846 -- Examine the contents of the list looking for an object
2847 -- declaration of a task type or one that contains a task
2848 -- within.
2849
2850 Item := First (List);
2851 while Present (Item) loop
2852 if Nkind (Item) = N_Object_Declaration then
2853 Item_Id := Defining_Entity (Item);
2854 Item_Typ := Etype (Item_Id);
2855
2856 if Has_Task (Item_Typ) then
2857
2858 -- The object is either of a task type, or contains a
2859 -- task component. Save it in the list of task objects
2860 -- associated with the activation call.
2861
2862 NE_List.Append (Task_Objs, Item_Id);
2863
2864 Process_Task_Object
2865 (Obj_Id => Item_Id,
2866 Typ => Item_Typ);
2867 end if;
2868 end if;
2869
2870 Next (Item);
2871 end loop;
2872 end Traverse_List;
2873
2874 -- Local variables
2875
2876 Context : Node_Id;
2877 Spec : Node_Id;
2878 Task_Objs : NE_List.Doubly_Linked_List;
2879
2880 -- Start of processing for Process_Activation
2881
2882 begin
2883 -- Nothing to do when the activation is a guaranteed ABE
2884
2885 if Is_Known_Guaranteed_ABE (Call) then
2886 return;
2887 end if;
2888
2889 Task_Objs := Activated_Task_Objects (Call_Rep);
2890
2891 -- The activation call has been processed at least once, and all
2892 -- task objects have already been collected. Directly process the
2893 -- objects without having to reexamine the context of the call.
2894
2895 if NE_List.Present (Task_Objs) then
2896 Process_Task_Objects (Task_Objs);
2897
2898 -- Otherwise the activation call is being processed for the first
2899 -- time. Collect all task objects in case the call is reprocessed
2900 -- multiple times.
2901
2902 else
2903 Task_Objs := NE_List.Create;
2904 Set_Activated_Task_Objects (Call_Rep, Task_Objs);
2905
2906 -- Find the context of the activation call where all task objects
2907 -- being activated are declared. This is usually the parent of the
2908 -- call.
2909
2910 Context := Parent (Call);
2911
2912 -- Handle the case where the activation call appears within the
2913 -- handled statements of a block or a body.
2914
2915 if Nkind (Context) = N_Handled_Sequence_Of_Statements then
2916 Context := Parent (Context);
2917 end if;
2918
2919 -- Process all task objects in both the spec and body when the
2920 -- activation call appears in a package body.
2921
2922 if Nkind (Context) = N_Package_Body then
2923 Spec :=
2924 Specification
2925 (Unit_Declaration_Node (Corresponding_Spec (Context)));
2926
2927 Traverse_List
2928 (List => Visible_Declarations (Spec),
2929 Task_Objs => Task_Objs);
2930
2931 Traverse_List
2932 (List => Private_Declarations (Spec),
2933 Task_Objs => Task_Objs);
2934
2935 Traverse_List
2936 (List => Declarations (Context),
2937 Task_Objs => Task_Objs);
2938
2939 -- Process all task objects in the spec when the activation call
2940 -- appears in a package spec.
2941
2942 elsif Nkind (Context) = N_Package_Specification then
2943 Traverse_List
2944 (List => Visible_Declarations (Context),
2945 Task_Objs => Task_Objs);
2946
2947 Traverse_List
2948 (List => Private_Declarations (Context),
2949 Task_Objs => Task_Objs);
2950
2951 -- Otherwise the context must be a block or a body. Process all
2952 -- task objects found in the declarations.
2953
2954 else
2955 pragma Assert (Nkind_In (Context, N_Block_Statement,
2956 N_Entry_Body,
2957 N_Protected_Body,
2958 N_Subprogram_Body,
2959 N_Task_Body));
2960
2961 Traverse_List
2962 (List => Declarations (Context),
2963 Task_Objs => Task_Objs);
2964 end if;
2965 end if;
2966 end Process_Activation;
2967 end Activation_Processor;
2968
2969 -----------------------
2970 -- Assignment_Target --
2971 -----------------------
2972
2973 function Assignment_Target (Asmt : Node_Id) return Node_Id is
2974 Nam : Node_Id;
2975
2976 begin
2977 Nam := Name (Asmt);
2978
2979 -- When the name denotes an array or record component, find the whole
2980 -- object.
2981
2982 while Nkind_In (Nam, N_Explicit_Dereference,
2983 N_Indexed_Component,
2984 N_Selected_Component,
2985 N_Slice)
2986 loop
2987 Nam := Prefix (Nam);
2988 end loop;
2989
2990 return Nam;
2991 end Assignment_Target;
2992
2993 --------------------
2994 -- Body_Processor --
2995 --------------------
2996
2997 package body Body_Processor is
2998
2999 ---------------------
3000 -- Data structures --
3001 ---------------------
3002
3003 -- The following map relates scenario lists to subprogram bodies
3004
3005 Nested_Scenarios_Map : NE_List_Map.Dynamic_Hash_Table := NE_List_Map.Nil;
3006
3007 -- The following set contains all subprogram bodies that have been
3008 -- processed by routine Traverse_Body.
3009
3010 Traversed_Bodies_Set : NE_Set.Membership_Set := NE_Set.Nil;
3011
3012 -----------------------
3013 -- Local subprograms --
3014 -----------------------
3015
3016 function Is_Traversed_Body (N : Node_Id) return Boolean;
3017 pragma Inline (Is_Traversed_Body);
3018 -- Determine whether subprogram body N has already been traversed
3019
3020 function Nested_Scenarios
3021 (N : Node_Id) return NE_List.Doubly_Linked_List;
3022 pragma Inline (Nested_Scenarios);
3023 -- Obtain the list of scenarios associated with subprogram body N
3024
3025 procedure Set_Is_Traversed_Body
3026 (N : Node_Id;
3027 Val : Boolean := True);
3028 pragma Inline (Set_Is_Traversed_Body);
3029 -- Mark subprogram body N as traversed depending on value Val
3030
3031 procedure Set_Nested_Scenarios
3032 (N : Node_Id;
3033 Scenarios : NE_List.Doubly_Linked_List);
3034 pragma Inline (Set_Nested_Scenarios);
3035 -- Associate scenario list Scenarios with subprogram body N
3036
3037 -----------------------------
3038 -- Finalize_Body_Processor --
3039 -----------------------------
3040
3041 procedure Finalize_Body_Processor is
3042 begin
3043 NE_List_Map.Destroy (Nested_Scenarios_Map);
3044 NE_Set.Destroy (Traversed_Bodies_Set);
3045 end Finalize_Body_Processor;
3046
3047 -------------------------------
3048 -- Initialize_Body_Processor --
3049 -------------------------------
3050
3051 procedure Initialize_Body_Processor is
3052 begin
3053 Nested_Scenarios_Map := NE_List_Map.Create (250);
3054 Traversed_Bodies_Set := NE_Set.Create (250);
3055 end Initialize_Body_Processor;
3056
3057 -----------------------
3058 -- Is_Traversed_Body --
3059 -----------------------
3060
3061 function Is_Traversed_Body (N : Node_Id) return Boolean is
3062 pragma Assert (Present (N));
3063 begin
3064 return NE_Set.Contains (Traversed_Bodies_Set, N);
3065 end Is_Traversed_Body;
3066
3067 ----------------------
3068 -- Nested_Scenarios --
3069 ----------------------
3070
3071 function Nested_Scenarios
3072 (N : Node_Id) return NE_List.Doubly_Linked_List
3073 is
3074 pragma Assert (Present (N));
3075 pragma Assert (Nkind (N) = N_Subprogram_Body);
3076
3077 begin
3078 return NE_List_Map.Get (Nested_Scenarios_Map, N);
3079 end Nested_Scenarios;
3080
3081 ----------------------------
3082 -- Reset_Traversed_Bodies --
3083 ----------------------------
3084
3085 procedure Reset_Traversed_Bodies is
3086 begin
3087 NE_Set.Reset (Traversed_Bodies_Set);
3088 end Reset_Traversed_Bodies;
3089
3090 ---------------------------
3091 -- Set_Is_Traversed_Body --
3092 ---------------------------
3093
3094 procedure Set_Is_Traversed_Body
3095 (N : Node_Id;
3096 Val : Boolean := True)
3097 is
3098 pragma Assert (Present (N));
3099
3100 begin
3101 if Val then
3102 NE_Set.Insert (Traversed_Bodies_Set, N);
3103 else
3104 NE_Set.Delete (Traversed_Bodies_Set, N);
3105 end if;
3106 end Set_Is_Traversed_Body;
3107
3108 --------------------------
3109 -- Set_Nested_Scenarios --
3110 --------------------------
3111
3112 procedure Set_Nested_Scenarios
3113 (N : Node_Id;
3114 Scenarios : NE_List.Doubly_Linked_List)
3115 is
3116 pragma Assert (Present (N));
3117 begin
3118 NE_List_Map.Put (Nested_Scenarios_Map, N, Scenarios);
3119 end Set_Nested_Scenarios;
3120
3121 -------------------
3122 -- Traverse_Body --
3123 -------------------
3124
3125 procedure Traverse_Body
3126 (N : Node_Id;
3127 Requires_Processing : Scenario_Predicate_Ptr;
3128 Processor : Scenario_Processor_Ptr;
3129 In_State : Processing_In_State)
3130 is
3131 Scenarios : NE_List.Doubly_Linked_List := NE_List.Nil;
3132 -- The list of scenarios that appear within the declarations and
3133 -- statement of subprogram body N. The variable is intentionally
3134 -- global because Is_Potential_Scenario needs to populate it.
3135
3136 function In_Task_Body (Nod : Node_Id) return Boolean;
3137 pragma Inline (In_Task_Body);
3138 -- Determine whether arbitrary node Nod appears within a task body
3139
3140 function Is_Synchronous_Suspension_Call
3141 (Nod : Node_Id) return Boolean;
3142 pragma Inline (Is_Synchronous_Suspension_Call);
3143 -- Determine whether arbitrary node Nod denotes a call to one of
3144 -- these routines:
3145 --
3146 -- Ada.Synchronous_Barriers.Wait_For_Release
3147 -- Ada.Synchronous_Task_Control.Suspend_Until_True
3148
3149 procedure Traverse_Collected_Scenarios;
3150 pragma Inline (Traverse_Collected_Scenarios);
3151 -- Traverse the already collected scenarios in list Scenarios by
3152 -- invoking Processor on each individual one.
3153
3154 procedure Traverse_List (List : List_Id);
3155 pragma Inline (Traverse_List);
3156 -- Invoke Traverse_Potential_Scenarios on each node in list List
3157
3158 function Traverse_Potential_Scenario
3159 (Scen : Node_Id) return Traverse_Result;
3160 pragma Inline (Traverse_Potential_Scenario);
3161 -- Determine whether arbitrary node Scen is a suitable scenario using
3162 -- predicate Is_Scenario and traverse it by invoking Processor on it.
3163
3164 procedure Traverse_Potential_Scenarios is
3165 new Traverse_Proc (Traverse_Potential_Scenario);
3166
3167 ------------------
3168 -- In_Task_Body --
3169 ------------------
3170
3171 function In_Task_Body (Nod : Node_Id) return Boolean is
3172 Par : Node_Id;
3173
3174 begin
3175 -- Climb the parent chain looking for a task body [procedure]
3176
3177 Par := Nod;
3178 while Present (Par) loop
3179 if Nkind (Par) = N_Task_Body then
3180 return True;
3181
3182 elsif Nkind (Par) = N_Subprogram_Body
3183 and then Is_Task_Body_Procedure (Par)
3184 then
3185 return True;
3186
3187 -- Prevent the search from going too far. Note that this test
3188 -- shares nodes with the two cases above, and must come last.
3189
3190 elsif Is_Body_Or_Package_Declaration (Par) then
3191 return False;
3192 end if;
3193
3194 Par := Parent (Par);
3195 end loop;
3196
3197 return False;
3198 end In_Task_Body;
3199
3200 ------------------------------------
3201 -- Is_Synchronous_Suspension_Call --
3202 ------------------------------------
3203
3204 function Is_Synchronous_Suspension_Call
3205 (Nod : Node_Id) return Boolean
3206 is
3207 Subp_Id : Entity_Id;
3208
3209 begin
3210 -- To qualify, the call must invoke one of the runtime routines
3211 -- which perform synchronous suspension.
3212
3213 if Is_Suitable_Call (Nod) then
3214 Subp_Id := Target (Nod);
3215
3216 return
3217 Is_RTE (Subp_Id, RE_Suspend_Until_True)
3218 or else
3219 Is_RTE (Subp_Id, RE_Wait_For_Release);
3220 end if;
3221
3222 return False;
3223 end Is_Synchronous_Suspension_Call;
3224
3225 ----------------------------------
3226 -- Traverse_Collected_Scenarios --
3227 ----------------------------------
3228
3229 procedure Traverse_Collected_Scenarios is
3230 Iter : NE_List.Iterator;
3231 Scen : Node_Id;
3232
3233 begin
3234 Iter := NE_List.Iterate (Scenarios);
3235 while NE_List.Has_Next (Iter) loop
3236 NE_List.Next (Iter, Scen);
3237
3238 -- The current scenario satisfies the input predicate, process
3239 -- it.
3240
3241 if Requires_Processing.all (Scen) then
3242 Processor.all (Scen, In_State);
3243 end if;
3244 end loop;
3245 end Traverse_Collected_Scenarios;
3246
3247 -------------------
3248 -- Traverse_List --
3249 -------------------
3250
3251 procedure Traverse_List (List : List_Id) is
3252 Scen : Node_Id;
3253
3254 begin
3255 Scen := First (List);
3256 while Present (Scen) loop
3257 Traverse_Potential_Scenarios (Scen);
3258 Next (Scen);
3259 end loop;
3260 end Traverse_List;
3261
3262 ---------------------------------
3263 -- Traverse_Potential_Scenario --
3264 ---------------------------------
3265
3266 function Traverse_Potential_Scenario
3267 (Scen : Node_Id) return Traverse_Result
3268 is
3269 begin
3270 -- Special cases
3271
3272 -- Skip constructs which do not have elaboration of their own and
3273 -- need to be elaborated by other means such as invocation, task
3274 -- activation, etc.
3275
3276 if Is_Non_Library_Level_Encapsulator (Scen) then
3277 return Skip;
3278
3279 -- Terminate the traversal of a task body when encountering an
3280 -- accept or select statement, and
3281 --
3282 -- * Entry calls during elaboration are not allowed. In this
3283 -- case the accept or select statement will cause the task
3284 -- to block at elaboration time because there are no entry
3285 -- calls to unblock it.
3286 --
3287 -- or
3288 --
3289 -- * Switch -gnatd_a (stop elaboration checks on accept or
3290 -- select statement) is in effect.
3291
3292 elsif (Debug_Flag_Underscore_A
3293 or else Restriction_Active
3294 (No_Entry_Calls_In_Elaboration_Code))
3295 and then Nkind_In (Original_Node (Scen), N_Accept_Statement,
3296 N_Selective_Accept)
3297 then
3298 return Abandon;
3299
3300 -- Terminate the traversal of a task body when encountering a
3301 -- suspension call, and
3302 --
3303 -- * Entry calls during elaboration are not allowed. In this
3304 -- case the suspension call emulates an entry call and will
3305 -- cause the task to block at elaboration time.
3306 --
3307 -- or
3308 --
3309 -- * Switch -gnatd_s (stop elaboration checks on synchronous
3310 -- suspension) is in effect.
3311 --
3312 -- Note that the guard should not be checking the state of flag
3313 -- Within_Task_Body because only suspension calls which appear
3314 -- immediately within the statements of the task are supported.
3315 -- Flag Within_Task_Body carries over to deeper levels of the
3316 -- traversal.
3317
3318 elsif (Debug_Flag_Underscore_S
3319 or else Restriction_Active
3320 (No_Entry_Calls_In_Elaboration_Code))
3321 and then Is_Synchronous_Suspension_Call (Scen)
3322 and then In_Task_Body (Scen)
3323 then
3324 return Abandon;
3325
3326 -- Certain nodes carry semantic lists which act as repositories
3327 -- until expansion transforms the node and relocates the contents.
3328 -- Examine these lists in case expansion is disabled.
3329
3330 elsif Nkind_In (Scen, N_And_Then, N_Or_Else) then
3331 Traverse_List (Actions (Scen));
3332
3333 elsif Nkind_In (Scen, N_Elsif_Part, N_Iteration_Scheme) then
3334 Traverse_List (Condition_Actions (Scen));
3335
3336 elsif Nkind (Scen) = N_If_Expression then
3337 Traverse_List (Then_Actions (Scen));
3338 Traverse_List (Else_Actions (Scen));
3339
3340 elsif Nkind_In (Scen, N_Component_Association,
3341 N_Iterated_Component_Association)
3342 then
3343 Traverse_List (Loop_Actions (Scen));
3344
3345 -- General case
3346
3347 -- The current node satisfies the input predicate, process it
3348
3349 elsif Requires_Processing.all (Scen) then
3350 Processor.all (Scen, In_State);
3351 end if;
3352
3353 -- Save a general scenario regardless of whether it satisfies the
3354 -- input predicate. This allows for quick subsequent traversals of
3355 -- general scenarios, even with different predicates.
3356
3357 if Is_Suitable_Access_Taken (Scen)
3358 or else Is_Suitable_Call (Scen)
3359 or else Is_Suitable_Instantiation (Scen)
3360 or else Is_Suitable_Variable_Assignment (Scen)
3361 or else Is_Suitable_Variable_Reference (Scen)
3362 then
3363 NE_List.Append (Scenarios, Scen);
3364 end if;
3365
3366 return OK;
3367 end Traverse_Potential_Scenario;
3368
3369 -- Start of processing for Traverse_Body
3370
3371 begin
3372 -- Nothing to do when the traversal is suppressed
3373
3374 if In_State.Traversal = No_Traversal then
3375 return;
3376
3377 -- Nothing to do when there is no input
3378
3379 elsif No (N) then
3380 return;
3381
3382 -- Nothing to do when the input is not a subprogram body
3383
3384 elsif Nkind (N) /= N_Subprogram_Body then
3385 return;
3386
3387 -- Nothing to do if the subprogram body was already traversed
3388
3389 elsif Is_Traversed_Body (N) then
3390 return;
3391 end if;
3392
3393 -- Mark the subprogram body as traversed
3394
3395 Set_Is_Traversed_Body (N);
3396
3397 Scenarios := Nested_Scenarios (N);
3398
3399 -- The subprogram body has been traversed at least once, and all
3400 -- scenarios that appear within its declarations and statements
3401 -- have already been collected. Directly retraverse the scenarios
3402 -- without having to retraverse the subprogram body subtree.
3403
3404 if NE_List.Present (Scenarios) then
3405 Traverse_Collected_Scenarios;
3406
3407 -- Otherwise the subprogram body is being traversed for the first
3408 -- time. Collect all scenarios that appear within its declarations
3409 -- and statements in case the subprogram body has to be retraversed
3410 -- multiple times.
3411
3412 else
3413 Scenarios := NE_List.Create;
3414 Set_Nested_Scenarios (N, Scenarios);
3415
3416 Traverse_List (Declarations (N));
3417 Traverse_Potential_Scenarios (Handled_Statement_Sequence (N));
3418 end if;
3419 end Traverse_Body;
3420 end Body_Processor;
3421
3422 -----------------------
3423 -- Build_Call_Marker --
3424 -----------------------
3425
3426 procedure Build_Call_Marker (N : Node_Id) is
3427 function In_External_Context
3428 (Call : Node_Id;
3429 Subp_Id : Entity_Id) return Boolean;
3430 pragma Inline (In_External_Context);
3431 -- Determine whether entry, operator, or subprogram Subp_Id is external
3432 -- to call Call which must reside within an instance.
3433
3434 function In_Premature_Context (Call : Node_Id) return Boolean;
3435 pragma Inline (In_Premature_Context);
3436 -- Determine whether call Call appears within a premature context
3437
3438 function Is_Default_Expression (Call : Node_Id) return Boolean;
3439 pragma Inline (Is_Default_Expression);
3440 -- Determine whether call Call acts as the expression of a defaulted
3441 -- parameter within a source call.
3442
3443 function Is_Generic_Formal_Subp (Subp_Id : Entity_Id) return Boolean;
3444 pragma Inline (Is_Generic_Formal_Subp);
3445 -- Determine whether subprogram Subp_Id denotes a generic formal
3446 -- subprogram which appears in the "prologue" of an instantiation.
3447
3448 -------------------------
3449 -- In_External_Context --
3450 -------------------------
3451
3452 function In_External_Context
3453 (Call : Node_Id;
3454 Subp_Id : Entity_Id) return Boolean
3455 is
3456 Spec_Decl : constant Entity_Id := Unit_Declaration_Node (Subp_Id);
3457
3458 Inst : Node_Id;
3459 Inst_Body : Node_Id;
3460 Inst_Spec : Node_Id;
3461
3462 begin
3463 Inst := Find_Enclosing_Instance (Call);
3464
3465 -- The call appears within an instance
3466
3467 if Present (Inst) then
3468
3469 -- The call comes from the main unit and the target does not
3470
3471 if In_Extended_Main_Code_Unit (Call)
3472 and then not In_Extended_Main_Code_Unit (Spec_Decl)
3473 then
3474 return True;
3475
3476 -- Otherwise the target declaration must not appear within the
3477 -- instance spec or body.
3478
3479 else
3480 Spec_And_Body_From_Node
3481 (N => Inst,
3482 Spec_Decl => Inst_Spec,
3483 Body_Decl => Inst_Body);
3484
3485 return not In_Subtree
3486 (N => Spec_Decl,
3487 Root1 => Inst_Spec,
3488 Root2 => Inst_Body);
3489 end if;
3490 end if;
3491
3492 return False;
3493 end In_External_Context;
3494
3495 --------------------------
3496 -- In_Premature_Context --
3497 --------------------------
3498
3499 function In_Premature_Context (Call : Node_Id) return Boolean is
3500 Par : Node_Id;
3501
3502 begin
3503 -- Climb the parent chain looking for premature contexts
3504
3505 Par := Parent (Call);
3506 while Present (Par) loop
3507
3508 -- Aspect specifications and generic associations are premature
3509 -- contexts because nested calls has not been relocated to their
3510 -- final context.
3511
3512 if Nkind_In (Par, N_Aspect_Specification,
3513 N_Generic_Association)
3514 then
3515 return True;
3516
3517 -- Prevent the search from going too far
3518
3519 elsif Is_Body_Or_Package_Declaration (Par) then
3520 exit;
3521 end if;
3522
3523 Par := Parent (Par);
3524 end loop;
3525
3526 return False;
3527 end In_Premature_Context;
3528
3529 ---------------------------
3530 -- Is_Default_Expression --
3531 ---------------------------
3532
3533 function Is_Default_Expression (Call : Node_Id) return Boolean is
3534 Outer_Call : constant Node_Id := Parent (Call);
3535 Outer_Nam : Node_Id;
3536
3537 begin
3538 -- To qualify, the node must appear immediately within a source call
3539 -- which invokes a source target.
3540
3541 if Nkind_In (Outer_Call, N_Entry_Call_Statement,
3542 N_Function_Call,
3543 N_Procedure_Call_Statement)
3544 and then Comes_From_Source (Outer_Call)
3545 then
3546 Outer_Nam := Call_Name (Outer_Call);
3547
3548 return
3549 Is_Entity_Name (Outer_Nam)
3550 and then Present (Entity (Outer_Nam))
3551 and then Is_Subprogram_Or_Entry (Entity (Outer_Nam))
3552 and then Comes_From_Source (Entity (Outer_Nam));
3553 end if;
3554
3555 return False;
3556 end Is_Default_Expression;
3557
3558 ----------------------------
3559 -- Is_Generic_Formal_Subp --
3560 ----------------------------
3561
3562 function Is_Generic_Formal_Subp (Subp_Id : Entity_Id) return Boolean is
3563 Subp_Decl : constant Node_Id := Unit_Declaration_Node (Subp_Id);
3564 Context : constant Node_Id := Parent (Subp_Decl);
3565
3566 begin
3567 -- To qualify, the subprogram must rename a generic actual subprogram
3568 -- where the enclosing context is an instantiation.
3569
3570 return
3571 Nkind (Subp_Decl) = N_Subprogram_Renaming_Declaration
3572 and then not Comes_From_Source (Subp_Decl)
3573 and then Nkind_In (Context, N_Function_Specification,
3574 N_Package_Specification,
3575 N_Procedure_Specification)
3576 and then Present (Generic_Parent (Context));
3577 end Is_Generic_Formal_Subp;
3578
3579 -- Local variables
3580
3581 Call_Nam : Node_Id;
3582 Marker : Node_Id;
3583 Subp_Id : Entity_Id;
3584
3585 -- Start of processing for Build_Call_Marker
3586
3587 begin
3588 -- Nothing to do when switch -gnatH (legacy elaboration checking mode
3589 -- enabled) is in effect because the legacy ABE mechanism does not need
3590 -- to carry out this action.
3591
3592 if Legacy_Elaboration_Checks then
3593 return;
3594
3595 -- Nothing to do for ASIS because ABE checks and diagnostics are not
3596 -- performed in this mode.
3597
3598 elsif ASIS_Mode then
3599 return;
3600
3601 -- Nothing to do when the call is being preanalyzed as the marker will
3602 -- be inserted in the wrong place.
3603
3604 elsif Preanalysis_Active then
3605 return;
3606
3607 -- Nothing to do when the elaboration phase of the compiler is not
3608 -- active.
3609
3610 elsif not Elaboration_Phase_Active then
3611 return;
3612
3613 -- Nothing to do when the input does not denote a call or a requeue
3614
3615 elsif not Nkind_In (N, N_Entry_Call_Statement,
3616 N_Function_Call,
3617 N_Procedure_Call_Statement,
3618 N_Requeue_Statement)
3619 then
3620 return;
3621
3622 -- Nothing to do when the input denotes entry call or requeue statement,
3623 -- and switch -gnatd_e (ignore entry calls and requeue statements for
3624 -- elaboration) is in effect.
3625
3626 elsif Debug_Flag_Underscore_E
3627 and then Nkind_In (N, N_Entry_Call_Statement, N_Requeue_Statement)
3628 then
3629 return;
3630
3631 -- Nothing to do when the call is analyzed/resolved too early within an
3632 -- intermediate context. This check is saved for last because it incurs
3633 -- a performance penalty.
3634
3635 elsif In_Premature_Context (N) then
3636 return;
3637 end if;
3638
3639 Call_Nam := Call_Name (N);
3640
3641 -- Nothing to do when the call is erroneous or left in a bad state
3642
3643 if not (Is_Entity_Name (Call_Nam)
3644 and then Present (Entity (Call_Nam))
3645 and then Is_Subprogram_Or_Entry (Entity (Call_Nam)))
3646 then
3647 return;
3648 end if;
3649
3650 Subp_Id := Canonical_Subprogram (Entity (Call_Nam));
3651
3652 -- Nothing to do when the call invokes a generic formal subprogram and
3653 -- switch -gnatd.G (ignore calls through generic formal parameters for
3654 -- elaboration) is in effect. This check must be performed with the
3655 -- direct target of the call to avoid the side effects of mapping
3656 -- actuals to formals using renamings.
3657
3658 if Debug_Flag_Dot_GG
3659 and then Is_Generic_Formal_Subp (Entity (Call_Nam))
3660 then
3661 return;
3662
3663 -- Nothing to do when the call appears within the expanded spec or
3664 -- body of an instantiated generic, the call does not invoke a generic
3665 -- formal subprogram, the target is external to the instance, and switch
3666 -- -gnatdL (ignore external calls from instances for elaboration) is in
3667 -- effect. This check must be performed with the direct target of the
3668 -- call to avoid the side effects of mapping actuals to formals using
3669 -- renamings.
3670
3671 elsif Debug_Flag_LL
3672 and then not Is_Generic_Formal_Subp (Entity (Call_Nam))
3673 and then In_External_Context
3674 (Call => N,
3675 Subp_Id => Subp_Id)
3676 then
3677 return;
3678
3679 -- Nothing to do when the call invokes an assertion pragma procedure
3680 -- and switch -gnatd_p (ignore assertion pragmas for elaboration) is
3681 -- in effect.
3682
3683 elsif Debug_Flag_Underscore_P
3684 and then Is_Assertion_Pragma_Target (Subp_Id)
3685 then
3686 return;
3687
3688 -- Source calls to source targets are always considered because they
3689 -- reflect the original call graph.
3690
3691 elsif Comes_From_Source (N) and then Comes_From_Source (Subp_Id) then
3692 null;
3693
3694 -- A call to a source function which acts as the default expression in
3695 -- another call requires special detection.
3696
3697 elsif Comes_From_Source (Subp_Id)
3698 and then Nkind (N) = N_Function_Call
3699 and then Is_Default_Expression (N)
3700 then
3701 null;
3702
3703 -- The target emulates Ada semantics
3704
3705 elsif Is_Ada_Semantic_Target (Subp_Id) then
3706 null;
3707
3708 -- The target acts as a link between scenarios
3709
3710 elsif Is_Bridge_Target (Subp_Id) then
3711 null;
3712
3713 -- The target emulates SPARK semantics
3714
3715 elsif Is_SPARK_Semantic_Target (Subp_Id) then
3716 null;
3717
3718 -- Otherwise the call is not suitable for ABE processing. This prevents
3719 -- the generation of call markers which will never play a role in ABE
3720 -- diagnostics.
3721
3722 else
3723 return;
3724 end if;
3725
3726 -- At this point it is known that the call will play some role in ABE
3727 -- checks and diagnostics. Create a corresponding call marker in case
3728 -- the original call is heavily transformed by expansion later on.
3729
3730 Marker := Make_Call_Marker (Sloc (N));
3731
3732 -- Inherit the attributes of the original call
3733
3734 Set_Is_Declaration_Level_Node
3735 (Marker, Find_Enclosing_Level (N) = Declaration_Level);
3736
3737 Set_Is_Dispatching_Call
3738 (Marker, Nkind_In (N, N_Function_Call, N_Procedure_Call_Statement)
3739 and then Present (Controlling_Argument (N)));
3740
3741 Set_Is_Elaboration_Checks_OK_Node
3742 (Marker, Is_Elaboration_Checks_OK_Node (N));
3743
3744 Set_Is_Elaboration_Warnings_OK_Node
3745 (Marker, Is_Elaboration_Warnings_OK_Node (N));
3746
3747 Set_Is_Ignored_Ghost_Node (Marker, Is_Ignored_Ghost_Node (N));
3748 Set_Is_Source_Call (Marker, Comes_From_Source (N));
3749 Set_Is_SPARK_Mode_On_Node (Marker, Is_SPARK_Mode_On_Node (N));
3750 Set_Target (Marker, Subp_Id);
3751
3752 -- The marker is inserted prior to the original call. This placement has
3753 -- several desirable effects:
3754
3755 -- 1) The marker appears in the same context, in close proximity to
3756 -- the call.
3757
3758 -- <marker>
3759 -- <call>
3760
3761 -- 2) Inserting the marker prior to the call ensures that an ABE check
3762 -- will take effect prior to the call.
3763
3764 -- <ABE check>
3765 -- <marker>
3766 -- <call>
3767
3768 -- 3) The above two properties are preserved even when the call is a
3769 -- function which is subsequently relocated in order to capture its
3770 -- result. Note that if the call is relocated to a new context, the
3771 -- relocated call will receive a marker of its own.
3772
3773 -- <ABE check>
3774 -- <maker>
3775 -- Temp : ... := Func_Call ...;
3776 -- ... Temp ...
3777
3778 -- The insertion must take place even when the call does not occur in
3779 -- the main unit to keep the tree symmetric. This ensures that internal
3780 -- name serialization is consistent in case the call marker causes the
3781 -- tree to transform in some way.
3782
3783 Insert_Action (N, Marker);
3784
3785 -- The marker becomes the "corresponding" scenario for the call. Save
3786 -- the marker for later processing by the ABE phase.
3787
3788 Record_Elaboration_Scenario (Marker);
3789 end Build_Call_Marker;
3790
3791 -------------------------------------
3792 -- Build_Variable_Reference_Marker --
3793 -------------------------------------
3794
3795 procedure Build_Variable_Reference_Marker
3796 (N : Node_Id;
3797 Read : Boolean;
3798 Write : Boolean)
3799 is
3800 function Ultimate_Variable (Var_Id : Entity_Id) return Entity_Id;
3801 pragma Inline (Ultimate_Variable);
3802 -- Obtain the ultimate renamed variable of variable Var_Id
3803
3804 -----------------------
3805 -- Ultimate_Variable --
3806 -----------------------
3807
3808 function Ultimate_Variable (Var_Id : Entity_Id) return Entity_Id is
3809 Ren_Id : Entity_Id;
3810
3811 begin
3812 Ren_Id := Var_Id;
3813 while Present (Renamed_Entity (Ren_Id))
3814 and then Nkind (Renamed_Entity (Ren_Id)) in N_Entity
3815 loop
3816 Ren_Id := Renamed_Entity (Ren_Id);
3817 end loop;
3818
3819 return Ren_Id;
3820 end Ultimate_Variable;
3821
3822 -- Local variables
3823
3824 Var_Id : constant Entity_Id := Ultimate_Variable (Entity (N));
3825 Marker : Node_Id;
3826
3827 -- Start of processing for Build_Variable_Reference_Marker
3828
3829 begin
3830 -- Nothing to do when the elaboration phase of the compiler is not
3831 -- active.
3832
3833 if not Elaboration_Phase_Active then
3834 return;
3835 end if;
3836
3837 Marker := Make_Variable_Reference_Marker (Sloc (N));
3838
3839 -- Inherit the attributes of the original variable reference
3840
3841 Set_Is_Elaboration_Checks_OK_Node
3842 (Marker, Is_Elaboration_Checks_OK_Node (N));
3843
3844 Set_Is_Elaboration_Warnings_OK_Node
3845 (Marker, Is_Elaboration_Warnings_OK_Node (N));
3846
3847 Set_Is_Read (Marker, Read);
3848 Set_Is_SPARK_Mode_On_Node (Marker, Is_SPARK_Mode_On_Node (N));
3849 Set_Is_Write (Marker, Write);
3850 Set_Target (Marker, Var_Id);
3851
3852 -- The marker is inserted prior to the original variable reference. The
3853 -- insertion must take place even when the reference does not occur in
3854 -- the main unit to keep the tree symmetric. This ensures that internal
3855 -- name serialization is consistent in case the variable marker causes
3856 -- the tree to transform in some way.
3857
3858 Insert_Action (N, Marker);
3859
3860 -- The marker becomes the "corresponding" scenario for the reference.
3861 -- Save the marker for later processing for the ABE phase.
3862
3863 Record_Elaboration_Scenario (Marker);
3864 end Build_Variable_Reference_Marker;
3865
3866 ---------------
3867 -- Call_Name --
3868 ---------------
3869
3870 function Call_Name (Call : Node_Id) return Node_Id is
3871 Nam : Node_Id;
3872
3873 begin
3874 Nam := Name (Call);
3875
3876 -- When the call invokes an entry family, the name appears as an indexed
3877 -- component.
3878
3879 if Nkind (Nam) = N_Indexed_Component then
3880 Nam := Prefix (Nam);
3881 end if;
3882
3883 -- When the call employs the object.operation form, the name appears as
3884 -- a selected component.
3885
3886 if Nkind (Nam) = N_Selected_Component then
3887 Nam := Selector_Name (Nam);
3888 end if;
3889
3890 return Nam;
3891 end Call_Name;
3892
3893 --------------------------
3894 -- Canonical_Subprogram --
3895 --------------------------
3896
3897 function Canonical_Subprogram (Subp_Id : Entity_Id) return Entity_Id is
3898 Canon_Id : Entity_Id;
3899
3900 begin
3901 Canon_Id := Subp_Id;
3902
3903 -- Use the original protected subprogram when dealing with one of the
3904 -- specialized lock-manipulating versions.
3905
3906 if Is_Protected_Body_Subp (Canon_Id) then
3907 Canon_Id := Protected_Subprogram (Canon_Id);
3908 end if;
3909
3910 -- Obtain the original subprogram except when the subprogram is also
3911 -- an instantiation. In this case the alias is the internally generated
3912 -- subprogram which appears within the anonymous package created for the
3913 -- instantiation, making it unuitable.
3914
3915 if not Is_Generic_Instance (Canon_Id) then
3916 Canon_Id := Get_Renamed_Entity (Canon_Id);
3917 end if;
3918
3919 return Canon_Id;
3920 end Canonical_Subprogram;
3921
3922 ---------------------------------
3923 -- Check_Elaboration_Scenarios --
3924 ---------------------------------
3925
3926 procedure Check_Elaboration_Scenarios is
3927 Iter : NE_Set.Iterator;
3928
3929 begin
3930 -- Nothing to do when switch -gnatH (legacy elaboration checking mode
3931 -- enabled) is in effect because the legacy ABE mechanism does not need
3932 -- to carry out this action.
3933
3934 if Legacy_Elaboration_Checks then
3935 Finalize_All_Data_Structures;
3936 return;
3937
3938 -- Nothing to do for ASIS because ABE checks and diagnostics are not
3939 -- performed in this mode.
3940
3941 elsif ASIS_Mode then
3942 Finalize_All_Data_Structures;
3943 return;
3944
3945 -- Nothing to do when the elaboration phase of the compiler is not
3946 -- active.
3947
3948 elsif not Elaboration_Phase_Active then
3949 Finalize_All_Data_Structures;
3950 return;
3951 end if;
3952
3953 -- Restore the original elaboration model which was in effect when the
3954 -- scenarios were first recorded. The model may be specified by pragma
3955 -- Elaboration_Checks which appears on the initial declaration of the
3956 -- main unit.
3957
3958 Install_Elaboration_Model (Unit_Entity (Cunit_Entity (Main_Unit)));
3959
3960 -- Examine the context of the main unit and record all units with prior
3961 -- elaboration with respect to it.
3962
3963 Collect_Elaborated_Units;
3964
3965 -- Examine all scenarios saved during the Recording phase applying the
3966 -- Ada or SPARK elaboration rules in order to detect and diagnose ABE
3967 -- issues, install conditional ABE checks, and ensure the elaboration
3968 -- of units.
3969
3970 Iter := Iterate_Declaration_Scenarios;
3971 Check_Conditional_ABE_Scenarios (Iter);
3972
3973 Iter := Iterate_Library_Body_Scenarios;
3974 Check_Conditional_ABE_Scenarios (Iter);
3975
3976 Iter := Iterate_Library_Spec_Scenarios;
3977 Check_Conditional_ABE_Scenarios (Iter);
3978
3979 -- Examine each SPARK scenario saved during the Recording phase which
3980 -- is not necessarily executable during elaboration, but still requires
3981 -- elaboration-related checks.
3982
3983 Check_SPARK_Scenarios;
3984
3985 -- Add conditional ABE checks for all scenarios that require one when
3986 -- the dynamic model is in effect.
3987
3988 Install_Dynamic_ABE_Checks;
3989
3990 -- Examine all scenarios saved during the Recording phase along with
3991 -- invocation constructs within the spec and body of the main unit.
3992 -- Record the declarations and paths that reach into an external unit
3993 -- in the ALI file of the main unit.
3994
3995 Record_Invocation_Graph;
3996
3997 -- Destroy all internal data structures and complete the elaboration
3998 -- phase of the compiler.
3999
4000 Finalize_All_Data_Structures;
4001 Set_Elaboration_Phase (Completed);
4002 end Check_Elaboration_Scenarios;
4003
4004 ---------------------
4005 -- Check_Installer --
4006 ---------------------
4007
4008 package body Check_Installer is
4009
4010 -----------------------
4011 -- Local subprograms --
4012 -----------------------
4013
4014 function ABE_Check_Or_Failure_OK
4015 (N : Node_Id;
4016 Targ_Id : Entity_Id;
4017 Unit_Id : Entity_Id) return Boolean;
4018 pragma Inline (ABE_Check_Or_Failure_OK);
4019 -- Determine whether a conditional ABE check or guaranteed ABE failure
4020 -- can be installed for scenario N with target Targ_Id which resides in
4021 -- unit Unit_Id.
4022
4023 function Insertion_Node (N : Node_Id) return Node_Id;
4024 pragma Inline (Insertion_Node);
4025 -- Obtain the proper insertion node of an ABE check or failure for
4026 -- scenario N.
4027
4028 procedure Insert_ABE_Check_Or_Failure (N : Node_Id; Check : Node_Id);
4029 pragma Inline (Insert_ABE_Check_Or_Failure);
4030 -- Insert conditional ABE check or guaranteed ABE failure Check prior to
4031 -- scenario N.
4032
4033 procedure Install_Scenario_ABE_Check_Common
4034 (N : Node_Id;
4035 Targ_Id : Entity_Id;
4036 Targ_Rep : Target_Rep_Id);
4037 pragma Inline (Install_Scenario_ABE_Check_Common);
4038 -- Install a conditional ABE check for scenario N to ensure that target
4039 -- Targ_Id is properly elaborated. Targ_Rep is the representation of the
4040 -- target.
4041
4042 procedure Install_Scenario_ABE_Failure_Common (N : Node_Id);
4043 pragma Inline (Install_Scenario_ABE_Failure_Common);
4044 -- Install a guaranteed ABE failure for scenario N
4045
4046 procedure Install_Unit_ABE_Check_Common
4047 (N : Node_Id;
4048 Unit_Id : Entity_Id);
4049 pragma Inline (Install_Unit_ABE_Check_Common);
4050 -- Install a conditional ABE check for scenario N to ensure that unit
4051 -- Unit_Id is properly elaborated.
4052
4053 -----------------------------
4054 -- ABE_Check_Or_Failure_OK --
4055 -----------------------------
4056
4057 function ABE_Check_Or_Failure_OK
4058 (N : Node_Id;
4059 Targ_Id : Entity_Id;
4060 Unit_Id : Entity_Id) return Boolean
4061 is
4062 pragma Unreferenced (Targ_Id);
4063
4064 Ins_Node : constant Node_Id := Insertion_Node (N);
4065
4066 begin
4067 if not Check_Or_Failure_Generation_OK then
4068 return False;
4069
4070 -- Nothing to do when the scenario denots a compilation unit because
4071 -- there is no executable environment at that level.
4072
4073 elsif Nkind (Parent (Ins_Node)) = N_Compilation_Unit then
4074 return False;
4075
4076 -- An ABE check or failure is not needed when the target is defined
4077 -- in a unit which is elaborated prior to the main unit. This check
4078 -- must also consider the following cases:
4079 --
4080 -- * The unit of the target appears in the context of the main unit
4081 --
4082 -- * The unit of the target is subject to pragma Elaborate_Body. An
4083 -- ABE check MUST NOT be generated because the unit is always
4084 -- elaborated prior to the main unit.
4085 --
4086 -- * The unit of the target is the main unit. An ABE check MUST be
4087 -- added in this case because a conditional ABE may be raised
4088 -- depending on the flow of execution within the main unit (flag
4089 -- Same_Unit_OK is False).
4090
4091 elsif Has_Prior_Elaboration
4092 (Unit_Id => Unit_Id,
4093 Context_OK => True,
4094 Elab_Body_OK => True)
4095 then
4096 return False;
4097 end if;
4098
4099 return True;
4100 end ABE_Check_Or_Failure_OK;
4101
4102 ------------------------------------
4103 -- Check_Or_Failure_Generation_OK --
4104 ------------------------------------
4105
4106 function Check_Or_Failure_Generation_OK return Boolean is
4107 begin
4108 -- An ABE check or failure is not needed when the compilation will
4109 -- not produce an executable.
4110
4111 if Serious_Errors_Detected > 0 then
4112 return False;
4113
4114 -- An ABE check or failure must not be installed when compiling for
4115 -- GNATprove because raise statements are not supported.
4116
4117 elsif GNATprove_Mode then
4118 return False;
4119 end if;
4120
4121 return True;
4122 end Check_Or_Failure_Generation_OK;
4123
4124 --------------------
4125 -- Insertion_Node --
4126 --------------------
4127
4128 function Insertion_Node (N : Node_Id) return Node_Id is
4129 begin
4130 -- When the scenario denotes an instantiation, the proper insertion
4131 -- node is the instance spec. This ensures that the generic actuals
4132 -- will not be evaluated prior to a potential ABE.
4133
4134 if Nkind (N) in N_Generic_Instantiation
4135 and then Present (Instance_Spec (N))
4136 then
4137 return Instance_Spec (N);
4138
4139 -- Otherwise the proper insertion node is the scenario itself
4140
4141 else
4142 return N;
4143 end if;
4144 end Insertion_Node;
4145
4146 ---------------------------------
4147 -- Insert_ABE_Check_Or_Failure --
4148 ---------------------------------
4149
4150 procedure Insert_ABE_Check_Or_Failure (N : Node_Id; Check : Node_Id) is
4151 Ins_Nod : constant Node_Id := Insertion_Node (N);
4152 Scop_Id : constant Entity_Id := Find_Enclosing_Scope (Ins_Nod);
4153
4154 begin
4155 -- Install the nearest enclosing scope of the scenario as there must
4156 -- be something on the scope stack.
4157
4158 Push_Scope (Scop_Id);
4159
4160 Insert_Action (Ins_Nod, Check);
4161
4162 Pop_Scope;
4163 end Insert_ABE_Check_Or_Failure;
4164
4165 --------------------------------
4166 -- Install_Dynamic_ABE_Checks --
4167 --------------------------------
4168
4169 procedure Install_Dynamic_ABE_Checks is
4170 Iter : NE_Set.Iterator;
4171 N : Node_Id;
4172
4173 begin
4174 if not Check_Or_Failure_Generation_OK then
4175 return;
4176
4177 -- Nothing to do if the dynamic model is not in effect
4178
4179 elsif not Dynamic_Elaboration_Checks then
4180 return;
4181 end if;
4182
4183 -- Install a conditional ABE check for each saved scenario
4184
4185 Iter := Iterate_Dynamic_ABE_Check_Scenarios;
4186 while NE_Set.Has_Next (Iter) loop
4187 NE_Set.Next (Iter, N);
4188
4189 Process_Conditional_ABE
4190 (N => N,
4191 In_State => Dynamic_Model_State);
4192 end loop;
4193 end Install_Dynamic_ABE_Checks;
4194
4195 --------------------------------
4196 -- Install_Scenario_ABE_Check --
4197 --------------------------------
4198
4199 procedure Install_Scenario_ABE_Check
4200 (N : Node_Id;
4201 Targ_Id : Entity_Id;
4202 Targ_Rep : Target_Rep_Id;
4203 Disable : Scenario_Rep_Id)
4204 is
4205 begin
4206 -- Nothing to do when the scenario does not need an ABE check
4207
4208 if not ABE_Check_Or_Failure_OK
4209 (N => N,
4210 Targ_Id => Targ_Id,
4211 Unit_Id => Unit (Targ_Rep))
4212 then
4213 return;
4214 end if;
4215
4216 -- Prevent multiple attempts to install the same ABE check
4217
4218 Disable_Elaboration_Checks (Disable);
4219
4220 Install_Scenario_ABE_Check_Common
4221 (N => N,
4222 Targ_Id => Targ_Id,
4223 Targ_Rep => Targ_Rep);
4224 end Install_Scenario_ABE_Check;
4225
4226 --------------------------------
4227 -- Install_Scenario_ABE_Check --
4228 --------------------------------
4229
4230 procedure Install_Scenario_ABE_Check
4231 (N : Node_Id;
4232 Targ_Id : Entity_Id;
4233 Targ_Rep : Target_Rep_Id;
4234 Disable : Target_Rep_Id)
4235 is
4236 begin
4237 -- Nothing to do when the scenario does not need an ABE check
4238
4239 if not ABE_Check_Or_Failure_OK
4240 (N => N,
4241 Targ_Id => Targ_Id,
4242 Unit_Id => Unit (Targ_Rep))
4243 then
4244 return;
4245 end if;
4246
4247 -- Prevent multiple attempts to install the same ABE check
4248
4249 Disable_Elaboration_Checks (Disable);
4250
4251 Install_Scenario_ABE_Check_Common
4252 (N => N,
4253 Targ_Id => Targ_Id,
4254 Targ_Rep => Targ_Rep);
4255 end Install_Scenario_ABE_Check;
4256
4257 ---------------------------------------
4258 -- Install_Scenario_ABE_Check_Common --
4259 ---------------------------------------
4260
4261 procedure Install_Scenario_ABE_Check_Common
4262 (N : Node_Id;
4263 Targ_Id : Entity_Id;
4264 Targ_Rep : Target_Rep_Id)
4265 is
4266 Targ_Body : constant Node_Id := Body_Declaration (Targ_Rep);
4267 Targ_Decl : constant Node_Id := Spec_Declaration (Targ_Rep);
4268
4269 pragma Assert (Present (Targ_Body));
4270 pragma Assert (Present (Targ_Decl));
4271
4272 procedure Build_Elaboration_Entity;
4273 pragma Inline (Build_Elaboration_Entity);
4274 -- Create a new elaboration flag for Targ_Id, insert it prior to
4275 -- Targ_Decl, and set it after Targ_Body.
4276
4277 ------------------------------
4278 -- Build_Elaboration_Entity --
4279 ------------------------------
4280
4281 procedure Build_Elaboration_Entity is
4282 Loc : constant Source_Ptr := Sloc (Targ_Id);
4283 Flag_Id : Entity_Id;
4284
4285 begin
4286 -- Nothing to do if the target has an elaboration flag
4287
4288 if Present (Elaboration_Entity (Targ_Id)) then
4289 return;
4290 end if;
4291
4292 -- Create the declaration of the elaboration flag. The name
4293 -- carries a unique counter in case the name is overloaded.
4294
4295 Flag_Id :=
4296 Make_Defining_Identifier (Loc,
4297 Chars => New_External_Name (Chars (Targ_Id), 'E', -1));
4298
4299 Set_Elaboration_Entity (Targ_Id, Flag_Id);
4300 Set_Elaboration_Entity_Required (Targ_Id);
4301
4302 Push_Scope (Scope (Targ_Id));
4303
4304 -- Generate:
4305 -- Enn : Short_Integer := 0;
4306
4307 Insert_Action (Targ_Decl,
4308 Make_Object_Declaration (Loc,
4309 Defining_Identifier => Flag_Id,
4310 Object_Definition =>
4311 New_Occurrence_Of (Standard_Short_Integer, Loc),
4312 Expression => Make_Integer_Literal (Loc, Uint_0)));
4313
4314 -- Generate:
4315 -- Enn := 1;
4316
4317 Set_Elaboration_Flag (Targ_Body, Targ_Id);
4318
4319 Pop_Scope;
4320 end Build_Elaboration_Entity;
4321
4322 -- Local variables
4323
4324 Loc : constant Source_Ptr := Sloc (N);
4325
4326 -- Start for processing for Install_Scenario_ABE_Check_Common
4327
4328 begin
4329 -- Create an elaboration flag for the target when it does not have
4330 -- one.
4331
4332 Build_Elaboration_Entity;
4333
4334 -- Generate:
4335 -- if not Targ_Id'Elaborated then
4336 -- raise Program_Error with "access before elaboration";
4337 -- end if;
4338
4339 Insert_ABE_Check_Or_Failure
4340 (N => N,
4341 Check =>
4342 Make_Raise_Program_Error (Loc,
4343 Condition =>
4344 Make_Op_Not (Loc,
4345 Right_Opnd =>
4346 Make_Attribute_Reference (Loc,
4347 Prefix => New_Occurrence_Of (Targ_Id, Loc),
4348 Attribute_Name => Name_Elaborated)),
4349 Reason => PE_Access_Before_Elaboration));
4350 end Install_Scenario_ABE_Check_Common;
4351
4352 ----------------------------------
4353 -- Install_Scenario_ABE_Failure --
4354 ----------------------------------
4355
4356 procedure Install_Scenario_ABE_Failure
4357 (N : Node_Id;
4358 Targ_Id : Entity_Id;
4359 Targ_Rep : Target_Rep_Id;
4360 Disable : Scenario_Rep_Id)
4361 is
4362 begin
4363 -- Nothing to do when the scenario does not require an ABE failure
4364
4365 if not ABE_Check_Or_Failure_OK
4366 (N => N,
4367 Targ_Id => Targ_Id,
4368 Unit_Id => Unit (Targ_Rep))
4369 then
4370 return;
4371 end if;
4372
4373 -- Prevent multiple attempts to install the same ABE check
4374
4375 Disable_Elaboration_Checks (Disable);
4376
4377 Install_Scenario_ABE_Failure_Common (N);
4378 end Install_Scenario_ABE_Failure;
4379
4380 ----------------------------------
4381 -- Install_Scenario_ABE_Failure --
4382 ----------------------------------
4383
4384 procedure Install_Scenario_ABE_Failure
4385 (N : Node_Id;
4386 Targ_Id : Entity_Id;
4387 Targ_Rep : Target_Rep_Id;
4388 Disable : Target_Rep_Id)
4389 is
4390 begin
4391 -- Nothing to do when the scenario does not require an ABE failure
4392
4393 if not ABE_Check_Or_Failure_OK
4394 (N => N,
4395 Targ_Id => Targ_Id,
4396 Unit_Id => Unit (Targ_Rep))
4397 then
4398 return;
4399 end if;
4400
4401 -- Prevent multiple attempts to install the same ABE check
4402
4403 Disable_Elaboration_Checks (Disable);
4404
4405 Install_Scenario_ABE_Failure_Common (N);
4406 end Install_Scenario_ABE_Failure;
4407
4408 -----------------------------------------
4409 -- Install_Scenario_ABE_Failure_Common --
4410 -----------------------------------------
4411
4412 procedure Install_Scenario_ABE_Failure_Common (N : Node_Id) is
4413 Loc : constant Source_Ptr := Sloc (N);
4414
4415 begin
4416 -- Generate:
4417 -- raise Program_Error with "access before elaboration";
4418
4419 Insert_ABE_Check_Or_Failure
4420 (N => N,
4421 Check =>
4422 Make_Raise_Program_Error (Loc,
4423 Reason => PE_Access_Before_Elaboration));
4424 end Install_Scenario_ABE_Failure_Common;
4425
4426 ----------------------------
4427 -- Install_Unit_ABE_Check --
4428 ----------------------------
4429
4430 procedure Install_Unit_ABE_Check
4431 (N : Node_Id;
4432 Unit_Id : Entity_Id;
4433 Disable : Scenario_Rep_Id)
4434 is
4435 Spec_Id : constant Entity_Id := Unique_Entity (Unit_Id);
4436
4437 begin
4438 -- Nothing to do when the scenario does not require an ABE check
4439
4440 if not ABE_Check_Or_Failure_OK
4441 (N => N,
4442 Targ_Id => Empty,
4443 Unit_Id => Spec_Id)
4444 then
4445 return;
4446 end if;
4447
4448 -- Prevent multiple attempts to install the same ABE check
4449
4450 Disable_Elaboration_Checks (Disable);
4451
4452 Install_Unit_ABE_Check_Common
4453 (N => N,
4454 Unit_Id => Unit_Id);
4455 end Install_Unit_ABE_Check;
4456
4457 ----------------------------
4458 -- Install_Unit_ABE_Check --
4459 ----------------------------
4460
4461 procedure Install_Unit_ABE_Check
4462 (N : Node_Id;
4463 Unit_Id : Entity_Id;
4464 Disable : Target_Rep_Id)
4465 is
4466 Spec_Id : constant Entity_Id := Unique_Entity (Unit_Id);
4467
4468 begin
4469 -- Nothing to do when the scenario does not require an ABE check
4470
4471 if not ABE_Check_Or_Failure_OK
4472 (N => N,
4473 Targ_Id => Empty,
4474 Unit_Id => Spec_Id)
4475 then
4476 return;
4477 end if;
4478
4479 -- Prevent multiple attempts to install the same ABE check
4480
4481 Disable_Elaboration_Checks (Disable);
4482
4483 Install_Unit_ABE_Check_Common
4484 (N => N,
4485 Unit_Id => Unit_Id);
4486 end Install_Unit_ABE_Check;
4487
4488 -----------------------------------
4489 -- Install_Unit_ABE_Check_Common --
4490 -----------------------------------
4491
4492 procedure Install_Unit_ABE_Check_Common
4493 (N : Node_Id;
4494 Unit_Id : Entity_Id)
4495 is
4496 Loc : constant Source_Ptr := Sloc (N);
4497 Spec_Id : constant Entity_Id := Unique_Entity (Unit_Id);
4498
4499 begin
4500 -- Generate:
4501 -- if not Spec_Id'Elaborated then
4502 -- raise Program_Error with "access before elaboration";
4503 -- end if;
4504
4505 Insert_ABE_Check_Or_Failure
4506 (N => N,
4507 Check =>
4508 Make_Raise_Program_Error (Loc,
4509 Condition =>
4510 Make_Op_Not (Loc,
4511 Right_Opnd =>
4512 Make_Attribute_Reference (Loc,
4513 Prefix => New_Occurrence_Of (Spec_Id, Loc),
4514 Attribute_Name => Name_Elaborated)),
4515 Reason => PE_Access_Before_Elaboration));
4516 end Install_Unit_ABE_Check_Common;
4517 end Check_Installer;
4518
4519 ----------------------
4520 -- Compilation_Unit --
4521 ----------------------
4522
4523 function Compilation_Unit (Unit_Id : Entity_Id) return Node_Id is
4524 Comp_Unit : Node_Id;
4525
4526 begin
4527 Comp_Unit := Parent (Unit_Id);
4528
4529 -- Handle the case where a concurrent subunit is rewritten as a null
4530 -- statement due to expansion activities.
4531
4532 if Nkind (Comp_Unit) = N_Null_Statement
4533 and then Nkind_In (Original_Node (Comp_Unit), N_Protected_Body,
4534 N_Task_Body)
4535 then
4536 Comp_Unit := Parent (Comp_Unit);
4537 pragma Assert (Nkind (Comp_Unit) = N_Subunit);
4538
4539 -- Otherwise use the declaration node of the unit
4540
4541 else
4542 Comp_Unit := Parent (Unit_Declaration_Node (Unit_Id));
4543 end if;
4544
4545 -- Handle the case where a subprogram instantiation which acts as a
4546 -- compilation unit is expanded into an anonymous package that wraps
4547 -- the instantiated subprogram.
4548
4549 if Nkind (Comp_Unit) = N_Package_Specification
4550 and then Nkind_In (Original_Node (Parent (Comp_Unit)),
4551 N_Function_Instantiation,
4552 N_Procedure_Instantiation)
4553 then
4554 Comp_Unit := Parent (Parent (Comp_Unit));
4555
4556 -- Handle the case where the compilation unit is a subunit
4557
4558 elsif Nkind (Comp_Unit) = N_Subunit then
4559 Comp_Unit := Parent (Comp_Unit);
4560 end if;
4561
4562 pragma Assert (Nkind (Comp_Unit) = N_Compilation_Unit);
4563
4564 return Comp_Unit;
4565 end Compilation_Unit;
4566
4567 -------------------------------
4568 -- Conditional_ABE_Processor --
4569 -------------------------------
4570
4571 package body Conditional_ABE_Processor is
4572
4573 -----------------------
4574 -- Local subprograms --
4575 -----------------------
4576
4577 function Is_Conditional_ABE_Scenario (N : Node_Id) return Boolean;
4578 pragma Inline (Is_Conditional_ABE_Scenario);
4579 -- Determine whether node N is a suitable scenario for conditional ABE
4580 -- checks and diagnostics.
4581
4582 procedure Process_Conditional_ABE_Access_Taken
4583 (Attr : Node_Id;
4584 Attr_Rep : Scenario_Rep_Id;
4585 In_State : Processing_In_State);
4586 pragma Inline (Process_Conditional_ABE_Access_Taken);
4587 -- Perform ABE checks and diagnostics for attribute reference Attr with
4588 -- representation Attr_Rep which takes 'Access of an entry, operator, or
4589 -- subprogram. In_State is the current state of the Processing phase.
4590
4591 procedure Process_Conditional_ABE_Activation
4592 (Call : Node_Id;
4593 Call_Rep : Scenario_Rep_Id;
4594 Obj_Id : Entity_Id;
4595 Obj_Rep : Target_Rep_Id;
4596 Task_Typ : Entity_Id;
4597 Task_Rep : Target_Rep_Id;
4598 In_State : Processing_In_State);
4599 pragma Inline (Process_Conditional_ABE_Activation);
4600 -- Perform common conditional ABE checks and diagnostics for activation
4601 -- call Call which activates object Obj_Id of task type Task_Typ. Formal
4602 -- Call_Rep denotes the representation of the call. Obj_Rep denotes the
4603 -- representation of the object. Task_Rep denotes the representation of
4604 -- the task type. In_State is the current state of the Processing phase.
4605
4606 procedure Process_Conditional_ABE_Call
4607 (Call : Node_Id;
4608 Call_Rep : Scenario_Rep_Id;
4609 In_State : Processing_In_State);
4610 pragma Inline (Process_Conditional_ABE_Call);
4611 -- Top-level dispatcher for processing of calls. Perform ABE checks and
4612 -- diagnostics for call Call with representation Call_Rep. In_State is
4613 -- the current state of the Processing phase.
4614
4615 procedure Process_Conditional_ABE_Call_Ada
4616 (Call : Node_Id;
4617 Call_Rep : Scenario_Rep_Id;
4618 Subp_Id : Entity_Id;
4619 Subp_Rep : Target_Rep_Id;
4620 In_State : Processing_In_State);
4621 pragma Inline (Process_Conditional_ABE_Call_Ada);
4622 -- Perform ABE checks and diagnostics for call Call which invokes entry,
4623 -- operator, or subprogram Subp_Id using the Ada rules. Call_Rep denotes
4624 -- the representation of the call. Subp_Rep denotes the representation
4625 -- of the subprogram. In_State is the current state of the Processing
4626 -- phase.
4627
4628 procedure Process_Conditional_ABE_Call_SPARK
4629 (Call : Node_Id;
4630 Call_Rep : Scenario_Rep_Id;
4631 Subp_Id : Entity_Id;
4632 Subp_Rep : Target_Rep_Id;
4633 In_State : Processing_In_State);
4634 pragma Inline (Process_Conditional_ABE_Call_SPARK);
4635 -- Perform ABE checks and diagnostics for call Call which invokes entry,
4636 -- operator, or subprogram Subp_Id using the SPARK rules. Call_Rep is
4637 -- the representation of the call. Subp_Rep denotes the representation
4638 -- of the subprogram. In_State is the current state of the Processing
4639 -- phase.
4640
4641 procedure Process_Conditional_ABE_Instantiation
4642 (Inst : Node_Id;
4643 Inst_Rep : Scenario_Rep_Id;
4644 In_State : Processing_In_State);
4645 pragma Inline (Process_Conditional_ABE_Instantiation);
4646 -- Top-level dispatcher for processing of instantiations. Perform ABE
4647 -- checks and diagnostics for instantiation Inst with representation
4648 -- Inst_Rep. In_State is the current state of the Processing phase.
4649
4650 procedure Process_Conditional_ABE_Instantiation_Ada
4651 (Inst : Node_Id;
4652 Inst_Rep : Scenario_Rep_Id;
4653 Gen_Id : Entity_Id;
4654 Gen_Rep : Target_Rep_Id;
4655 In_State : Processing_In_State);
4656 pragma Inline (Process_Conditional_ABE_Instantiation_Ada);
4657 -- Perform ABE checks and diagnostics for instantiation Inst of generic
4658 -- Gen_Id using the Ada rules. Inst_Rep denotes the representation of
4659 -- the instnace. Gen_Rep is the representation of the generic. In_State
4660 -- is the current state of the Processing phase.
4661
4662 procedure Process_Conditional_ABE_Instantiation_SPARK
4663 (Inst : Node_Id;
4664 Inst_Rep : Scenario_Rep_Id;
4665 Gen_Id : Entity_Id;
4666 Gen_Rep : Target_Rep_Id;
4667 In_State : Processing_In_State);
4668 pragma Inline (Process_Conditional_ABE_Instantiation_SPARK);
4669 -- Perform ABE checks and diagnostics for instantiation Inst of generic
4670 -- Gen_Id using the SPARK rules. Inst_Rep denotes the representation of
4671 -- the instnace. Gen_Rep is the representation of the generic. In_State
4672 -- is the current state of the Processing phase.
4673
4674 procedure Process_Conditional_ABE_Variable_Assignment
4675 (Asmt : Node_Id;
4676 Asmt_Rep : Scenario_Rep_Id;
4677 In_State : Processing_In_State);
4678 pragma Inline (Process_Conditional_ABE_Variable_Assignment);
4679 -- Top-level dispatcher for processing of variable assignments. Perform
4680 -- ABE checks and diagnostics for assignment Asmt with representation
4681 -- Asmt_Rep. In_State denotes the current state of the Processing phase.
4682
4683 procedure Process_Conditional_ABE_Variable_Assignment_Ada
4684 (Asmt : Node_Id;
4685 Asmt_Rep : Scenario_Rep_Id;
4686 Var_Id : Entity_Id;
4687 Var_Rep : Target_Rep_Id;
4688 In_State : Processing_In_State);
4689 pragma Inline (Process_Conditional_ABE_Variable_Assignment_Ada);
4690 -- Perform ABE checks and diagnostics for assignment statement Asmt that
4691 -- modifies the value of variable Var_Id using the Ada rules. Asmt_Rep
4692 -- denotes the representation of the assignment. Var_Rep denotes the
4693 -- representation of the variable. In_State is the current state of the
4694 -- Processing phase.
4695
4696 procedure Process_Conditional_ABE_Variable_Assignment_SPARK
4697 (Asmt : Node_Id;
4698 Asmt_Rep : Scenario_Rep_Id;
4699 Var_Id : Entity_Id;
4700 Var_Rep : Target_Rep_Id;
4701 In_State : Processing_In_State);
4702 pragma Inline (Process_Conditional_ABE_Variable_Assignment_SPARK);
4703 -- Perform ABE checks and diagnostics for assignment statement Asmt that
4704 -- modifies the value of variable Var_Id using the SPARK rules. Asmt_Rep
4705 -- denotes the representation of the assignment. Var_Rep denotes the
4706 -- representation of the variable. In_State is the current state of the
4707 -- Processing phase.
4708
4709 procedure Process_Conditional_ABE_Variable_Reference
4710 (Ref : Node_Id;
4711 Ref_Rep : Scenario_Rep_Id;
4712 In_State : Processing_In_State);
4713 pragma Inline (Process_Conditional_ABE_Variable_Reference);
4714 -- Perform ABE checks and diagnostics for variable reference Ref with
4715 -- representation Ref_Rep. In_State denotes the current state of the
4716 -- Processing phase.
4717
4718 procedure Traverse_Conditional_ABE_Body
4719 (N : Node_Id;
4720 In_State : Processing_In_State);
4721 pragma Inline (Traverse_Conditional_ABE_Body);
4722 -- Traverse subprogram body N looking for suitable scenarios that need
4723 -- to be processed for conditional ABE checks and diagnostics. In_State
4724 -- is the current state of the Processing phase.
4725
4726 -------------------------------------
4727 -- Check_Conditional_ABE_Scenarios --
4728 -------------------------------------
4729
4730 procedure Check_Conditional_ABE_Scenarios
4731 (Iter : in out NE_Set.Iterator)
4732 is
4733 N : Node_Id;
4734
4735 begin
4736 while NE_Set.Has_Next (Iter) loop
4737 NE_Set.Next (Iter, N);
4738
4739 -- Reset the traversed status of all subprogram bodies because the
4740 -- current conditional scenario acts as a new DFS traversal root.
4741
4742 Reset_Traversed_Bodies;
4743
4744 Process_Conditional_ABE
4745 (N => N,
4746 In_State => Conditional_ABE_State);
4747 end loop;
4748 end Check_Conditional_ABE_Scenarios;
4749
4750 ---------------------------------
4751 -- Is_Conditional_ABE_Scenario --
4752 ---------------------------------
4753
4754 function Is_Conditional_ABE_Scenario (N : Node_Id) return Boolean is
4755 begin
4756 return
4757 Is_Suitable_Access_Taken (N)
4758 or else Is_Suitable_Call (N)
4759 or else Is_Suitable_Instantiation (N)
4760 or else Is_Suitable_Variable_Assignment (N)
4761 or else Is_Suitable_Variable_Reference (N);
4762 end Is_Conditional_ABE_Scenario;
4763
4764 -----------------------------
4765 -- Process_Conditional_ABE --
4766 -----------------------------
4767
4768 procedure Process_Conditional_ABE
4769 (N : Node_Id;
4770 In_State : Processing_In_State)
4771 is
4772 Scen : constant Node_Id := Scenario (N);
4773 Scen_Rep : Scenario_Rep_Id;
4774
4775 begin
4776 -- Add the current scenario to the stack of active scenarios
4777
4778 Push_Active_Scenario (Scen);
4779
4780 -- 'Access
4781
4782 if Is_Suitable_Access_Taken (Scen) then
4783 Process_Conditional_ABE_Access_Taken
4784 (Attr => Scen,
4785 Attr_Rep => Scenario_Representation_Of (Scen, In_State),
4786 In_State => In_State);
4787
4788 -- Call or task activation
4789
4790 elsif Is_Suitable_Call (Scen) then
4791 Scen_Rep := Scenario_Representation_Of (Scen, In_State);
4792
4793 -- Routine Build_Call_Marker creates call markers regardless of
4794 -- whether the call occurs within the main unit or not. This way
4795 -- the serialization of internal names is kept consistent. Only
4796 -- call markers found within the main unit must be processed.
4797
4798 if In_Main_Context (Scen) then
4799 Scen_Rep := Scenario_Representation_Of (Scen, In_State);
4800
4801 if Kind (Scen_Rep) = Call_Scenario then
4802 Process_Conditional_ABE_Call
4803 (Call => Scen,
4804 Call_Rep => Scen_Rep,
4805 In_State => In_State);
4806
4807 else
4808 pragma Assert (Kind (Scen_Rep) = Task_Activation_Scenario);
4809
4810 Process_Activation
4811 (Call => Scen,
4812 Call_Rep => Scen_Rep,
4813 Processor => Process_Conditional_ABE_Activation'Access,
4814 In_State => In_State);
4815 end if;
4816 end if;
4817
4818 -- Instantiation
4819
4820 elsif Is_Suitable_Instantiation (Scen) then
4821 Process_Conditional_ABE_Instantiation
4822 (Inst => Scen,
4823 Inst_Rep => Scenario_Representation_Of (Scen, In_State),
4824 In_State => In_State);
4825
4826 -- Variable assignments
4827
4828 elsif Is_Suitable_Variable_Assignment (Scen) then
4829 Process_Conditional_ABE_Variable_Assignment
4830 (Asmt => Scen,
4831 Asmt_Rep => Scenario_Representation_Of (Scen, In_State),
4832 In_State => In_State);
4833
4834 -- Variable references
4835
4836 elsif Is_Suitable_Variable_Reference (Scen) then
4837
4838 -- Routine Build_Variable_Reference_Marker makes variable markers
4839 -- regardless of whether the reference occurs within the main unit
4840 -- or not. This way the serialization of internal names is kept
4841 -- consistent. Only variable markers within the main unit must be
4842 -- processed.
4843
4844 if In_Main_Context (Scen) then
4845 Process_Conditional_ABE_Variable_Reference
4846 (Ref => Scen,
4847 Ref_Rep => Scenario_Representation_Of (Scen, In_State),
4848 In_State => In_State);
4849 end if;
4850 end if;
4851
4852 -- Remove the current scenario from the stack of active scenarios
4853 -- once all ABE diagnostics and checks have been performed.
4854
4855 Pop_Active_Scenario (Scen);
4856 end Process_Conditional_ABE;
4857
4858 ------------------------------------------
4859 -- Process_Conditional_ABE_Access_Taken --
4860 ------------------------------------------
4861
4862 procedure Process_Conditional_ABE_Access_Taken
4863 (Attr : Node_Id;
4864 Attr_Rep : Scenario_Rep_Id;
4865 In_State : Processing_In_State)
4866 is
4867 function Build_Access_Marker (Subp_Id : Entity_Id) return Node_Id;
4868 pragma Inline (Build_Access_Marker);
4869 -- Create a suitable call marker which invokes subprogram Subp_Id
4870
4871 -------------------------
4872 -- Build_Access_Marker --
4873 -------------------------
4874
4875 function Build_Access_Marker (Subp_Id : Entity_Id) return Node_Id is
4876 Marker : Node_Id;
4877
4878 begin
4879 Marker := Make_Call_Marker (Sloc (Attr));
4880
4881 -- Inherit relevant attributes from the attribute
4882
4883 Set_Target (Marker, Subp_Id);
4884 Set_Is_Declaration_Level_Node
4885 (Marker, Level (Attr_Rep) = Declaration_Level);
4886 Set_Is_Dispatching_Call
4887 (Marker, False);
4888 Set_Is_Elaboration_Checks_OK_Node
4889 (Marker, Elaboration_Checks_OK (Attr_Rep));
4890 Set_Is_Elaboration_Warnings_OK_Node
4891 (Marker, Elaboration_Warnings_OK (Attr_Rep));
4892 Set_Is_Source_Call
4893 (Marker, Comes_From_Source (Attr));
4894 Set_Is_SPARK_Mode_On_Node
4895 (Marker, SPARK_Mode_Of (Attr_Rep) = Is_On);
4896
4897 -- Partially insert the call marker into the tree by setting its
4898 -- parent pointer.
4899
4900 Set_Parent (Marker, Attr);
4901
4902 return Marker;
4903 end Build_Access_Marker;
4904
4905 -- Local variables
4906
4907 Root : constant Node_Id := Root_Scenario;
4908 Subp_Id : constant Entity_Id := Target (Attr_Rep);
4909 Subp_Rep : constant Target_Rep_Id :=
4910 Target_Representation_Of (Subp_Id, In_State);
4911 Body_Decl : constant Node_Id := Body_Declaration (Subp_Rep);
4912
4913 New_In_State : Processing_In_State := In_State;
4914 -- Each step of the Processing phase constitutes a new state
4915
4916 -- Start of processing for Process_Conditional_ABE_Access
4917
4918 begin
4919 -- Output relevant information when switch -gnatel (info messages on
4920 -- implicit Elaborate[_All] pragmas) is in effect.
4921
4922 if Elab_Info_Messages
4923 and then not New_In_State.Suppress_Info_Messages
4924 then
4925 Error_Msg_NE
4926 ("info: access to & during elaboration", Attr, Subp_Id);
4927 end if;
4928
4929 -- Warnings are suppressed when a prior scenario is already in that
4930 -- mode or when the attribute or the target have warnings suppressed.
4931 -- Update the state of the Processing phase to reflect this.
4932
4933 New_In_State.Suppress_Warnings :=
4934 New_In_State.Suppress_Warnings
4935 or else not Elaboration_Warnings_OK (Attr_Rep)
4936 or else not Elaboration_Warnings_OK (Subp_Rep);
4937
4938 -- Do not emit any ABE diagnostics when the current or previous
4939 -- scenario in this traversal has suppressed elaboration warnings.
4940
4941 if New_In_State.Suppress_Warnings then
4942 null;
4943
4944 -- Both the attribute and the corresponding subprogram body are in
4945 -- the same unit. The body must appear prior to the root scenario
4946 -- which started the recursive search. If this is not the case, then
4947 -- there is a potential ABE if the access value is used to call the
4948 -- subprogram. Emit a warning only when switch -gnatw.f (warnings on
4949 -- suspucious 'Access) is in effect.
4950
4951 elsif Warn_On_Elab_Access
4952 and then Present (Body_Decl)
4953 and then In_Extended_Main_Code_Unit (Body_Decl)
4954 and then Earlier_In_Extended_Unit (Root, Body_Decl)
4955 then
4956 Error_Msg_Name_1 := Attribute_Name (Attr);
4957 Error_Msg_NE
4958 ("??% attribute of & before body seen", Attr, Subp_Id);
4959 Error_Msg_N ("\possible Program_Error on later references", Attr);
4960
4961 Output_Active_Scenarios (Attr, New_In_State);
4962 end if;
4963
4964 -- Treat the attribute an an immediate invocation of the target when
4965 -- switch -gnatd.o (conservative elaboration order for indirect
4966 -- calls) is in effect. This has the following desirable effects:
4967 --
4968 -- * Ensure that the unit with the corresponding body is elaborated
4969 -- prior to the main unit.
4970 --
4971 -- * Perform conditional ABE checks and diagnostics
4972 --
4973 -- * Traverse the body of the target (if available)
4974
4975 if Debug_Flag_Dot_O then
4976 Process_Conditional_ABE
4977 (N => Build_Access_Marker (Subp_Id),
4978 In_State => New_In_State);
4979
4980 -- Otherwise ensure that the unit with the corresponding body is
4981 -- elaborated prior to the main unit.
4982
4983 else
4984 Ensure_Prior_Elaboration
4985 (N => Attr,
4986 Unit_Id => Unit (Subp_Rep),
4987 Prag_Nam => Name_Elaborate_All,
4988 In_State => New_In_State);
4989 end if;
4990 end Process_Conditional_ABE_Access_Taken;
4991
4992 ----------------------------------------
4993 -- Process_Conditional_ABE_Activation --
4994 ----------------------------------------
4995
4996 procedure Process_Conditional_ABE_Activation
4997 (Call : Node_Id;
4998 Call_Rep : Scenario_Rep_Id;
4999 Obj_Id : Entity_Id;
5000 Obj_Rep : Target_Rep_Id;
5001 Task_Typ : Entity_Id;
5002 Task_Rep : Target_Rep_Id;
5003 In_State : Processing_In_State)
5004 is
5005 pragma Unreferenced (Task_Typ);
5006
5007 Body_Decl : constant Node_Id := Body_Declaration (Task_Rep);
5008 Spec_Decl : constant Node_Id := Spec_Declaration (Task_Rep);
5009 Root : constant Node_Id := Root_Scenario;
5010 Unit_Id : constant Node_Id := Unit (Task_Rep);
5011
5012 Check_OK : constant Boolean :=
5013 not In_State.Suppress_Checks
5014 and then Ghost_Mode_Of (Obj_Rep) /= Is_Ignored
5015 and then Ghost_Mode_Of (Task_Rep) /= Is_Ignored
5016 and then Elaboration_Checks_OK (Obj_Rep)
5017 and then Elaboration_Checks_OK (Task_Rep);
5018 -- A run-time ABE check may be installed only when the object and the
5019 -- task type have active elaboration checks, and both are not ignored
5020 -- Ghost constructs.
5021
5022 New_In_State : Processing_In_State := In_State;
5023 -- Each step of the Processing phase constitutes a new state
5024
5025 begin
5026 -- Output relevant information when switch -gnatel (info messages on
5027 -- implicit Elaborate[_All] pragmas) is in effect.
5028
5029 if Elab_Info_Messages
5030 and then not New_In_State.Suppress_Info_Messages
5031 then
5032 Error_Msg_NE
5033 ("info: activation of & during elaboration", Call, Obj_Id);
5034 end if;
5035
5036 -- Nothing to do when the call activates a task whose type is defined
5037 -- within an instance and switch -gnatd_i (ignore activations and
5038 -- calls to instances for elaboration) is in effect.
5039
5040 if Debug_Flag_Underscore_I
5041 and then In_External_Instance
5042 (N => Call,
5043 Target_Decl => Spec_Decl)
5044 then
5045 return;
5046
5047 -- Nothing to do when the activation is a guaranteed ABE
5048
5049 elsif Is_Known_Guaranteed_ABE (Call) then
5050 return;
5051
5052 -- Nothing to do when the root scenario appears at the declaration
5053 -- level and the task is in the same unit, but outside this context.
5054 --
5055 -- task type Task_Typ; -- task declaration
5056 --
5057 -- procedure Proc is
5058 -- function A ... is
5059 -- begin
5060 -- if Some_Condition then
5061 -- declare
5062 -- T : Task_Typ;
5063 -- begin
5064 -- <activation call> -- activation site
5065 -- end;
5066 -- ...
5067 -- end A;
5068 --
5069 -- X : ... := A; -- root scenario
5070 -- ...
5071 --
5072 -- task body Task_Typ is
5073 -- ...
5074 -- end Task_Typ;
5075 --
5076 -- In the example above, the context of X is the declarative list of
5077 -- Proc. The "elaboration" of X may reach the activation of T whose
5078 -- body is defined outside of X's context. The task body is relevant
5079 -- only when Proc is invoked, but this happens only during "normal"
5080 -- elaboration, therefore the task body must not be considered if
5081 -- this is not the case.
5082
5083 elsif Is_Up_Level_Target
5084 (Targ_Decl => Spec_Decl,
5085 In_State => New_In_State)
5086 then
5087 return;
5088
5089 -- Nothing to do when the activation is ABE-safe
5090 --
5091 -- generic
5092 -- package Gen is
5093 -- task type Task_Typ;
5094 -- end Gen;
5095 --
5096 -- package body Gen is
5097 -- task body Task_Typ is
5098 -- begin
5099 -- ...
5100 -- end Task_Typ;
5101 -- end Gen;
5102 --
5103 -- with Gen;
5104 -- procedure Main is
5105 -- package Nested is
5106 -- package Inst is new Gen;
5107 -- T : Inst.Task_Typ;
5108 -- <activation call> -- safe activation
5109 -- end Nested;
5110 -- ...
5111
5112 elsif Is_Safe_Activation (Call, Task_Rep) then
5113
5114 -- Note that the task body must still be examined for any nested
5115 -- scenarios.
5116
5117 null;
5118
5119 -- The activation call and the task body are both in the main unit
5120 --
5121 -- If the root scenario appears prior to the task body, then this is
5122 -- a possible ABE with respect to the root scenario.
5123 --
5124 -- task type Task_Typ;
5125 --
5126 -- function A ... is
5127 -- begin
5128 -- if Some_Condition then
5129 -- declare
5130 -- package Pack is
5131 -- T : Task_Typ;
5132 -- end Pack; -- activation of T
5133 -- ...
5134 -- end A;
5135 --
5136 -- X : ... := A; -- root scenario
5137 --
5138 -- task body Task_Typ is -- task body
5139 -- ...
5140 -- end Task_Typ;
5141 --
5142 -- Y : ... := A; -- root scenario
5143 --
5144 -- IMPORTANT: The activation of T is a possible ABE for X, but
5145 -- not for Y. Intalling an unconditional ABE raise prior to the
5146 -- activation call would be wrong as it will fail for Y as well
5147 -- but in Y's case the activation of T is never an ABE.
5148
5149 elsif Present (Body_Decl)
5150 and then In_Extended_Main_Code_Unit (Body_Decl)
5151 then
5152 if Earlier_In_Extended_Unit (Root, Body_Decl) then
5153
5154 -- Do not emit any ABE diagnostics when a previous scenario in
5155 -- this traversal has suppressed elaboration warnings.
5156
5157 if New_In_State.Suppress_Warnings then
5158 null;
5159
5160 -- Do not emit any ABE diagnostics when the activation occurs
5161 -- in a partial finalization context because this action leads
5162 -- to confusing noise.
5163
5164 elsif New_In_State.Within_Partial_Finalization then
5165 null;
5166
5167 -- Otherwise emit the ABE disgnostic
5168
5169 else
5170 Error_Msg_Sloc := Sloc (Call);
5171 Error_Msg_N
5172 ("??task & will be activated # before elaboration of its "
5173 & "body", Obj_Id);
5174 Error_Msg_N
5175 ("\Program_Error may be raised at run time", Obj_Id);
5176
5177 Output_Active_Scenarios (Obj_Id, New_In_State);
5178 end if;
5179
5180 -- Install a conditional run-time ABE check to verify that the
5181 -- task body has been elaborated prior to the activation call.
5182
5183 if Check_OK then
5184 Install_Scenario_ABE_Check
5185 (N => Call,
5186 Targ_Id => Defining_Entity (Spec_Decl),
5187 Targ_Rep => Task_Rep,
5188 Disable => Obj_Rep);
5189
5190 -- Update the state of the Processing phase to indicate that
5191 -- no implicit Elaborate[_All] pragma must be generated from
5192 -- this point on.
5193 --
5194 -- task type Task_Typ;
5195 --
5196 -- function A ... is
5197 -- begin
5198 -- if Some_Condition then
5199 -- declare
5200 -- package Pack is
5201 -- <ABE check>
5202 -- T : Task_Typ;
5203 -- end Pack; -- activation of T
5204 -- ...
5205 -- end A;
5206 --
5207 -- X : ... := A;
5208 --
5209 -- task body Task_Typ is
5210 -- begin
5211 -- External.Subp; -- imparts Elaborate_All
5212 -- end Task_Typ;
5213 --
5214 -- If Some_Condition is True, then the ABE check will fail
5215 -- at runtime and the call to External.Subp will never take
5216 -- place, rendering the implicit Elaborate_All useless.
5217 --
5218 -- If the value of Some_Condition is False, then the call
5219 -- to External.Subp will never take place, rendering the
5220 -- implicit Elaborate_All useless.
5221
5222 New_In_State.Suppress_Implicit_Pragmas := True;
5223 end if;
5224 end if;
5225
5226 -- Otherwise the task body is not available in this compilation or
5227 -- it resides in an external unit. Install a run-time ABE check to
5228 -- verify that the task body has been elaborated prior to the
5229 -- activation call when the dynamic model is in effect.
5230
5231 elsif Check_OK
5232 and then New_In_State.Processing = Dynamic_Model_Processing
5233 then
5234 Install_Unit_ABE_Check
5235 (N => Call,
5236 Unit_Id => Unit_Id,
5237 Disable => Obj_Rep);
5238 end if;
5239
5240 -- Both the activation call and task type are subject to SPARK_Mode
5241 -- On, this triggers the SPARK rules for task activation. Compared
5242 -- to calls and instantiations, task activation in SPARK does not
5243 -- require the presence of Elaborate[_All] pragmas in case the task
5244 -- type is defined outside the main unit. This is because SPARK uses
5245 -- a special policy which activates all tasks after the main unit has
5246 -- finished its elaboration.
5247
5248 if SPARK_Mode_Of (Call_Rep) = Is_On
5249 and then SPARK_Mode_Of (Task_Rep) = Is_On
5250 then
5251 null;
5252
5253 -- Otherwise the Ada rules are in effect. Ensure that the unit with
5254 -- the task body is elaborated prior to the main unit.
5255
5256 else
5257 Ensure_Prior_Elaboration
5258 (N => Call,
5259 Unit_Id => Unit_Id,
5260 Prag_Nam => Name_Elaborate_All,
5261 In_State => New_In_State);
5262 end if;
5263
5264 Traverse_Conditional_ABE_Body
5265 (N => Body_Decl,
5266 In_State => New_In_State);
5267 end Process_Conditional_ABE_Activation;
5268
5269 ----------------------------------
5270 -- Process_Conditional_ABE_Call --
5271 ----------------------------------
5272
5273 procedure Process_Conditional_ABE_Call
5274 (Call : Node_Id;
5275 Call_Rep : Scenario_Rep_Id;
5276 In_State : Processing_In_State)
5277 is
5278 function In_Initialization_Context (N : Node_Id) return Boolean;
5279 pragma Inline (In_Initialization_Context);
5280 -- Determine whether arbitrary node N appears within a type init
5281 -- proc, primitive [Deep_]Initialize, or a block created for
5282 -- initialization purposes.
5283
5284 function Is_Partial_Finalization_Proc
5285 (Subp_Id : Entity_Id) return Boolean;
5286 pragma Inline (Is_Partial_Finalization_Proc);
5287 -- Determine whether subprogram Subp_Id is a partial finalization
5288 -- procedure.
5289
5290 -------------------------------
5291 -- In_Initialization_Context --
5292 -------------------------------
5293
5294 function In_Initialization_Context (N : Node_Id) return Boolean is
5295 Par : Node_Id;
5296 Spec_Id : Entity_Id;
5297
5298 begin
5299 -- Climb the parent chain looking for initialization actions
5300
5301 Par := Parent (N);
5302 while Present (Par) loop
5303
5304 -- A block may be part of the initialization actions of a
5305 -- default initialized object.
5306
5307 if Nkind (Par) = N_Block_Statement
5308 and then Is_Initialization_Block (Par)
5309 then
5310 return True;
5311
5312 -- A subprogram body may denote an initialization routine
5313
5314 elsif Nkind (Par) = N_Subprogram_Body then
5315 Spec_Id := Unique_Defining_Entity (Par);
5316
5317 -- The current subprogram body denotes a type init proc or
5318 -- primitive [Deep_]Initialize.
5319
5320 if Is_Init_Proc (Spec_Id)
5321 or else Is_Controlled_Proc (Spec_Id, Name_Initialize)
5322 or else Is_TSS (Spec_Id, TSS_Deep_Initialize)
5323 then
5324 return True;
5325 end if;
5326
5327 -- Prevent the search from going too far
5328
5329 elsif Is_Body_Or_Package_Declaration (Par) then
5330 exit;
5331 end if;
5332
5333 Par := Parent (Par);
5334 end loop;
5335
5336 return False;
5337 end In_Initialization_Context;
5338
5339 ----------------------------------
5340 -- Is_Partial_Finalization_Proc --
5341 ----------------------------------
5342
5343 function Is_Partial_Finalization_Proc
5344 (Subp_Id : Entity_Id) return Boolean
5345 is
5346 begin
5347 -- To qualify, the subprogram must denote a finalizer procedure
5348 -- or primitive [Deep_]Finalize, and the call must appear within
5349 -- an initialization context.
5350
5351 return
5352 (Is_Controlled_Proc (Subp_Id, Name_Finalize)
5353 or else Is_Finalizer_Proc (Subp_Id)
5354 or else Is_TSS (Subp_Id, TSS_Deep_Finalize))
5355 and then In_Initialization_Context (Call);
5356 end Is_Partial_Finalization_Proc;
5357
5358 -- Local variables
5359
5360 Subp_Id : constant Entity_Id := Target (Call_Rep);
5361 Subp_Rep : constant Target_Rep_Id :=
5362 Target_Representation_Of (Subp_Id, In_State);
5363 Subp_Decl : constant Node_Id := Spec_Declaration (Subp_Rep);
5364
5365 SPARK_Rules_On : constant Boolean :=
5366 SPARK_Mode_Of (Call_Rep) = Is_On
5367 and then SPARK_Mode_Of (Subp_Rep) = Is_On;
5368
5369 New_In_State : Processing_In_State := In_State;
5370 -- Each step of the Processing phase constitutes a new state
5371
5372 -- Start of processing for Process_Conditional_ABE_Call
5373
5374 begin
5375 -- Output relevant information when switch -gnatel (info messages on
5376 -- implicit Elaborate[_All] pragmas) is in effect.
5377
5378 if Elab_Info_Messages
5379 and then not New_In_State.Suppress_Info_Messages
5380 then
5381 Info_Call
5382 (Call => Call,
5383 Subp_Id => Subp_Id,
5384 Info_Msg => True,
5385 In_SPARK => SPARK_Rules_On);
5386 end if;
5387
5388 -- Check whether the invocation of an entry clashes with an existing
5389 -- restriction. This check is relevant only when the processing was
5390 -- started from some library-level scenario.
5391
5392 if Is_Protected_Entry (Subp_Id) then
5393 Check_Restriction (No_Entry_Calls_In_Elaboration_Code, Call);
5394
5395 elsif Is_Task_Entry (Subp_Id) then
5396 Check_Restriction (No_Entry_Calls_In_Elaboration_Code, Call);
5397
5398 -- Task entry calls are never processed because the entry being
5399 -- invoked does not have a corresponding "body", it has a select.
5400
5401 return;
5402 end if;
5403
5404 -- Nothing to do when the call invokes a target defined within an
5405 -- instance and switch -gnatd_i (ignore activations and calls to
5406 -- instances for elaboration) is in effect.
5407
5408 if Debug_Flag_Underscore_I
5409 and then In_External_Instance
5410 (N => Call,
5411 Target_Decl => Subp_Decl)
5412 then
5413 return;
5414
5415 -- Nothing to do when the call is a guaranteed ABE
5416
5417 elsif Is_Known_Guaranteed_ABE (Call) then
5418 return;
5419
5420 -- Nothing to do when the root scenario appears at the declaration
5421 -- level and the target is in the same unit but outside this context.
5422 --
5423 -- function B ...; -- target declaration
5424 --
5425 -- procedure Proc is
5426 -- function A ... is
5427 -- begin
5428 -- if Some_Condition then
5429 -- return B; -- call site
5430 -- ...
5431 -- end A;
5432 --
5433 -- X : ... := A; -- root scenario
5434 -- ...
5435 --
5436 -- function B ... is
5437 -- ...
5438 -- end B;
5439 --
5440 -- In the example above, the context of X is the declarative region
5441 -- of Proc. The "elaboration" of X may eventually reach B which is
5442 -- defined outside of X's context. B is relevant only when Proc is
5443 -- invoked, but this happens only by means of "normal" elaboration,
5444 -- therefore B must not be considered if this is not the case.
5445
5446 elsif Is_Up_Level_Target
5447 (Targ_Decl => Subp_Decl,
5448 In_State => New_In_State)
5449 then
5450 return;
5451 end if;
5452
5453 -- Warnings are suppressed when a prior scenario is already in that
5454 -- mode, or the call or target have warnings suppressed. Update the
5455 -- state of the Processing phase to reflect this.
5456
5457 New_In_State.Suppress_Warnings :=
5458 New_In_State.Suppress_Warnings
5459 or else not Elaboration_Warnings_OK (Call_Rep)
5460 or else not Elaboration_Warnings_OK (Subp_Rep);
5461
5462 -- The call occurs in an initial condition context when a prior
5463 -- scenario is already in that mode, or when the target is an
5464 -- Initial_Condition procedure. Update the state of the Processing
5465 -- phase to reflect this.
5466
5467 New_In_State.Within_Initial_Condition :=
5468 New_In_State.Within_Initial_Condition
5469 or else Is_Initial_Condition_Proc (Subp_Id);
5470
5471 -- The call occurs in a partial finalization context when a prior
5472 -- scenario is already in that mode, or when the target denotes a
5473 -- [Deep_]Finalize primitive or a finalizer within an initialization
5474 -- context. Update the state of the Processing phase to reflect this.
5475
5476 New_In_State.Within_Partial_Finalization :=
5477 New_In_State.Within_Partial_Finalization
5478 or else Is_Partial_Finalization_Proc (Subp_Id);
5479
5480 -- The SPARK rules are in effect. Note that -gnatd.v (enforce SPARK
5481 -- elaboration rules in SPARK code) is intentionally not taken into
5482 -- account here because Process_Conditional_ABE_Call_SPARK has two
5483 -- separate modes of operation.
5484
5485 if SPARK_Rules_On then
5486 Process_Conditional_ABE_Call_SPARK
5487 (Call => Call,
5488 Call_Rep => Call_Rep,
5489 Subp_Id => Subp_Id,
5490 Subp_Rep => Subp_Rep,
5491 In_State => New_In_State);
5492
5493 -- Otherwise the Ada rules are in effect
5494
5495 else
5496 Process_Conditional_ABE_Call_Ada
5497 (Call => Call,
5498 Call_Rep => Call_Rep,
5499 Subp_Id => Subp_Id,
5500 Subp_Rep => Subp_Rep,
5501 In_State => New_In_State);
5502 end if;
5503
5504 -- Inspect the target body (and barried function) for other suitable
5505 -- elaboration scenarios.
5506
5507 Traverse_Conditional_ABE_Body
5508 (N => Barrier_Body_Declaration (Subp_Rep),
5509 In_State => New_In_State);
5510
5511 Traverse_Conditional_ABE_Body
5512 (N => Body_Declaration (Subp_Rep),
5513 In_State => New_In_State);
5514 end Process_Conditional_ABE_Call;
5515
5516 --------------------------------------
5517 -- Process_Conditional_ABE_Call_Ada --
5518 --------------------------------------
5519
5520 procedure Process_Conditional_ABE_Call_Ada
5521 (Call : Node_Id;
5522 Call_Rep : Scenario_Rep_Id;
5523 Subp_Id : Entity_Id;
5524 Subp_Rep : Target_Rep_Id;
5525 In_State : Processing_In_State)
5526 is
5527 Body_Decl : constant Node_Id := Body_Declaration (Subp_Rep);
5528 Root : constant Node_Id := Root_Scenario;
5529 Unit_Id : constant Node_Id := Unit (Subp_Rep);
5530
5531 Check_OK : constant Boolean :=
5532 not In_State.Suppress_Checks
5533 and then Ghost_Mode_Of (Call_Rep) /= Is_Ignored
5534 and then Ghost_Mode_Of (Subp_Rep) /= Is_Ignored
5535 and then Elaboration_Checks_OK (Call_Rep)
5536 and then Elaboration_Checks_OK (Subp_Rep);
5537 -- A run-time ABE check may be installed only when both the call
5538 -- and the target have active elaboration checks, and both are not
5539 -- ignored Ghost constructs.
5540
5541 New_In_State : Processing_In_State := In_State;
5542 -- Each step of the Processing phase constitutes a new state
5543
5544 begin
5545 -- Nothing to do for an Ada dispatching call because there are no
5546 -- ABE diagnostics for either models. ABE checks for the dynamic
5547 -- model are handled by Install_Primitive_Elaboration_Check.
5548
5549 if Is_Dispatching_Call (Call_Rep) then
5550 return;
5551
5552 -- Nothing to do when the call is ABE-safe
5553 --
5554 -- generic
5555 -- function Gen ...;
5556 --
5557 -- function Gen ... is
5558 -- begin
5559 -- ...
5560 -- end Gen;
5561 --
5562 -- with Gen;
5563 -- procedure Main is
5564 -- function Inst is new Gen;
5565 -- X : ... := Inst; -- safe call
5566 -- ...
5567
5568 elsif Is_Safe_Call (Call, Subp_Id, Subp_Rep) then
5569 return;
5570
5571 -- The call and the target body are both in the main unit
5572 --
5573 -- If the root scenario appears prior to the target body, then this
5574 -- is a possible ABE with respect to the root scenario.
5575 --
5576 -- function B ...;
5577 --
5578 -- function A ... is
5579 -- begin
5580 -- if Some_Condition then
5581 -- return B; -- call site
5582 -- ...
5583 -- end A;
5584 --
5585 -- X : ... := A; -- root scenario
5586 --
5587 -- function B ... is -- target body
5588 -- ...
5589 -- end B;
5590 --
5591 -- Y : ... := A; -- root scenario
5592 --
5593 -- IMPORTANT: The call to B from A is a possible ABE for X, but
5594 -- not for Y. Installing an unconditional ABE raise prior to the
5595 -- call to B would be wrong as it will fail for Y as well, but in
5596 -- Y's case the call to B is never an ABE.
5597
5598 elsif Present (Body_Decl)
5599 and then In_Extended_Main_Code_Unit (Body_Decl)
5600 then
5601 if Earlier_In_Extended_Unit (Root, Body_Decl) then
5602
5603 -- Do not emit any ABE diagnostics when a previous scenario in
5604 -- this traversal has suppressed elaboration warnings.
5605
5606 if New_In_State.Suppress_Warnings then
5607 null;
5608
5609 -- Do not emit any ABE diagnostics when the call occurs in a
5610 -- partial finalization context because this leads to confusing
5611 -- noise.
5612
5613 elsif New_In_State.Within_Partial_Finalization then
5614 null;
5615
5616 -- Otherwise emit the ABE diagnostic
5617
5618 else
5619 Error_Msg_NE
5620 ("??cannot call & before body seen", Call, Subp_Id);
5621 Error_Msg_N
5622 ("\Program_Error may be raised at run time", Call);
5623
5624 Output_Active_Scenarios (Call, New_In_State);
5625 end if;
5626
5627 -- Install a conditional run-time ABE check to verify that the
5628 -- target body has been elaborated prior to the call.
5629
5630 if Check_OK then
5631 Install_Scenario_ABE_Check
5632 (N => Call,
5633 Targ_Id => Subp_Id,
5634 Targ_Rep => Subp_Rep,
5635 Disable => Call_Rep);
5636
5637 -- Update the state of the Processing phase to indicate that
5638 -- no implicit Elaborate[_All] pragma must be generated from
5639 -- this point on.
5640 --
5641 -- function B ...;
5642 --
5643 -- function A ... is
5644 -- begin
5645 -- if Some_Condition then
5646 -- <ABE check>
5647 -- return B;
5648 -- ...
5649 -- end A;
5650 --
5651 -- X : ... := A;
5652 --
5653 -- function B ... is
5654 -- External.Subp; -- imparts Elaborate_All
5655 -- end B;
5656 --
5657 -- If Some_Condition is True, then the ABE check will fail
5658 -- at runtime and the call to External.Subp will never take
5659 -- place, rendering the implicit Elaborate_All useless.
5660 --
5661 -- If the value of Some_Condition is False, then the call
5662 -- to External.Subp will never take place, rendering the
5663 -- implicit Elaborate_All useless.
5664
5665 New_In_State.Suppress_Implicit_Pragmas := True;
5666 end if;
5667 end if;
5668
5669 -- Otherwise the target body is not available in this compilation or
5670 -- it resides in an external unit. Install a run-time ABE check to
5671 -- verify that the target body has been elaborated prior to the call
5672 -- site when the dynamic model is in effect.
5673
5674 elsif Check_OK
5675 and then New_In_State.Processing = Dynamic_Model_Processing
5676 then
5677 Install_Unit_ABE_Check
5678 (N => Call,
5679 Unit_Id => Unit_Id,
5680 Disable => Call_Rep);
5681 end if;
5682
5683 -- Ensure that the unit with the target body is elaborated prior to
5684 -- the main unit. The implicit Elaborate[_All] is generated only when
5685 -- the call has elaboration checks enabled. This behaviour parallels
5686 -- that of the old ABE mechanism.
5687
5688 if Elaboration_Checks_OK (Call_Rep) then
5689 Ensure_Prior_Elaboration
5690 (N => Call,
5691 Unit_Id => Unit_Id,
5692 Prag_Nam => Name_Elaborate_All,
5693 In_State => New_In_State);
5694 end if;
5695 end Process_Conditional_ABE_Call_Ada;
5696
5697 ----------------------------------------
5698 -- Process_Conditional_ABE_Call_SPARK --
5699 ----------------------------------------
5700
5701 procedure Process_Conditional_ABE_Call_SPARK
5702 (Call : Node_Id;
5703 Call_Rep : Scenario_Rep_Id;
5704 Subp_Id : Entity_Id;
5705 Subp_Rep : Target_Rep_Id;
5706 In_State : Processing_In_State)
5707 is
5708 pragma Unreferenced (Call_Rep);
5709
5710 Body_Decl : constant Node_Id := Body_Declaration (Subp_Rep);
5711 Region : Node_Id;
5712
5713 begin
5714 -- Ensure that a suitable elaboration model is in effect for SPARK
5715 -- rule verification.
5716
5717 Check_SPARK_Model_In_Effect;
5718
5719 -- The call and the target body are both in the main unit
5720
5721 if Present (Body_Decl)
5722 and then In_Extended_Main_Code_Unit (Body_Decl)
5723 and then Earlier_In_Extended_Unit (Call, Body_Decl)
5724 then
5725 -- Do not emit any ABE diagnostics when a previous scenario in
5726 -- this traversal has suppressed elaboration warnings.
5727
5728 if In_State.Suppress_Warnings then
5729 null;
5730
5731 -- Do not emit any ABE diagnostics when the call occurs in an
5732 -- initial condition context because this leads to incorrect
5733 -- diagnostics.
5734
5735 elsif In_State.Within_Initial_Condition then
5736 null;
5737
5738 -- Do not emit any ABE diagnostics when the call occurs in a
5739 -- partial finalization context because this leads to confusing
5740 -- noise.
5741
5742 elsif In_State.Within_Partial_Finalization then
5743 null;
5744
5745 -- Ensure that a call that textually precedes the subprogram body
5746 -- it invokes appears within the early call region of the body.
5747 --
5748 -- IMPORTANT: This check must always be performed even when switch
5749 -- -gnatd.v (enforce SPARK elaboration rules in SPARK code) is not
5750 -- specified because the static model cannot guarantee the absence
5751 -- of elaboration issues when dispatching calls are involved.
5752
5753 else
5754 Region := Find_Early_Call_Region (Body_Decl);
5755
5756 if Earlier_In_Extended_Unit (Call, Region) then
5757 Error_Msg_NE
5758 ("call must appear within early call region of subprogram "
5759 & "body & (SPARK RM 7.7(3))",
5760 Call, Subp_Id);
5761
5762 Error_Msg_Sloc := Sloc (Region);
5763 Error_Msg_N ("\region starts #", Call);
5764
5765 Error_Msg_Sloc := Sloc (Body_Decl);
5766 Error_Msg_N ("\region ends #", Call);
5767
5768 Output_Active_Scenarios (Call, In_State);
5769 end if;
5770 end if;
5771 end if;
5772
5773 -- A call to a source target or to a target which emulates Ada
5774 -- or SPARK semantics imposes an Elaborate_All requirement on the
5775 -- context of the main unit. Determine whether the context has a
5776 -- pragma strong enough to meet the requirement.
5777 --
5778 -- IMPORTANT: This check must be performed only when switch -gnatd.v
5779 -- (enforce SPARK elaboration rules in SPARK code) is active because
5780 -- the static model can ensure the prior elaboration of the unit
5781 -- which contains a body by installing an implicit Elaborate[_All]
5782 -- pragma.
5783
5784 if Debug_Flag_Dot_V then
5785 if Comes_From_Source (Subp_Id)
5786 or else Is_Ada_Semantic_Target (Subp_Id)
5787 or else Is_SPARK_Semantic_Target (Subp_Id)
5788 then
5789 Meet_Elaboration_Requirement
5790 (N => Call,
5791 Targ_Id => Subp_Id,
5792 Req_Nam => Name_Elaborate_All,
5793 In_State => In_State);
5794 end if;
5795
5796 -- Otherwise ensure that the unit with the target body is elaborated
5797 -- prior to the main unit.
5798
5799 else
5800 Ensure_Prior_Elaboration
5801 (N => Call,
5802 Unit_Id => Unit (Subp_Rep),
5803 Prag_Nam => Name_Elaborate_All,
5804 In_State => In_State);
5805 end if;
5806 end Process_Conditional_ABE_Call_SPARK;
5807
5808 -------------------------------------------
5809 -- Process_Conditional_ABE_Instantiation --
5810 -------------------------------------------
5811
5812 procedure Process_Conditional_ABE_Instantiation
5813 (Inst : Node_Id;
5814 Inst_Rep : Scenario_Rep_Id;
5815 In_State : Processing_In_State)
5816 is
5817 Gen_Id : constant Entity_Id := Target (Inst_Rep);
5818 Gen_Rep : constant Target_Rep_Id :=
5819 Target_Representation_Of (Gen_Id, In_State);
5820
5821 SPARK_Rules_On : constant Boolean :=
5822 SPARK_Mode_Of (Inst_Rep) = Is_On
5823 and then SPARK_Mode_Of (Gen_Rep) = Is_On;
5824
5825 New_In_State : Processing_In_State := In_State;
5826 -- Each step of the Processing phase constitutes a new state
5827
5828 begin
5829 -- Output relevant information when switch -gnatel (info messages on
5830 -- implicit Elaborate[_All] pragmas) is in effect.
5831
5832 if Elab_Info_Messages
5833 and then not New_In_State.Suppress_Info_Messages
5834 then
5835 Info_Instantiation
5836 (Inst => Inst,
5837 Gen_Id => Gen_Id,
5838 Info_Msg => True,
5839 In_SPARK => SPARK_Rules_On);
5840 end if;
5841
5842 -- Nothing to do when the instantiation is a guaranteed ABE
5843
5844 if Is_Known_Guaranteed_ABE (Inst) then
5845 return;
5846
5847 -- Nothing to do when the root scenario appears at the declaration
5848 -- level and the generic is in the same unit, but outside this
5849 -- context.
5850 --
5851 -- generic
5852 -- procedure Gen is ...; -- generic declaration
5853 --
5854 -- procedure Proc is
5855 -- function A ... is
5856 -- begin
5857 -- if Some_Condition then
5858 -- declare
5859 -- procedure I is new Gen; -- instantiation site
5860 -- ...
5861 -- ...
5862 -- end A;
5863 --
5864 -- X : ... := A; -- root scenario
5865 -- ...
5866 --
5867 -- procedure Gen is
5868 -- ...
5869 -- end Gen;
5870 --
5871 -- In the example above, the context of X is the declarative region
5872 -- of Proc. The "elaboration" of X may eventually reach Gen which
5873 -- appears outside of X's context. Gen is relevant only when Proc is
5874 -- invoked, but this happens only by means of "normal" elaboration,
5875 -- therefore Gen must not be considered if this is not the case.
5876
5877 elsif Is_Up_Level_Target
5878 (Targ_Decl => Spec_Declaration (Gen_Rep),
5879 In_State => New_In_State)
5880 then
5881 return;
5882 end if;
5883
5884 -- Warnings are suppressed when a prior scenario is already in that
5885 -- mode, or when the instantiation has warnings suppressed. Update
5886 -- the state of the processing phase to reflect this.
5887
5888 New_In_State.Suppress_Warnings :=
5889 New_In_State.Suppress_Warnings
5890 or else not Elaboration_Warnings_OK (Inst_Rep);
5891
5892 -- The SPARK rules are in effect
5893
5894 if SPARK_Rules_On then
5895 Process_Conditional_ABE_Instantiation_SPARK
5896 (Inst => Inst,
5897 Inst_Rep => Inst_Rep,
5898 Gen_Id => Gen_Id,
5899 Gen_Rep => Gen_Rep,
5900 In_State => New_In_State);
5901
5902 -- Otherwise the Ada rules are in effect, or SPARK code is allowed to
5903 -- violate the SPARK rules.
5904
5905 else
5906 Process_Conditional_ABE_Instantiation_Ada
5907 (Inst => Inst,
5908 Inst_Rep => Inst_Rep,
5909 Gen_Id => Gen_Id,
5910 Gen_Rep => Gen_Rep,
5911 In_State => New_In_State);
5912 end if;
5913 end Process_Conditional_ABE_Instantiation;
5914
5915 -----------------------------------------------
5916 -- Process_Conditional_ABE_Instantiation_Ada --
5917 -----------------------------------------------
5918
5919 procedure Process_Conditional_ABE_Instantiation_Ada
5920 (Inst : Node_Id;
5921 Inst_Rep : Scenario_Rep_Id;
5922 Gen_Id : Entity_Id;
5923 Gen_Rep : Target_Rep_Id;
5924 In_State : Processing_In_State)
5925 is
5926 Body_Decl : constant Node_Id := Body_Declaration (Gen_Rep);
5927 Root : constant Node_Id := Root_Scenario;
5928 Unit_Id : constant Entity_Id := Unit (Gen_Rep);
5929
5930 Check_OK : constant Boolean :=
5931 not In_State.Suppress_Checks
5932 and then Ghost_Mode_Of (Inst_Rep) /= Is_Ignored
5933 and then Ghost_Mode_Of (Gen_Rep) /= Is_Ignored
5934 and then Elaboration_Checks_OK (Inst_Rep)
5935 and then Elaboration_Checks_OK (Gen_Rep);
5936 -- A run-time ABE check may be installed only when both the instance
5937 -- and the generic have active elaboration checks and both are not
5938 -- ignored Ghost constructs.
5939
5940 New_In_State : Processing_In_State := In_State;
5941 -- Each step of the Processing phase constitutes a new state
5942
5943 begin
5944 -- Nothing to do when the instantiation is ABE-safe
5945 --
5946 -- generic
5947 -- package Gen is
5948 -- ...
5949 -- end Gen;
5950 --
5951 -- package body Gen is
5952 -- ...
5953 -- end Gen;
5954 --
5955 -- with Gen;
5956 -- procedure Main is
5957 -- package Inst is new Gen (ABE); -- safe instantiation
5958 -- ...
5959
5960 if Is_Safe_Instantiation (Inst, Gen_Id, Gen_Rep) then
5961 return;
5962
5963 -- The instantiation and the generic body are both in the main unit
5964 --
5965 -- If the root scenario appears prior to the generic body, then this
5966 -- is a possible ABE with respect to the root scenario.
5967 --
5968 -- generic
5969 -- package Gen is
5970 -- ...
5971 -- end Gen;
5972 --
5973 -- function A ... is
5974 -- begin
5975 -- if Some_Condition then
5976 -- declare
5977 -- package Inst is new Gen; -- instantiation site
5978 -- ...
5979 -- end A;
5980 --
5981 -- X : ... := A; -- root scenario
5982 --
5983 -- package body Gen is -- generic body
5984 -- ...
5985 -- end Gen;
5986 --
5987 -- Y : ... := A; -- root scenario
5988 --
5989 -- IMPORTANT: The instantiation of Gen is a possible ABE for X,
5990 -- but not for Y. Installing an unconditional ABE raise prior to
5991 -- the instance site would be wrong as it will fail for Y as well,
5992 -- but in Y's case the instantiation of Gen is never an ABE.
5993
5994 elsif Present (Body_Decl)
5995 and then In_Extended_Main_Code_Unit (Body_Decl)
5996 then
5997 if Earlier_In_Extended_Unit (Root, Body_Decl) then
5998
5999 -- Do not emit any ABE diagnostics when a previous scenario in
6000 -- this traversal has suppressed elaboration warnings.
6001
6002 if New_In_State.Suppress_Warnings then
6003 null;
6004
6005 -- Do not emit any ABE diagnostics when the instantiation
6006 -- occurs in partial finalization context because this leads
6007 -- to unwanted noise.
6008
6009 elsif New_In_State.Within_Partial_Finalization then
6010 null;
6011
6012 -- Otherwise output the diagnostic
6013
6014 else
6015 Error_Msg_NE
6016 ("??cannot instantiate & before body seen", Inst, Gen_Id);
6017 Error_Msg_N
6018 ("\Program_Error may be raised at run time", Inst);
6019
6020 Output_Active_Scenarios (Inst, New_In_State);
6021 end if;
6022
6023 -- Install a conditional run-time ABE check to verify that the
6024 -- generic body has been elaborated prior to the instantiation.
6025
6026 if Check_OK then
6027 Install_Scenario_ABE_Check
6028 (N => Inst,
6029 Targ_Id => Gen_Id,
6030 Targ_Rep => Gen_Rep,
6031 Disable => Inst_Rep);
6032
6033 -- Update the state of the Processing phase to indicate that
6034 -- no implicit Elaborate[_All] pragma must be generated from
6035 -- this point on.
6036 --
6037 -- generic
6038 -- package Gen is
6039 -- ...
6040 -- end Gen;
6041 --
6042 -- function A ... is
6043 -- begin
6044 -- if Some_Condition then
6045 -- <ABE check>
6046 -- declare Inst is new Gen;
6047 -- ...
6048 -- end A;
6049 --
6050 -- X : ... := A;
6051 --
6052 -- package body Gen is
6053 -- begin
6054 -- External.Subp; -- imparts Elaborate_All
6055 -- end Gen;
6056 --
6057 -- If Some_Condition is True, then the ABE check will fail
6058 -- at runtime and the call to External.Subp will never take
6059 -- place, rendering the implicit Elaborate_All useless.
6060 --
6061 -- If the value of Some_Condition is False, then the call
6062 -- to External.Subp will never take place, rendering the
6063 -- implicit Elaborate_All useless.
6064
6065 New_In_State.Suppress_Implicit_Pragmas := True;
6066 end if;
6067 end if;
6068
6069 -- Otherwise the generic body is not available in this compilation
6070 -- or it resides in an external unit. Install a run-time ABE check
6071 -- to verify that the generic body has been elaborated prior to the
6072 -- instantiation when the dynamic model is in effect.
6073
6074 elsif Check_OK
6075 and then New_In_State.Processing = Dynamic_Model_Processing
6076 then
6077 Install_Unit_ABE_Check
6078 (N => Inst,
6079 Unit_Id => Unit_Id,
6080 Disable => Inst_Rep);
6081 end if;
6082
6083 -- Ensure that the unit with the generic body is elaborated prior
6084 -- to the main unit. No implicit pragma has to be generated if the
6085 -- instantiation has elaboration checks suppressed. This behaviour
6086 -- parallels that of the old ABE mechanism.
6087
6088 if Elaboration_Checks_OK (Inst_Rep) then
6089 Ensure_Prior_Elaboration
6090 (N => Inst,
6091 Unit_Id => Unit_Id,
6092 Prag_Nam => Name_Elaborate,
6093 In_State => New_In_State);
6094 end if;
6095 end Process_Conditional_ABE_Instantiation_Ada;
6096
6097 -------------------------------------------------
6098 -- Process_Conditional_ABE_Instantiation_SPARK --
6099 -------------------------------------------------
6100
6101 procedure Process_Conditional_ABE_Instantiation_SPARK
6102 (Inst : Node_Id;
6103 Inst_Rep : Scenario_Rep_Id;
6104 Gen_Id : Entity_Id;
6105 Gen_Rep : Target_Rep_Id;
6106 In_State : Processing_In_State)
6107 is
6108 pragma Unreferenced (Inst_Rep);
6109
6110 Req_Nam : Name_Id;
6111
6112 begin
6113 -- Ensure that a suitable elaboration model is in effect for SPARK
6114 -- rule verification.
6115
6116 Check_SPARK_Model_In_Effect;
6117
6118 -- A source instantiation imposes an Elaborate[_All] requirement
6119 -- on the context of the main unit. Determine whether the context
6120 -- has a pragma strong enough to meet the requirement. The check
6121 -- is orthogonal to the ABE ramifications of the instantiation.
6122 --
6123 -- IMPORTANT: This check must be performed only when switch -gnatd.v
6124 -- (enforce SPARK elaboration rules in SPARK code) is active because
6125 -- the static model can ensure the prior elaboration of the unit
6126 -- which contains a body by installing an implicit Elaborate[_All]
6127 -- pragma.
6128
6129 if Debug_Flag_Dot_V then
6130 if Nkind (Inst) = N_Package_Instantiation then
6131 Req_Nam := Name_Elaborate_All;
6132 else
6133 Req_Nam := Name_Elaborate;
6134 end if;
6135
6136 Meet_Elaboration_Requirement
6137 (N => Inst,
6138 Targ_Id => Gen_Id,
6139 Req_Nam => Req_Nam,
6140 In_State => In_State);
6141
6142 -- Otherwise ensure that the unit with the target body is elaborated
6143 -- prior to the main unit.
6144
6145 else
6146 Ensure_Prior_Elaboration
6147 (N => Inst,
6148 Unit_Id => Unit (Gen_Rep),
6149 Prag_Nam => Name_Elaborate,
6150 In_State => In_State);
6151 end if;
6152 end Process_Conditional_ABE_Instantiation_SPARK;
6153
6154 -------------------------------------------------
6155 -- Process_Conditional_ABE_Variable_Assignment --
6156 -------------------------------------------------
6157
6158 procedure Process_Conditional_ABE_Variable_Assignment
6159 (Asmt : Node_Id;
6160 Asmt_Rep : Scenario_Rep_Id;
6161 In_State : Processing_In_State)
6162 is
6163
6164 Var_Id : constant Entity_Id := Target (Asmt_Rep);
6165 Var_Rep : constant Target_Rep_Id :=
6166 Target_Representation_Of (Var_Id, In_State);
6167
6168 SPARK_Rules_On : constant Boolean :=
6169 SPARK_Mode_Of (Asmt_Rep) = Is_On
6170 and then SPARK_Mode_Of (Var_Rep) = Is_On;
6171
6172 begin
6173 -- Output relevant information when switch -gnatel (info messages on
6174 -- implicit Elaborate[_All] pragmas) is in effect.
6175
6176 if Elab_Info_Messages
6177 and then not In_State.Suppress_Info_Messages
6178 then
6179 Elab_Msg_NE
6180 (Msg => "assignment to & during elaboration",
6181 N => Asmt,
6182 Id => Var_Id,
6183 Info_Msg => True,
6184 In_SPARK => SPARK_Rules_On);
6185 end if;
6186
6187 -- The SPARK rules are in effect. These rules are applied regardless
6188 -- of whether switch -gnatd.v (enforce SPARK elaboration rules in
6189 -- SPARK code) is in effect because the static model cannot ensure
6190 -- safe assignment of variables.
6191
6192 if SPARK_Rules_On then
6193 Process_Conditional_ABE_Variable_Assignment_SPARK
6194 (Asmt => Asmt,
6195 Asmt_Rep => Asmt_Rep,
6196 Var_Id => Var_Id,
6197 Var_Rep => Var_Rep,
6198 In_State => In_State);
6199
6200 -- Otherwise the Ada rules are in effect
6201
6202 else
6203 Process_Conditional_ABE_Variable_Assignment_Ada
6204 (Asmt => Asmt,
6205 Asmt_Rep => Asmt_Rep,
6206 Var_Id => Var_Id,
6207 Var_Rep => Var_Rep,
6208 In_State => In_State);
6209 end if;
6210 end Process_Conditional_ABE_Variable_Assignment;
6211
6212 -----------------------------------------------------
6213 -- Process_Conditional_ABE_Variable_Assignment_Ada --
6214 -----------------------------------------------------
6215
6216 procedure Process_Conditional_ABE_Variable_Assignment_Ada
6217 (Asmt : Node_Id;
6218 Asmt_Rep : Scenario_Rep_Id;
6219 Var_Id : Entity_Id;
6220 Var_Rep : Target_Rep_Id;
6221 In_State : Processing_In_State)
6222 is
6223 pragma Unreferenced (Asmt_Rep);
6224
6225 Var_Decl : constant Node_Id := Variable_Declaration (Var_Rep);
6226 Unit_Id : constant Entity_Id := Unit (Var_Rep);
6227
6228 begin
6229 -- Emit a warning when an uninitialized variable declared in a
6230 -- package spec without a pragma Elaborate_Body is initialized
6231 -- by elaboration code within the corresponding body.
6232
6233 if Is_Elaboration_Warnings_OK_Id (Var_Id)
6234 and then not Is_Initialized (Var_Decl)
6235 and then not Has_Pragma_Elaborate_Body (Unit_Id)
6236 then
6237 -- Do not emit any ABE diagnostics when a previous scenario in
6238 -- this traversal has suppressed elaboration warnings.
6239
6240 if not In_State.Suppress_Warnings then
6241 Error_Msg_NE
6242 ("??variable & can be accessed by clients before this "
6243 & "initialization", Asmt, Var_Id);
6244
6245 Error_Msg_NE
6246 ("\add pragma ""Elaborate_Body"" to spec & to ensure proper "
6247 & "initialization", Asmt, Unit_Id);
6248
6249 Output_Active_Scenarios (Asmt, In_State);
6250 end if;
6251
6252 -- Generate an implicit Elaborate_Body in the spec
6253
6254 Set_Elaborate_Body_Desirable (Unit_Id);
6255 end if;
6256 end Process_Conditional_ABE_Variable_Assignment_Ada;
6257
6258 -------------------------------------------------------
6259 -- Process_Conditional_ABE_Variable_Assignment_SPARK --
6260 -------------------------------------------------------
6261
6262 procedure Process_Conditional_ABE_Variable_Assignment_SPARK
6263 (Asmt : Node_Id;
6264 Asmt_Rep : Scenario_Rep_Id;
6265 Var_Id : Entity_Id;
6266 Var_Rep : Target_Rep_Id;
6267 In_State : Processing_In_State)
6268 is
6269 pragma Unreferenced (Asmt_Rep);
6270
6271 Var_Decl : constant Node_Id := Variable_Declaration (Var_Rep);
6272 Unit_Id : constant Entity_Id := Unit (Var_Rep);
6273
6274 begin
6275 -- Ensure that a suitable elaboration model is in effect for SPARK
6276 -- rule verification.
6277
6278 Check_SPARK_Model_In_Effect;
6279
6280 -- Do not emit any ABE diagnostics when a previous scenario in this
6281 -- traversal has suppressed elaboration warnings.
6282
6283 if In_State.Suppress_Warnings then
6284 null;
6285
6286 -- Emit an error when an initialized variable declared in a package
6287 -- spec that is missing pragma Elaborate_Body is further modified by
6288 -- elaboration code within the corresponding body.
6289
6290 elsif Is_Elaboration_Warnings_OK_Id (Var_Id)
6291 and then Is_Initialized (Var_Decl)
6292 and then not Has_Pragma_Elaborate_Body (Unit_Id)
6293 then
6294 Error_Msg_NE
6295 ("variable & modified by elaboration code in package body",
6296 Asmt, Var_Id);
6297
6298 Error_Msg_NE
6299 ("\add pragma ""Elaborate_Body"" to spec & to ensure full "
6300 & "initialization", Asmt, Unit_Id);
6301
6302 Output_Active_Scenarios (Asmt, In_State);
6303 end if;
6304 end Process_Conditional_ABE_Variable_Assignment_SPARK;
6305
6306 ------------------------------------------------
6307 -- Process_Conditional_ABE_Variable_Reference --
6308 ------------------------------------------------
6309
6310 procedure Process_Conditional_ABE_Variable_Reference
6311 (Ref : Node_Id;
6312 Ref_Rep : Scenario_Rep_Id;
6313 In_State : Processing_In_State)
6314 is
6315 Var_Id : constant Entity_Id := Target (Ref);
6316 Var_Rep : Target_Rep_Id;
6317 Unit_Id : Entity_Id;
6318
6319 begin
6320 -- Nothing to do when the variable reference is not a read
6321
6322 if not Is_Read_Reference (Ref_Rep) then
6323 return;
6324 end if;
6325
6326 Var_Rep := Target_Representation_Of (Var_Id, In_State);
6327 Unit_Id := Unit (Var_Rep);
6328
6329 -- Output relevant information when switch -gnatel (info messages on
6330 -- implicit Elaborate[_All] pragmas) is in effect.
6331
6332 if Elab_Info_Messages
6333 and then not In_State.Suppress_Info_Messages
6334 then
6335 Elab_Msg_NE
6336 (Msg => "read of variable & during elaboration",
6337 N => Ref,
6338 Id => Var_Id,
6339 Info_Msg => True,
6340 In_SPARK => True);
6341 end if;
6342
6343 -- Nothing to do when the variable appears within the main unit
6344 -- because diagnostics on reads are relevant only for external
6345 -- variables.
6346
6347 if Is_Same_Unit (Unit_Id, Cunit_Entity (Main_Unit)) then
6348 null;
6349
6350 -- Nothing to do when the variable is already initialized. Note that
6351 -- the variable may be further modified by the external unit.
6352
6353 elsif Is_Initialized (Variable_Declaration (Var_Rep)) then
6354 null;
6355
6356 -- Nothing to do when the external unit guarantees the initialization
6357 -- of the variable by means of pragma Elaborate_Body.
6358
6359 elsif Has_Pragma_Elaborate_Body (Unit_Id) then
6360 null;
6361
6362 -- A variable read imposes an Elaborate requirement on the context of
6363 -- the main unit. Determine whether the context has a pragma strong
6364 -- enough to meet the requirement.
6365
6366 else
6367 Meet_Elaboration_Requirement
6368 (N => Ref,
6369 Targ_Id => Var_Id,
6370 Req_Nam => Name_Elaborate,
6371 In_State => In_State);
6372 end if;
6373 end Process_Conditional_ABE_Variable_Reference;
6374
6375 -----------------------------------
6376 -- Traverse_Conditional_ABE_Body --
6377 -----------------------------------
6378
6379 procedure Traverse_Conditional_ABE_Body
6380 (N : Node_Id;
6381 In_State : Processing_In_State)
6382 is
6383 begin
6384 Traverse_Body
6385 (N => N,
6386 Requires_Processing => Is_Conditional_ABE_Scenario'Access,
6387 Processor => Process_Conditional_ABE'Access,
6388 In_State => In_State);
6389 end Traverse_Conditional_ABE_Body;
6390 end Conditional_ABE_Processor;
6391
6392 -------------
6393 -- Destroy --
6394 -------------
6395
6396 procedure Destroy (NE : in out Node_Or_Entity_Id) is
6397 pragma Unreferenced (NE);
6398 begin
6399 null;
6400 end Destroy;
6401
6402 -----------------
6403 -- Diagnostics --
6404 -----------------
6405
6406 package body Diagnostics is
6407
6408 -----------------
6409 -- Elab_Msg_NE --
6410 -----------------
6411
6412 procedure Elab_Msg_NE
6413 (Msg : String;
6414 N : Node_Id;
6415 Id : Entity_Id;
6416 Info_Msg : Boolean;
6417 In_SPARK : Boolean)
6418 is
6419 function Prefix return String;
6420 pragma Inline (Prefix);
6421 -- Obtain the prefix of the message
6422
6423 function Suffix return String;
6424 pragma Inline (Suffix);
6425 -- Obtain the suffix of the message
6426
6427 ------------
6428 -- Prefix --
6429 ------------
6430
6431 function Prefix return String is
6432 begin
6433 if Info_Msg then
6434 return "info: ";
6435 else
6436 return "";
6437 end if;
6438 end Prefix;
6439
6440 ------------
6441 -- Suffix --
6442 ------------
6443
6444 function Suffix return String is
6445 begin
6446 if In_SPARK then
6447 return " in SPARK";
6448 else
6449 return "";
6450 end if;
6451 end Suffix;
6452
6453 -- Start of processing for Elab_Msg_NE
6454
6455 begin
6456 Error_Msg_NE (Prefix & Msg & Suffix, N, Id);
6457 end Elab_Msg_NE;
6458
6459 ---------------
6460 -- Info_Call --
6461 ---------------
6462
6463 procedure Info_Call
6464 (Call : Node_Id;
6465 Subp_Id : Entity_Id;
6466 Info_Msg : Boolean;
6467 In_SPARK : Boolean)
6468 is
6469 procedure Info_Accept_Alternative;
6470 pragma Inline (Info_Accept_Alternative);
6471 -- Output information concerning an accept alternative
6472
6473 procedure Info_Simple_Call;
6474 pragma Inline (Info_Simple_Call);
6475 -- Output information concerning the call
6476
6477 procedure Info_Type_Actions (Action : String);
6478 pragma Inline (Info_Type_Actions);
6479 -- Output information concerning action Action of a type
6480
6481 procedure Info_Verification_Call
6482 (Pred : String;
6483 Id : Entity_Id;
6484 Id_Kind : String);
6485 pragma Inline (Info_Verification_Call);
6486 -- Output information concerning the verification of predicate Pred
6487 -- applied to related entity Id with kind Id_Kind.
6488
6489 -----------------------------
6490 -- Info_Accept_Alternative --
6491 -----------------------------
6492
6493 procedure Info_Accept_Alternative is
6494 Entry_Id : constant Entity_Id := Receiving_Entry (Subp_Id);
6495 pragma Assert (Present (Entry_Id));
6496
6497 begin
6498 Elab_Msg_NE
6499 (Msg => "accept for entry & during elaboration",
6500 N => Call,
6501 Id => Entry_Id,
6502 Info_Msg => Info_Msg,
6503 In_SPARK => In_SPARK);
6504 end Info_Accept_Alternative;
6505
6506 ----------------------
6507 -- Info_Simple_Call --
6508 ----------------------
6509
6510 procedure Info_Simple_Call is
6511 begin
6512 Elab_Msg_NE
6513 (Msg => "call to & during elaboration",
6514 N => Call,
6515 Id => Subp_Id,
6516 Info_Msg => Info_Msg,
6517 In_SPARK => In_SPARK);
6518 end Info_Simple_Call;
6519
6520 -----------------------
6521 -- Info_Type_Actions --
6522 -----------------------
6523
6524 procedure Info_Type_Actions (Action : String) is
6525 Typ : constant Entity_Id := First_Formal_Type (Subp_Id);
6526 pragma Assert (Present (Typ));
6527
6528 begin
6529 Elab_Msg_NE
6530 (Msg => Action & " actions for type & during elaboration",
6531 N => Call,
6532 Id => Typ,
6533 Info_Msg => Info_Msg,
6534 In_SPARK => In_SPARK);
6535 end Info_Type_Actions;
6536
6537 ----------------------------
6538 -- Info_Verification_Call --
6539 ----------------------------
6540
6541 procedure Info_Verification_Call
6542 (Pred : String;
6543 Id : Entity_Id;
6544 Id_Kind : String)
6545 is
6546 pragma Assert (Present (Id));
6547
6548 begin
6549 Elab_Msg_NE
6550 (Msg =>
6551 "verification of " & Pred & " of " & Id_Kind & " & during "
6552 & "elaboration",
6553 N => Call,
6554 Id => Id,
6555 Info_Msg => Info_Msg,
6556 In_SPARK => In_SPARK);
6557 end Info_Verification_Call;
6558
6559 -- Start of processing for Info_Call
6560
6561 begin
6562 -- Do not output anything for targets defined in internal units
6563 -- because this creates noise.
6564
6565 if not In_Internal_Unit (Subp_Id) then
6566
6567 -- Accept alternative
6568
6569 if Is_Accept_Alternative_Proc (Subp_Id) then
6570 Info_Accept_Alternative;
6571
6572 -- Adjustment
6573
6574 elsif Is_TSS (Subp_Id, TSS_Deep_Adjust) then
6575 Info_Type_Actions ("adjustment");
6576
6577 -- Default_Initial_Condition
6578
6579 elsif Is_Default_Initial_Condition_Proc (Subp_Id) then
6580 Info_Verification_Call
6581 (Pred => "Default_Initial_Condition",
6582 Id => First_Formal_Type (Subp_Id),
6583 Id_Kind => "type");
6584
6585 -- Entries
6586
6587 elsif Is_Protected_Entry (Subp_Id) then
6588 Info_Simple_Call;
6589
6590 -- Task entry calls are never processed because the entry being
6591 -- invoked does not have a corresponding "body", it has a select.
6592
6593 elsif Is_Task_Entry (Subp_Id) then
6594 null;
6595
6596 -- Finalization
6597
6598 elsif Is_TSS (Subp_Id, TSS_Deep_Finalize) then
6599 Info_Type_Actions ("finalization");
6600
6601 -- Calls to _Finalizer procedures must not appear in the output
6602 -- because this creates confusing noise.
6603
6604 elsif Is_Finalizer_Proc (Subp_Id) then
6605 null;
6606
6607 -- Initial_Condition
6608
6609 elsif Is_Initial_Condition_Proc (Subp_Id) then
6610 Info_Verification_Call
6611 (Pred => "Initial_Condition",
6612 Id => Find_Enclosing_Scope (Call),
6613 Id_Kind => "package");
6614
6615 -- Initialization
6616
6617 elsif Is_Init_Proc (Subp_Id)
6618 or else Is_TSS (Subp_Id, TSS_Deep_Initialize)
6619 then
6620 Info_Type_Actions ("initialization");
6621
6622 -- Invariant
6623
6624 elsif Is_Invariant_Proc (Subp_Id) then
6625 Info_Verification_Call
6626 (Pred => "invariants",
6627 Id => First_Formal_Type (Subp_Id),
6628 Id_Kind => "type");
6629
6630 -- Partial invariant calls must not appear in the output because
6631 -- this creates confusing noise.
6632
6633 elsif Is_Partial_Invariant_Proc (Subp_Id) then
6634 null;
6635
6636 -- _Postconditions
6637
6638 elsif Is_Postconditions_Proc (Subp_Id) then
6639 Info_Verification_Call
6640 (Pred => "postconditions",
6641 Id => Find_Enclosing_Scope (Call),
6642 Id_Kind => "subprogram");
6643
6644 -- Subprograms must come last because some of the previous cases
6645 -- fall under this category.
6646
6647 elsif Ekind (Subp_Id) = E_Function then
6648 Info_Simple_Call;
6649
6650 elsif Ekind (Subp_Id) = E_Procedure then
6651 Info_Simple_Call;
6652
6653 else
6654 pragma Assert (False);
6655 return;
6656 end if;
6657 end if;
6658 end Info_Call;
6659
6660 ------------------------
6661 -- Info_Instantiation --
6662 ------------------------
6663
6664 procedure Info_Instantiation
6665 (Inst : Node_Id;
6666 Gen_Id : Entity_Id;
6667 Info_Msg : Boolean;
6668 In_SPARK : Boolean)
6669 is
6670 begin
6671 Elab_Msg_NE
6672 (Msg => "instantiation of & during elaboration",
6673 N => Inst,
6674 Id => Gen_Id,
6675 Info_Msg => Info_Msg,
6676 In_SPARK => In_SPARK);
6677 end Info_Instantiation;
6678
6679 -----------------------------
6680 -- Info_Variable_Reference --
6681 -----------------------------
6682
6683 procedure Info_Variable_Reference
6684 (Ref : Node_Id;
6685 Var_Id : Entity_Id;
6686 Info_Msg : Boolean;
6687 In_SPARK : Boolean)
6688 is
6689 begin
6690 if Is_Read (Ref) then
6691 Elab_Msg_NE
6692 (Msg => "read of variable & during elaboration",
6693 N => Ref,
6694 Id => Var_Id,
6695 Info_Msg => Info_Msg,
6696 In_SPARK => In_SPARK);
6697 end if;
6698 end Info_Variable_Reference;
6699 end Diagnostics;
6700
6701 ---------------------------------
6702 -- Early_Call_Region_Processor --
6703 ---------------------------------
6704
6705 package body Early_Call_Region_Processor is
6706
6707 ---------------------
6708 -- Data structures --
6709 ---------------------
6710
6711 -- The following map relates early call regions to subprogram bodies
6712
6713 procedure Destroy (N : in out Node_Id);
6714 -- Destroy node N
6715
6716 package ECR_Map is new Dynamic_Hash_Tables
6717 (Key_Type => Entity_Id,
6718 Value_Type => Node_Id,
6719 No_Value => Empty,
6720 Expansion_Threshold => 1.5,
6721 Expansion_Factor => 2,
6722 Compression_Threshold => 0.3,
6723 Compression_Factor => 2,
6724 "=" => "=",
6725 Destroy_Value => Destroy,
6726 Hash => Hash);
6727
6728 Early_Call_Regions_Map : ECR_Map.Dynamic_Hash_Table := ECR_Map.Nil;
6729
6730 -----------------------
6731 -- Local subprograms --
6732 -----------------------
6733
6734 function Early_Call_Region (Body_Id : Entity_Id) return Node_Id;
6735 pragma Inline (Early_Call_Region);
6736 -- Obtain the early call region associated with entry or subprogram body
6737 -- Body_Id.
6738
6739 procedure Set_Early_Call_Region (Body_Id : Entity_Id; Start : Node_Id);
6740 pragma Inline (Set_Early_Call_Region);
6741 -- Associate an early call region with begins at construct Start with
6742 -- entry or subprogram body Body_Id.
6743
6744 -------------
6745 -- Destroy --
6746 -------------
6747
6748 procedure Destroy (N : in out Node_Id) is
6749 pragma Unreferenced (N);
6750 begin
6751 null;
6752 end Destroy;
6753
6754 -----------------------
6755 -- Early_Call_Region --
6756 -----------------------
6757
6758 function Early_Call_Region (Body_Id : Entity_Id) return Node_Id is
6759 pragma Assert (Present (Body_Id));
6760 begin
6761 return ECR_Map.Get (Early_Call_Regions_Map, Body_Id);
6762 end Early_Call_Region;
6763
6764 ------------------------------------------
6765 -- Finalize_Early_Call_Region_Processor --
6766 ------------------------------------------
6767
6768 procedure Finalize_Early_Call_Region_Processor is
6769 begin
6770 ECR_Map.Destroy (Early_Call_Regions_Map);
6771 end Finalize_Early_Call_Region_Processor;
6772
6773 ----------------------------
6774 -- Find_Early_Call_Region --
6775 ----------------------------
6776
6777 function Find_Early_Call_Region
6778 (Body_Decl : Node_Id;
6779 Assume_Elab_Body : Boolean := False;
6780 Skip_Memoization : Boolean := False) return Node_Id
6781 is
6782 -- NOTE: The routines within Find_Early_Call_Region are intentionally
6783 -- unnested to avoid deep indentation of code.
6784
6785 ECR_Found : exception;
6786 -- This exception is raised when the early call region has been found
6787
6788 Start : Node_Id := Empty;
6789 -- The start of the early call region. This variable is updated by
6790 -- the various nested routines. Due to the use of exceptions, the
6791 -- variable must be global to the nested routines.
6792
6793 -- The algorithm implemented in this routine attempts to find the
6794 -- early call region of a subprogram body by inspecting constructs
6795 -- in reverse declarative order, while navigating the tree. The
6796 -- algorithm consists of an Inspection phase and Advancement phase.
6797 -- The pseudocode is as follows:
6798 --
6799 -- loop
6800 -- inspection phase
6801 -- advancement phase
6802 -- end loop
6803 --
6804 -- The infinite loop is terminated by raising exception ECR_Found.
6805 -- The algorithm utilizes two pointers, Curr and Start, to represent
6806 -- the current construct to inspect and the start of the early call
6807 -- region.
6808 --
6809 -- IMPORTANT: The algorithm must maintain the following invariant at
6810 -- all time for it to function properly:
6811 --
6812 -- A nested construct is entered only when it contains suitable
6813 -- constructs.
6814 --
6815 -- This guarantees that leaving a nested or encapsulating construct
6816 -- functions properly.
6817 --
6818 -- The Inspection phase determines whether the current construct is
6819 -- non-preelaborable, and if it is, the algorithm terminates.
6820 --
6821 -- The Advancement phase walks the tree in reverse declarative order,
6822 -- while entering and leaving nested and encapsulating constructs. It
6823 -- may also terminate the elaborithm. There are several special cases
6824 -- of advancement.
6825 --
6826 -- 1) General case:
6827 --
6828 -- <construct 1>
6829 -- ...
6830 -- <construct N-1> <- Curr
6831 -- <construct N> <- Start
6832 -- <subprogram body>
6833 --
6834 -- In the general case, a declarative or statement list is traversed
6835 -- in reverse order where Curr is the lead pointer, and Start is the
6836 -- last preelaborable construct.
6837 --
6838 -- 2) Entering handled bodies
6839 --
6840 -- package body Nested is <- Curr (2.3)
6841 -- <declarations> <- Curr (2.2)
6842 -- begin
6843 -- <statements> <- Curr (2.1)
6844 -- end Nested;
6845 -- <construct> <- Start
6846 --
6847 -- In this case, the algorithm enters a handled body by starting from
6848 -- the last statement (2.1), or the last declaration (2.2), or the
6849 -- body is consumed (2.3) because it is empty and thus preelaborable.
6850 --
6851 -- 3) Entering package declarations
6852 --
6853 -- package Nested is <- Curr (2.3)
6854 -- <visible declarations> <- Curr (2.2)
6855 -- private
6856 -- <private declarations> <- Curr (2.1)
6857 -- end Nested;
6858 -- <construct> <- Start
6859 --
6860 -- In this case, the algorithm enters a package declaration by
6861 -- starting from the last private declaration (2.1), the last visible
6862 -- declaration (2.2), or the package is consumed (2.3) because it is
6863 -- empty and thus preelaborable.
6864 --
6865 -- 4) Transitioning from list to list of the same construct
6866 --
6867 -- Certain constructs have two eligible lists. The algorithm must
6868 -- thus transition from the second to the first list when the second
6869 -- list is exhausted.
6870 --
6871 -- declare <- Curr (4.2)
6872 -- <declarations> <- Curr (4.1)
6873 -- begin
6874 -- <statements> <- Start
6875 -- end;
6876 --
6877 -- In this case, the algorithm has exhausted the second list (the
6878 -- statements in the example above), and continues with the last
6879 -- declaration (4.1) or the construct is consumed (4.2) because it
6880 -- contains only preelaborable code.
6881 --
6882 -- 5) Transitioning from list to construct
6883 --
6884 -- tack body Task is <- Curr (5.1)
6885 -- <- Curr (Empty)
6886 -- <construct 1> <- Start
6887 --
6888 -- In this case, the algorithm has exhausted a list, Curr is Empty,
6889 -- and the owner of the list is consumed (5.1).
6890 --
6891 -- 6) Transitioning from unit to unit
6892 --
6893 -- A package body with a spec subject to pragma Elaborate_Body
6894 -- extends the possible range of the early call region to the package
6895 -- spec.
6896 --
6897 -- package Pack is <- Curr (6.3)
6898 -- pragma Elaborate_Body; <- Curr (6.2)
6899 -- <visible declarations> <- Curr (6.2)
6900 -- private
6901 -- <private declarations> <- Curr (6.1)
6902 -- end Pack;
6903 --
6904 -- package body Pack is <- Curr, Start
6905 --
6906 -- In this case, the algorithm has reached a package body compilation
6907 -- unit whose spec is subject to pragma Elaborate_Body, or the caller
6908 -- of the algorithm has specified this behavior. This transition is
6909 -- equivalent to 3).
6910 --
6911 -- 7) Transitioning from unit to termination
6912 --
6913 -- Reaching a compilation unit always terminates the algorithm as
6914 -- there are no more lists to examine. This must take case 6) into
6915 -- account.
6916 --
6917 -- 8) Transitioning from subunit to stub
6918 --
6919 -- package body Pack is separate; <- Curr (8.1)
6920 --
6921 -- separate (...)
6922 -- package body Pack is <- Curr, Start
6923 --
6924 -- Reaching a subunit continues the search from the corresponding
6925 -- stub (8.1).
6926
6927 procedure Advance (Curr : in out Node_Id);
6928 pragma Inline (Advance);
6929 -- Update the Curr and Start pointers depending on their location
6930 -- in the tree to the next eligible construct. This routine raises
6931 -- ECR_Found.
6932
6933 procedure Enter_Handled_Body (Curr : in out Node_Id);
6934 pragma Inline (Enter_Handled_Body);
6935 -- Update the Curr and Start pointers to enter a nested handled body
6936 -- if applicable. This routine raises ECR_Found.
6937
6938 procedure Enter_Package_Declaration (Curr : in out Node_Id);
6939 pragma Inline (Enter_Package_Declaration);
6940 -- Update the Curr and Start pointers to enter a nested package spec
6941 -- if applicable. This routine raises ECR_Found.
6942
6943 function Find_ECR (N : Node_Id) return Node_Id;
6944 pragma Inline (Find_ECR);
6945 -- Find an early call region starting from arbitrary node N
6946
6947 function Has_Suitable_Construct (List : List_Id) return Boolean;
6948 pragma Inline (Has_Suitable_Construct);
6949 -- Determine whether list List contains a suitable construct for
6950 -- inclusion into an early call region.
6951
6952 procedure Include (N : Node_Id; Curr : out Node_Id);
6953 pragma Inline (Include);
6954 -- Update the Curr and Start pointers to include arbitrary construct
6955 -- N in the early call region. This routine raises ECR_Found.
6956
6957 function Is_OK_Preelaborable_Construct (N : Node_Id) return Boolean;
6958 pragma Inline (Is_OK_Preelaborable_Construct);
6959 -- Determine whether arbitrary node N denotes a preelaboration-safe
6960 -- construct.
6961
6962 function Is_Suitable_Construct (N : Node_Id) return Boolean;
6963 pragma Inline (Is_Suitable_Construct);
6964 -- Determine whether arbitrary node N denotes a suitable construct
6965 -- for inclusion into the early call region.
6966
6967 procedure Transition_Body_Declarations
6968 (Bod : Node_Id;
6969 Curr : out Node_Id);
6970 pragma Inline (Transition_Body_Declarations);
6971 -- Update the Curr and Start pointers when construct Bod denotes a
6972 -- block statement or a suitable body. This routine raises ECR_Found.
6973
6974 procedure Transition_Handled_Statements
6975 (HSS : Node_Id;
6976 Curr : out Node_Id);
6977 pragma Inline (Transition_Handled_Statements);
6978 -- Update the Curr and Start pointers when node HSS denotes a handled
6979 -- sequence of statements. This routine raises ECR_Found.
6980
6981 procedure Transition_Spec_Declarations
6982 (Spec : Node_Id;
6983 Curr : out Node_Id);
6984 pragma Inline (Transition_Spec_Declarations);
6985 -- Update the Curr and Start pointers when construct Spec denotes
6986 -- a concurrent definition or a package spec. This routine raises
6987 -- ECR_Found.
6988
6989 procedure Transition_Unit (Unit : Node_Id; Curr : out Node_Id);
6990 pragma Inline (Transition_Unit);
6991 -- Update the Curr and Start pointers when node Unit denotes a
6992 -- potential compilation unit. This routine raises ECR_Found.
6993
6994 -------------
6995 -- Advance --
6996 -------------
6997
6998 procedure Advance (Curr : in out Node_Id) is
6999 Context : Node_Id;
7000
7001 begin
7002 -- Curr denotes one of the following cases upon entry into this
7003 -- routine:
7004 --
7005 -- * Empty - There is no current construct when a declarative or
7006 -- a statement list has been exhausted. This does not indicate
7007 -- that the early call region has been computed as it is still
7008 -- possible to transition to another list.
7009 --
7010 -- * Encapsulator - The current construct wraps declarations
7011 -- and/or statements. This indicates that the early call
7012 -- region may extend within the nested construct.
7013 --
7014 -- * Preelaborable - The current construct is preelaborable
7015 -- because Find_ECR would not invoke Advance if this was not
7016 -- the case.
7017
7018 -- The current construct is an encapsulator or is preelaborable
7019
7020 if Present (Curr) then
7021
7022 -- Enter encapsulators by inspecting their declarations and/or
7023 -- statements.
7024
7025 if Nkind_In (Curr, N_Block_Statement, N_Package_Body) then
7026 Enter_Handled_Body (Curr);
7027
7028 elsif Nkind (Curr) = N_Package_Declaration then
7029 Enter_Package_Declaration (Curr);
7030
7031 -- Early call regions have a property which can be exploited to
7032 -- optimize the algorithm.
7033 --
7034 -- <preceding subprogram body>
7035 -- <preelaborable construct 1>
7036 -- ...
7037 -- <preelaborable construct N>
7038 -- <initiating subprogram body>
7039 --
7040 -- If a traversal initiated from a subprogram body reaches a
7041 -- preceding subprogram body, then both bodies share the same
7042 -- early call region.
7043 --
7044 -- The property results in the following desirable effects:
7045 --
7046 -- * If the preceding body already has an early call region,
7047 -- then the initiating body can reuse it. This minimizes the
7048 -- amount of processing performed by the algorithm.
7049 --
7050 -- * If the preceding body lack an early call region, then the
7051 -- algorithm can compute the early call region, and reuse it
7052 -- for the initiating body. This processing performs the same
7053 -- amount of work, but has the beneficial effect of computing
7054 -- the early call regions of all preceding bodies.
7055
7056 elsif Nkind_In (Curr, N_Entry_Body, N_Subprogram_Body) then
7057 Start :=
7058 Find_Early_Call_Region
7059 (Body_Decl => Curr,
7060 Assume_Elab_Body => Assume_Elab_Body,
7061 Skip_Memoization => Skip_Memoization);
7062
7063 raise ECR_Found;
7064
7065 -- Otherwise current construct is preelaborable. Unpdate the
7066 -- early call region to include it.
7067
7068 else
7069 Include (Curr, Curr);
7070 end if;
7071
7072 -- Otherwise the current construct is missing, indicating that the
7073 -- current list has been exhausted. Depending on the context of
7074 -- the list, several transitions are possible.
7075
7076 else
7077 -- The invariant of the algorithm ensures that Curr and Start
7078 -- are at the same level of nesting at the point of transition.
7079 -- The algorithm can determine which list the traversal came
7080 -- from by examining Start.
7081
7082 Context := Parent (Start);
7083
7084 -- Attempt the following transitions:
7085 --
7086 -- private declarations -> visible declarations
7087 -- private declarations -> upper level
7088 -- private declarations -> terminate
7089 -- visible declarations -> upper level
7090 -- visible declarations -> terminate
7091
7092 if Nkind_In (Context, N_Package_Specification,
7093 N_Protected_Definition,
7094 N_Task_Definition)
7095 then
7096 Transition_Spec_Declarations (Context, Curr);
7097
7098 -- Attempt the following transitions:
7099 --
7100 -- statements -> declarations
7101 -- statements -> upper level
7102 -- statements -> corresponding package spec (Elab_Body)
7103 -- statements -> terminate
7104
7105 elsif Nkind (Context) = N_Handled_Sequence_Of_Statements then
7106 Transition_Handled_Statements (Context, Curr);
7107
7108 -- Attempt the following transitions:
7109 --
7110 -- declarations -> upper level
7111 -- declarations -> corresponding package spec (Elab_Body)
7112 -- declarations -> terminate
7113
7114 elsif Nkind_In (Context, N_Block_Statement,
7115 N_Entry_Body,
7116 N_Package_Body,
7117 N_Protected_Body,
7118 N_Subprogram_Body,
7119 N_Task_Body)
7120 then
7121 Transition_Body_Declarations (Context, Curr);
7122
7123 -- Otherwise it is not possible to transition. Stop the search
7124 -- because there are no more declarations or statements to
7125 -- check.
7126
7127 else
7128 raise ECR_Found;
7129 end if;
7130 end if;
7131 end Advance;
7132
7133 --------------------------
7134 -- Enter_Handled_Body --
7135 --------------------------
7136
7137 procedure Enter_Handled_Body (Curr : in out Node_Id) is
7138 Decls : constant List_Id := Declarations (Curr);
7139 HSS : constant Node_Id := Handled_Statement_Sequence (Curr);
7140 Stmts : List_Id := No_List;
7141
7142 begin
7143 if Present (HSS) then
7144 Stmts := Statements (HSS);
7145 end if;
7146
7147 -- The handled body has a non-empty statement sequence. The
7148 -- construct to inspect is the last statement.
7149
7150 if Has_Suitable_Construct (Stmts) then
7151 Curr := Last (Stmts);
7152
7153 -- The handled body lacks statements, but has non-empty
7154 -- declarations. The construct to inspect is the last declaration.
7155
7156 elsif Has_Suitable_Construct (Decls) then
7157 Curr := Last (Decls);
7158
7159 -- Otherwise the handled body lacks both declarations and
7160 -- statements. The construct to inspect is the node which precedes
7161 -- the handled body. Update the early call region to include the
7162 -- handled body.
7163
7164 else
7165 Include (Curr, Curr);
7166 end if;
7167 end Enter_Handled_Body;
7168
7169 -------------------------------
7170 -- Enter_Package_Declaration --
7171 -------------------------------
7172
7173 procedure Enter_Package_Declaration (Curr : in out Node_Id) is
7174 Pack_Spec : constant Node_Id := Specification (Curr);
7175 Prv_Decls : constant List_Id := Private_Declarations (Pack_Spec);
7176 Vis_Decls : constant List_Id := Visible_Declarations (Pack_Spec);
7177
7178 begin
7179 -- The package has a non-empty private declarations. The construct
7180 -- to inspect is the last private declaration.
7181
7182 if Has_Suitable_Construct (Prv_Decls) then
7183 Curr := Last (Prv_Decls);
7184
7185 -- The package lacks private declarations, but has non-empty
7186 -- visible declarations. In this case the construct to inspect
7187 -- is the last visible declaration.
7188
7189 elsif Has_Suitable_Construct (Vis_Decls) then
7190 Curr := Last (Vis_Decls);
7191
7192 -- Otherwise the package lacks any declarations. The construct
7193 -- to inspect is the node which precedes the package. Update the
7194 -- early call region to include the package declaration.
7195
7196 else
7197 Include (Curr, Curr);
7198 end if;
7199 end Enter_Package_Declaration;
7200
7201 --------------
7202 -- Find_ECR --
7203 --------------
7204
7205 function Find_ECR (N : Node_Id) return Node_Id is
7206 Curr : Node_Id;
7207
7208 begin
7209 -- The early call region starts at N
7210
7211 Curr := Prev (N);
7212 Start := N;
7213
7214 -- Inspect each node in reverse declarative order while going in
7215 -- and out of nested and enclosing constructs. Note that the only
7216 -- way to terminate this infinite loop is to raise ECR_Found.
7217
7218 loop
7219 -- The current construct is not preelaboration-safe. Terminate
7220 -- the traversal.
7221
7222 if Present (Curr)
7223 and then not Is_OK_Preelaborable_Construct (Curr)
7224 then
7225 raise ECR_Found;
7226 end if;
7227
7228 -- Advance to the next suitable construct. This may terminate
7229 -- the traversal by raising ECR_Found.
7230
7231 Advance (Curr);
7232 end loop;
7233
7234 exception
7235 when ECR_Found =>
7236 return Start;
7237 end Find_ECR;
7238
7239 ----------------------------
7240 -- Has_Suitable_Construct --
7241 ----------------------------
7242
7243 function Has_Suitable_Construct (List : List_Id) return Boolean is
7244 Item : Node_Id;
7245
7246 begin
7247 -- Examine the list in reverse declarative order, looking for a
7248 -- suitable construct.
7249
7250 if Present (List) then
7251 Item := Last (List);
7252 while Present (Item) loop
7253 if Is_Suitable_Construct (Item) then
7254 return True;
7255 end if;
7256
7257 Prev (Item);
7258 end loop;
7259 end if;
7260
7261 return False;
7262 end Has_Suitable_Construct;
7263
7264 -------------
7265 -- Include --
7266 -------------
7267
7268 procedure Include (N : Node_Id; Curr : out Node_Id) is
7269 begin
7270 Start := N;
7271
7272 -- The input node is a compilation unit. This terminates the
7273 -- search because there are no more lists to inspect and there are
7274 -- no more enclosing constructs to climb up to. The transitions
7275 -- are:
7276 --
7277 -- private declarations -> terminate
7278 -- visible declarations -> terminate
7279 -- statements -> terminate
7280 -- declarations -> terminate
7281
7282 if Nkind (Parent (Start)) = N_Compilation_Unit then
7283 raise ECR_Found;
7284
7285 -- Otherwise the input node is still within some list
7286
7287 else
7288 Curr := Prev (Start);
7289 end if;
7290 end Include;
7291
7292 -----------------------------------
7293 -- Is_OK_Preelaborable_Construct --
7294 -----------------------------------
7295
7296 function Is_OK_Preelaborable_Construct (N : Node_Id) return Boolean is
7297 begin
7298 -- Assignment statements are acceptable as long as they were
7299 -- produced by the ABE mechanism to update elaboration flags.
7300
7301 if Nkind (N) = N_Assignment_Statement then
7302 return Is_Elaboration_Code (N);
7303
7304 -- Block statements are acceptable even though they directly
7305 -- violate preelaborability. The intention is not to penalize
7306 -- the early call region when a block contains only preelaborable
7307 -- constructs.
7308 --
7309 -- declare
7310 -- Val : constant Integer := 1;
7311 -- begin
7312 -- pragma Assert (Val = 1);
7313 -- null;
7314 -- end;
7315 --
7316 -- Note that the Advancement phase does enter blocks, and will
7317 -- detect any non-preelaborable declarations or statements within.
7318
7319 elsif Nkind (N) = N_Block_Statement then
7320 return True;
7321 end if;
7322
7323 -- Otherwise the construct must be preelaborable. The check must
7324 -- take the syntactic and semantic structure of the construct. DO
7325 -- NOT use Is_Preelaborable_Construct here.
7326
7327 return not Is_Non_Preelaborable_Construct (N);
7328 end Is_OK_Preelaborable_Construct;
7329
7330 ---------------------------
7331 -- Is_Suitable_Construct --
7332 ---------------------------
7333
7334 function Is_Suitable_Construct (N : Node_Id) return Boolean is
7335 Context : constant Node_Id := Parent (N);
7336
7337 begin
7338 -- An internally-generated statement sequence which contains only
7339 -- a single null statement is not a suitable construct because it
7340 -- is a byproduct of the parser. Such a null statement should be
7341 -- excluded from the early call region because it carries the
7342 -- source location of the "end" keyword, and may lead to confusing
7343 -- diagnistics.
7344
7345 if Nkind (N) = N_Null_Statement
7346 and then not Comes_From_Source (N)
7347 and then Present (Context)
7348 and then Nkind (Context) = N_Handled_Sequence_Of_Statements
7349 then
7350 return False;
7351 end if;
7352
7353 -- Otherwise only constructs which correspond to pure Ada
7354 -- constructs are considered suitable.
7355
7356 case Nkind (N) is
7357 when N_Call_Marker
7358 | N_Freeze_Entity
7359 | N_Freeze_Generic_Entity
7360 | N_Implicit_Label_Declaration
7361 | N_Itype_Reference
7362 | N_Pop_Constraint_Error_Label
7363 | N_Pop_Program_Error_Label
7364 | N_Pop_Storage_Error_Label
7365 | N_Push_Constraint_Error_Label
7366 | N_Push_Program_Error_Label
7367 | N_Push_Storage_Error_Label
7368 | N_SCIL_Dispatch_Table_Tag_Init
7369 | N_SCIL_Dispatching_Call
7370 | N_SCIL_Membership_Test
7371 | N_Variable_Reference_Marker
7372 =>
7373 return False;
7374
7375 when others =>
7376 return True;
7377 end case;
7378 end Is_Suitable_Construct;
7379
7380 ----------------------------------
7381 -- Transition_Body_Declarations --
7382 ----------------------------------
7383
7384 procedure Transition_Body_Declarations
7385 (Bod : Node_Id;
7386 Curr : out Node_Id)
7387 is
7388 Decls : constant List_Id := Declarations (Bod);
7389
7390 begin
7391 -- The search must come from the declarations of the body
7392
7393 pragma Assert
7394 (Is_Non_Empty_List (Decls)
7395 and then List_Containing (Start) = Decls);
7396
7397 -- The search finished inspecting the declarations. The construct
7398 -- to inspect is the node which precedes the handled body, unless
7399 -- the body is a compilation unit. The transitions are:
7400 --
7401 -- declarations -> upper level
7402 -- declarations -> corresponding package spec (Elab_Body)
7403 -- declarations -> terminate
7404
7405 Transition_Unit (Bod, Curr);
7406 end Transition_Body_Declarations;
7407
7408 -----------------------------------
7409 -- Transition_Handled_Statements --
7410 -----------------------------------
7411
7412 procedure Transition_Handled_Statements
7413 (HSS : Node_Id;
7414 Curr : out Node_Id)
7415 is
7416 Bod : constant Node_Id := Parent (HSS);
7417 Decls : constant List_Id := Declarations (Bod);
7418 Stmts : constant List_Id := Statements (HSS);
7419
7420 begin
7421 -- The search must come from the statements of certain bodies or
7422 -- statements.
7423
7424 pragma Assert (Nkind_In (Bod, N_Block_Statement,
7425 N_Entry_Body,
7426 N_Package_Body,
7427 N_Protected_Body,
7428 N_Subprogram_Body,
7429 N_Task_Body));
7430
7431 -- The search must come from the statements of the handled
7432 -- sequence.
7433
7434 pragma Assert
7435 (Is_Non_Empty_List (Stmts)
7436 and then List_Containing (Start) = Stmts);
7437
7438 -- The search finished inspecting the statements. The handled body
7439 -- has non-empty declarations. The construct to inspect is the
7440 -- last declaration. The transitions are:
7441 --
7442 -- statements -> declarations
7443
7444 if Has_Suitable_Construct (Decls) then
7445 Curr := Last (Decls);
7446
7447 -- Otherwise the handled body lacks declarations. The construct to
7448 -- inspect is the node which precedes the handled body, unless the
7449 -- body is a compilation unit. The transitions are:
7450 --
7451 -- statements -> upper level
7452 -- statements -> corresponding package spec (Elab_Body)
7453 -- statements -> terminate
7454
7455 else
7456 Transition_Unit (Bod, Curr);
7457 end if;
7458 end Transition_Handled_Statements;
7459
7460 ----------------------------------
7461 -- Transition_Spec_Declarations --
7462 ----------------------------------
7463
7464 procedure Transition_Spec_Declarations
7465 (Spec : Node_Id;
7466 Curr : out Node_Id)
7467 is
7468 Prv_Decls : constant List_Id := Private_Declarations (Spec);
7469 Vis_Decls : constant List_Id := Visible_Declarations (Spec);
7470
7471 begin
7472 pragma Assert (Present (Start) and then Is_List_Member (Start));
7473
7474 -- The search came from the private declarations and finished
7475 -- their inspection.
7476
7477 if Has_Suitable_Construct (Prv_Decls)
7478 and then List_Containing (Start) = Prv_Decls
7479 then
7480 -- The context has non-empty visible declarations. The node to
7481 -- inspect is the last visible declaration. The transitions
7482 -- are:
7483 --
7484 -- private declarations -> visible declarations
7485
7486 if Has_Suitable_Construct (Vis_Decls) then
7487 Curr := Last (Vis_Decls);
7488
7489 -- Otherwise the context lacks visible declarations. The
7490 -- construct to inspect is the node which precedes the context
7491 -- unless the context is a compilation unit. The transitions
7492 -- are:
7493 --
7494 -- private declarations -> upper level
7495 -- private declarations -> terminate
7496
7497 else
7498 Transition_Unit (Parent (Spec), Curr);
7499 end if;
7500
7501 -- The search came from the visible declarations and finished
7502 -- their inspections. The construct to inspect is the node which
7503 -- precedes the context, unless the context is a compilaton unit.
7504 -- The transitions are:
7505 --
7506 -- visible declarations -> upper level
7507 -- visible declarations -> terminate
7508
7509 elsif Has_Suitable_Construct (Vis_Decls)
7510 and then List_Containing (Start) = Vis_Decls
7511 then
7512 Transition_Unit (Parent (Spec), Curr);
7513
7514 -- At this point both declarative lists are empty, but the
7515 -- traversal still came from within the spec. This indicates
7516 -- that the invariant of the algorithm has been violated.
7517
7518 else
7519 pragma Assert (False);
7520 raise ECR_Found;
7521 end if;
7522 end Transition_Spec_Declarations;
7523
7524 ---------------------
7525 -- Transition_Unit --
7526 ---------------------
7527
7528 procedure Transition_Unit
7529 (Unit : Node_Id;
7530 Curr : out Node_Id)
7531 is
7532 Context : constant Node_Id := Parent (Unit);
7533
7534 begin
7535 -- The unit is a compilation unit. This terminates the search
7536 -- because there are no more lists to inspect and there are no
7537 -- more enclosing constructs to climb up to.
7538
7539 if Nkind (Context) = N_Compilation_Unit then
7540
7541 -- A package body with a corresponding spec subject to pragma
7542 -- Elaborate_Body is an exception to the above. The annotation
7543 -- allows the search to continue into the package declaration.
7544 -- The transitions are:
7545 --
7546 -- statements -> corresponding package spec (Elab_Body)
7547 -- declarations -> corresponding package spec (Elab_Body)
7548
7549 if Nkind (Unit) = N_Package_Body
7550 and then (Assume_Elab_Body
7551 or else Has_Pragma_Elaborate_Body
7552 (Corresponding_Spec (Unit)))
7553 then
7554 Curr := Unit_Declaration_Node (Corresponding_Spec (Unit));
7555 Enter_Package_Declaration (Curr);
7556
7557 -- Otherwise terminate the search. The transitions are:
7558 --
7559 -- private declarations -> terminate
7560 -- visible declarations -> terminate
7561 -- statements -> terminate
7562 -- declarations -> terminate
7563
7564 else
7565 raise ECR_Found;
7566 end if;
7567
7568 -- The unit is a subunit. The construct to inspect is the node
7569 -- which precedes the corresponding stub. Update the early call
7570 -- region to include the unit.
7571
7572 elsif Nkind (Context) = N_Subunit then
7573 Start := Unit;
7574 Curr := Corresponding_Stub (Context);
7575
7576 -- Otherwise the unit is nested. The construct to inspect is the
7577 -- node which precedes the unit. Update the early call region to
7578 -- include the unit.
7579
7580 else
7581 Include (Unit, Curr);
7582 end if;
7583 end Transition_Unit;
7584
7585 -- Local variables
7586
7587 Body_Id : constant Entity_Id := Unique_Defining_Entity (Body_Decl);
7588 Region : Node_Id;
7589
7590 -- Start of processing for Find_Early_Call_Region
7591
7592 begin
7593 -- The caller demands the start of the early call region without
7594 -- saving or retrieving it to/from internal data structures.
7595
7596 if Skip_Memoization then
7597 Region := Find_ECR (Body_Decl);
7598
7599 -- Default behavior
7600
7601 else
7602 -- Check whether the early call region of the subprogram body is
7603 -- available.
7604
7605 Region := Early_Call_Region (Body_Id);
7606
7607 if No (Region) then
7608 Region := Find_ECR (Body_Decl);
7609
7610 -- Associate the early call region with the subprogram body in
7611 -- case other scenarios need it.
7612
7613 Set_Early_Call_Region (Body_Id, Region);
7614 end if;
7615 end if;
7616
7617 -- A subprogram body must always have an early call region
7618
7619 pragma Assert (Present (Region));
7620
7621 return Region;
7622 end Find_Early_Call_Region;
7623
7624 --------------------------------------------
7625 -- Initialize_Early_Call_Region_Processor --
7626 --------------------------------------------
7627
7628 procedure Initialize_Early_Call_Region_Processor is
7629 begin
7630 Early_Call_Regions_Map := ECR_Map.Create (100);
7631 end Initialize_Early_Call_Region_Processor;
7632
7633 ---------------------------
7634 -- Set_Early_Call_Region --
7635 ---------------------------
7636
7637 procedure Set_Early_Call_Region (Body_Id : Entity_Id; Start : Node_Id) is
7638 pragma Assert (Present (Body_Id));
7639 pragma Assert (Present (Start));
7640
7641 begin
7642 ECR_Map.Put (Early_Call_Regions_Map, Body_Id, Start);
7643 end Set_Early_Call_Region;
7644 end Early_Call_Region_Processor;
7645
7646 ----------------------
7647 -- Elaborated_Units --
7648 ----------------------
7649
7650 package body Elaborated_Units is
7651
7652 -----------
7653 -- Types --
7654 -----------
7655
7656 -- The following type idenfities the elaboration attributes of a unit
7657
7658 type Elaboration_Attributes_Id is new Natural;
7659
7660 No_Elaboration_Attributes : constant Elaboration_Attributes_Id :=
7661 Elaboration_Attributes_Id'First;
7662 First_Elaboration_Attributes : constant Elaboration_Attributes_Id :=
7663 No_Elaboration_Attributes + 1;
7664
7665 -- The following type represents the elaboration attributes of a unit
7666
7667 type Elaboration_Attributes_Record is record
7668 Elab_Pragma : Node_Id := Empty;
7669 -- This attribute denotes a source Elaborate or Elaborate_All pragma
7670 -- which guarantees the prior elaboration of some unit with respect
7671 -- to the main unit. The pragma may come from the following contexts:
7672 --
7673 -- * The main unit
7674 -- * The spec of the main unit (if applicable)
7675 -- * Any parent spec of the main unit (if applicable)
7676 -- * Any parent subunit of the main unit (if applicable)
7677 --
7678 -- The attribute remains Empty if no such pragma is available. Source
7679 -- pragmas play a role in satisfying SPARK elaboration requirements.
7680
7681 With_Clause : Node_Id := Empty;
7682 -- This attribute denotes an internally-generated or a source with
7683 -- clause for some unit withed by the main unit. With clauses carry
7684 -- flags which represent implicit Elaborate or Elaborate_All pragmas.
7685 -- These clauses play a role in supplying elaboration dependencies to
7686 -- binde.
7687 end record;
7688
7689 ---------------------
7690 -- Data structures --
7691 ---------------------
7692
7693 -- The following table stores all elaboration attributes
7694
7695 package Elaboration_Attributes is new Table.Table
7696 (Table_Index_Type => Elaboration_Attributes_Id,
7697 Table_Component_Type => Elaboration_Attributes_Record,
7698 Table_Low_Bound => First_Elaboration_Attributes,
7699 Table_Initial => 250,
7700 Table_Increment => 200,
7701 Table_Name => "Elaboration_Attributes");
7702
7703 procedure Destroy (EA_Id : in out Elaboration_Attributes_Id);
7704 -- Destroy elaboration attributes EA_Id
7705
7706 package UA_Map is new Dynamic_Hash_Tables
7707 (Key_Type => Entity_Id,
7708 Value_Type => Elaboration_Attributes_Id,
7709 No_Value => No_Elaboration_Attributes,
7710 Expansion_Threshold => 1.5,
7711 Expansion_Factor => 2,
7712 Compression_Threshold => 0.3,
7713 Compression_Factor => 2,
7714 "=" => "=",
7715 Destroy_Value => Destroy,
7716 Hash => Hash);
7717
7718 -- The following map relates an elaboration attributes of a unit to the
7719 -- unit.
7720
7721 Unit_To_Attributes_Map : UA_Map.Dynamic_Hash_Table := UA_Map.Nil;
7722
7723 ------------------
7724 -- Constructors --
7725 ------------------
7726
7727 function Elaboration_Attributes_Of
7728 (Unit_Id : Entity_Id) return Elaboration_Attributes_Id;
7729 pragma Inline (Elaboration_Attributes_Of);
7730 -- Obtain the elaboration attributes of unit Unit_Id
7731
7732 -----------------------
7733 -- Local subprograms --
7734 -----------------------
7735
7736 function Elab_Pragma (EA_Id : Elaboration_Attributes_Id) return Node_Id;
7737 pragma Inline (Elab_Pragma);
7738 -- Obtain the Elaborate[_All] pragma of elaboration attributes EA_Id
7739
7740 procedure Ensure_Prior_Elaboration_Dynamic
7741 (N : Node_Id;
7742 Unit_Id : Entity_Id;
7743 Prag_Nam : Name_Id;
7744 In_State : Processing_In_State);
7745 pragma Inline (Ensure_Prior_Elaboration_Dynamic);
7746 -- Guarantee the elaboration of unit Unit_Id with respect to the main
7747 -- unit by suggesting the use of Elaborate[_All] with name Prag_Nam. N
7748 -- denotes the related scenario. In_State is the current state of the
7749 -- Processing phase.
7750
7751 procedure Ensure_Prior_Elaboration_Static
7752 (N : Node_Id;
7753 Unit_Id : Entity_Id;
7754 Prag_Nam : Name_Id;
7755 In_State : Processing_In_State);
7756 pragma Inline (Ensure_Prior_Elaboration_Static);
7757 -- Guarantee the elaboration of unit Unit_Id with respect to the main
7758 -- unit by installing an implicit Elaborate[_All] pragma with name
7759 -- Prag_Nam. N denotes the related scenario. In_State is the current
7760 -- state of the Processing phase.
7761
7762 function Present (EA_Id : Elaboration_Attributes_Id) return Boolean;
7763 pragma Inline (Present);
7764 -- Determine whether elaboration attributes UA_Id exist
7765
7766 procedure Set_Elab_Pragma
7767 (EA_Id : Elaboration_Attributes_Id;
7768 Prag : Node_Id);
7769 pragma Inline (Set_Elab_Pragma);
7770 -- Set the Elaborate[_All] pragma of elaboration attributes EA_Id to
7771 -- Prag.
7772
7773 procedure Set_With_Clause
7774 (EA_Id : Elaboration_Attributes_Id;
7775 Clause : Node_Id);
7776 pragma Inline (Set_With_Clause);
7777 -- Set the with clause of elaboration attributes EA_Id to Clause
7778
7779 function With_Clause (EA_Id : Elaboration_Attributes_Id) return Node_Id;
7780 pragma Inline (With_Clause);
7781 -- Obtain the implicit or source with clause of elaboration attributes
7782 -- EA_Id.
7783
7784 ------------------------------
7785 -- Collect_Elaborated_Units --
7786 ------------------------------
7787
7788 procedure Collect_Elaborated_Units is
7789 procedure Add_Pragma (Prag : Node_Id);
7790 pragma Inline (Add_Pragma);
7791 -- Determine whether pragma Prag denotes a legal Elaborate[_All]
7792 -- pragma. If this is the case, add the related unit to the context.
7793 -- For pragma Elaborate_All, include recursively all units withed by
7794 -- the related unit.
7795
7796 procedure Add_Unit
7797 (Unit_Id : Entity_Id;
7798 Prag : Node_Id;
7799 Full_Context : Boolean);
7800 pragma Inline (Add_Unit);
7801 -- Add unit Unit_Id to the elaboration context. Prag denotes the
7802 -- pragma which prompted the inclusion of the unit to the context.
7803 -- If flag Full_Context is set, examine the nonlimited clauses of
7804 -- unit Unit_Id and add each withed unit to the context.
7805
7806 procedure Find_Elaboration_Context (Comp_Unit : Node_Id);
7807 pragma Inline (Find_Elaboration_Context);
7808 -- Examine the context items of compilation unit Comp_Unit for
7809 -- suitable elaboration-related pragmas and add all related units
7810 -- to the context.
7811
7812 ----------------
7813 -- Add_Pragma --
7814 ----------------
7815
7816 procedure Add_Pragma (Prag : Node_Id) is
7817 Prag_Args : constant List_Id :=
7818 Pragma_Argument_Associations (Prag);
7819 Prag_Nam : constant Name_Id := Pragma_Name (Prag);
7820 Unit_Arg : Node_Id;
7821
7822 begin
7823 -- Nothing to do if the pragma is not related to elaboration
7824
7825 if not Nam_In (Prag_Nam, Name_Elaborate, Name_Elaborate_All) then
7826 return;
7827
7828 -- Nothing to do when the pragma is illegal
7829
7830 elsif Error_Posted (Prag) then
7831 return;
7832 end if;
7833
7834 Unit_Arg := Get_Pragma_Arg (First (Prag_Args));
7835
7836 -- The argument of the pragma may appear in package.package form
7837
7838 if Nkind (Unit_Arg) = N_Selected_Component then
7839 Unit_Arg := Selector_Name (Unit_Arg);
7840 end if;
7841
7842 Add_Unit
7843 (Unit_Id => Entity (Unit_Arg),
7844 Prag => Prag,
7845 Full_Context => Prag_Nam = Name_Elaborate_All);
7846 end Add_Pragma;
7847
7848 --------------
7849 -- Add_Unit --
7850 --------------
7851
7852 procedure Add_Unit
7853 (Unit_Id : Entity_Id;
7854 Prag : Node_Id;
7855 Full_Context : Boolean)
7856 is
7857 Clause : Node_Id;
7858 EA_Id : Elaboration_Attributes_Id;
7859 Unit_Prag : Node_Id;
7860
7861 begin
7862 -- Nothing to do when some previous error left a with clause or a
7863 -- pragma in a bad state.
7864
7865 if No (Unit_Id) then
7866 return;
7867 end if;
7868
7869 EA_Id := Elaboration_Attributes_Of (Unit_Id);
7870 Unit_Prag := Elab_Pragma (EA_Id);
7871
7872 -- The unit is already included in the context by means of pragma
7873 -- Elaborate[_All].
7874
7875 if Present (Unit_Prag) then
7876
7877 -- Upgrade an existing pragma Elaborate when the unit is
7878 -- subject to Elaborate_All because the new pragma covers a
7879 -- larger set of units.
7880
7881 if Pragma_Name (Unit_Prag) = Name_Elaborate
7882 and then Pragma_Name (Prag) = Name_Elaborate_All
7883 then
7884 Set_Elab_Pragma (EA_Id, Prag);
7885
7886 -- Otherwise the unit retains its existing pragma and does not
7887 -- need to be included in the context again.
7888
7889 else
7890 return;
7891 end if;
7892
7893 -- Otherwise the current unit is not included in the context
7894
7895 else
7896 Set_Elab_Pragma (EA_Id, Prag);
7897 end if;
7898
7899 -- Includes all units withed by the current one when computing the
7900 -- full context.
7901
7902 if Full_Context then
7903
7904 -- Process all nonlimited with clauses found in the context of
7905 -- the current unit. Note that limited clauses do not impose an
7906 -- elaboration order.
7907
7908 Clause := First (Context_Items (Compilation_Unit (Unit_Id)));
7909 while Present (Clause) loop
7910 if Nkind (Clause) = N_With_Clause
7911 and then not Error_Posted (Clause)
7912 and then not Limited_Present (Clause)
7913 then
7914 Add_Unit
7915 (Unit_Id => Entity (Name (Clause)),
7916 Prag => Prag,
7917 Full_Context => Full_Context);
7918 end if;
7919
7920 Next (Clause);
7921 end loop;
7922 end if;
7923 end Add_Unit;
7924
7925 ------------------------------
7926 -- Find_Elaboration_Context --
7927 ------------------------------
7928
7929 procedure Find_Elaboration_Context (Comp_Unit : Node_Id) is
7930 pragma Assert (Nkind (Comp_Unit) = N_Compilation_Unit);
7931
7932 Prag : Node_Id;
7933
7934 begin
7935 -- Process all elaboration-related pragmas found in the context of
7936 -- the compilation unit.
7937
7938 Prag := First (Context_Items (Comp_Unit));
7939 while Present (Prag) loop
7940 if Nkind (Prag) = N_Pragma then
7941 Add_Pragma (Prag);
7942 end if;
7943
7944 Next (Prag);
7945 end loop;
7946 end Find_Elaboration_Context;
7947
7948 -- Local variables
7949
7950 Par_Id : Entity_Id;
7951 Unit_Id : Node_Id;
7952
7953 -- Start of processing for Collect_Elaborated_Units
7954
7955 begin
7956 -- Perform a traversal to examines the context of the main unit. The
7957 -- traversal performs the following jumps:
7958 --
7959 -- subunit -> parent subunit
7960 -- parent subunit -> body
7961 -- body -> spec
7962 -- spec -> parent spec
7963 -- parent spec -> grandparent spec and so on
7964 --
7965 -- The traversal relies on units rather than scopes because the scope
7966 -- of a subunit is some spec, while this traversal must process the
7967 -- body as well. Given that protected and task bodies can also be
7968 -- subunits, this complicates the scope approach even further.
7969
7970 Unit_Id := Unit (Cunit (Main_Unit));
7971
7972 -- Perform the following traversals when the main unit is a subunit
7973 --
7974 -- subunit -> parent subunit
7975 -- parent subunit -> body
7976
7977 while Present (Unit_Id) and then Nkind (Unit_Id) = N_Subunit loop
7978 Find_Elaboration_Context (Parent (Unit_Id));
7979
7980 -- Continue the traversal by going to the unit which contains the
7981 -- corresponding stub.
7982
7983 if Present (Corresponding_Stub (Unit_Id)) then
7984 Unit_Id :=
7985 Unit (Cunit (Get_Source_Unit (Corresponding_Stub (Unit_Id))));
7986
7987 -- Otherwise the subunit may be erroneous or left in a bad state
7988
7989 else
7990 exit;
7991 end if;
7992 end loop;
7993
7994 -- Perform the following traversal now that subunits have been taken
7995 -- care of, or the main unit is a body.
7996 --
7997 -- body -> spec
7998
7999 if Present (Unit_Id)
8000 and then Nkind_In (Unit_Id, N_Package_Body, N_Subprogram_Body)
8001 then
8002 Find_Elaboration_Context (Parent (Unit_Id));
8003
8004 -- Continue the traversal by going to the unit which contains the
8005 -- corresponding spec.
8006
8007 if Present (Corresponding_Spec (Unit_Id)) then
8008 Unit_Id :=
8009 Unit (Cunit (Get_Source_Unit (Corresponding_Spec (Unit_Id))));
8010 end if;
8011 end if;
8012
8013 -- Perform the following traversals now that the body has been taken
8014 -- care of, or the main unit is a spec.
8015 --
8016 -- spec -> parent spec
8017 -- parent spec -> grandparent spec and so on
8018
8019 if Present (Unit_Id)
8020 and then Nkind_In (Unit_Id, N_Generic_Package_Declaration,
8021 N_Generic_Subprogram_Declaration,
8022 N_Package_Declaration,
8023 N_Subprogram_Declaration)
8024 then
8025 Find_Elaboration_Context (Parent (Unit_Id));
8026
8027 -- Process a potential chain of parent units which ends with the
8028 -- main unit spec. The traversal can now safely rely on the scope
8029 -- chain.
8030
8031 Par_Id := Scope (Defining_Entity (Unit_Id));
8032 while Present (Par_Id) and then Par_Id /= Standard_Standard loop
8033 Find_Elaboration_Context (Compilation_Unit (Par_Id));
8034
8035 Par_Id := Scope (Par_Id);
8036 end loop;
8037 end if;
8038 end Collect_Elaborated_Units;
8039
8040 -------------
8041 -- Destroy --
8042 -------------
8043
8044 procedure Destroy (EA_Id : in out Elaboration_Attributes_Id) is
8045 pragma Unreferenced (EA_Id);
8046 begin
8047 null;
8048 end Destroy;
8049
8050 -----------------
8051 -- Elab_Pragma --
8052 -----------------
8053
8054 function Elab_Pragma
8055 (EA_Id : Elaboration_Attributes_Id) return Node_Id
8056 is
8057 pragma Assert (Present (EA_Id));
8058 begin
8059 return Elaboration_Attributes.Table (EA_Id).Elab_Pragma;
8060 end Elab_Pragma;
8061
8062 -------------------------------
8063 -- Elaboration_Attributes_Of --
8064 -------------------------------
8065
8066 function Elaboration_Attributes_Of
8067 (Unit_Id : Entity_Id) return Elaboration_Attributes_Id
8068 is
8069 EA_Id : Elaboration_Attributes_Id;
8070
8071 begin
8072 EA_Id := UA_Map.Get (Unit_To_Attributes_Map, Unit_Id);
8073
8074 -- The unit lacks elaboration attributes. This indicates that the
8075 -- unit is encountered for the first time. Create the elaboration
8076 -- attributes for it.
8077
8078 if not Present (EA_Id) then
8079 Elaboration_Attributes.Append
8080 ((Elab_Pragma => Empty,
8081 With_Clause => Empty));
8082 EA_Id := Elaboration_Attributes.Last;
8083
8084 -- Associate the elaboration attributes with the unit
8085
8086 UA_Map.Put (Unit_To_Attributes_Map, Unit_Id, EA_Id);
8087 end if;
8088
8089 pragma Assert (Present (EA_Id));
8090
8091 return EA_Id;
8092 end Elaboration_Attributes_Of;
8093
8094 ------------------------------
8095 -- Ensure_Prior_Elaboration --
8096 ------------------------------
8097
8098 procedure Ensure_Prior_Elaboration
8099 (N : Node_Id;
8100 Unit_Id : Entity_Id;
8101 Prag_Nam : Name_Id;
8102 In_State : Processing_In_State)
8103 is
8104 pragma Assert (Nam_In (Prag_Nam, Name_Elaborate, Name_Elaborate_All));
8105
8106 begin
8107 -- Nothing to do when the need for prior elaboration came from a
8108 -- partial finalization routine which occurs in an initialization
8109 -- context. This behaviour parallels that of the old ABE mechanism.
8110
8111 if In_State.Within_Partial_Finalization then
8112 return;
8113
8114 -- Nothing to do when the need for prior elaboration came from a task
8115 -- body and switch -gnatd.y (disable implicit pragma Elaborate_All on
8116 -- task bodies) is in effect.
8117
8118 elsif Debug_Flag_Dot_Y and then In_State.Within_Task_Body then
8119 return;
8120
8121 -- Nothing to do when the unit is elaborated prior to the main unit.
8122 -- This check must also consider the following cases:
8123 --
8124 -- * No check is made against the context of the main unit because
8125 -- this is specific to the elaboration model in effect and requires
8126 -- custom handling (see Ensure_xxx_Prior_Elaboration).
8127 --
8128 -- * Unit_Id is subject to pragma Elaborate_Body. An implicit pragma
8129 -- Elaborate[_All] MUST be generated even though Unit_Id is always
8130 -- elaborated prior to the main unit. This conservative strategy
8131 -- ensures that other units withed by Unit_Id will not lead to an
8132 -- ABE.
8133 --
8134 -- package A is package body A is
8135 -- procedure ABE; procedure ABE is ... end ABE;
8136 -- end A; end A;
8137 --
8138 -- with A;
8139 -- package B is package body B is
8140 -- pragma Elaborate_Body; procedure Proc is
8141 -- begin
8142 -- procedure Proc; A.ABE;
8143 -- package B; end Proc;
8144 -- end B;
8145 --
8146 -- with B;
8147 -- package C is package body C is
8148 -- ... ...
8149 -- end C; begin
8150 -- B.Proc;
8151 -- end C;
8152 --
8153 -- In the example above, the elaboration of C invokes B.Proc. B is
8154 -- subject to pragma Elaborate_Body. If no pragma Elaborate[_All]
8155 -- is gnerated for B in C, then the following elaboratio order will
8156 -- lead to an ABE:
8157 --
8158 -- spec of A elaborated
8159 -- spec of B elaborated
8160 -- body of B elaborated
8161 -- spec of C elaborated
8162 -- body of C elaborated <-- calls B.Proc which calls A.ABE
8163 -- body of A elaborated <-- problem
8164 --
8165 -- The generation of an implicit pragma Elaborate_All (B) ensures
8166 -- that the elaboration order mechanism will not pick the above
8167 -- order.
8168 --
8169 -- An implicit Elaborate is NOT generated when the unit is subject
8170 -- to Elaborate_Body because both pragmas have the same effect.
8171 --
8172 -- * Unit_Id is the main unit. An implicit pragma Elaborate[_All]
8173 -- MUST NOT be generated in this case because a unit cannot depend
8174 -- on its own elaboration. This case is therefore treated as valid
8175 -- prior elaboration.
8176
8177 elsif Has_Prior_Elaboration
8178 (Unit_Id => Unit_Id,
8179 Same_Unit_OK => True,
8180 Elab_Body_OK => Prag_Nam = Name_Elaborate)
8181 then
8182 return;
8183 end if;
8184
8185 -- Suggest the use of pragma Prag_Nam when the dynamic model is in
8186 -- effect.
8187
8188 if Dynamic_Elaboration_Checks then
8189 Ensure_Prior_Elaboration_Dynamic
8190 (N => N,
8191 Unit_Id => Unit_Id,
8192 Prag_Nam => Prag_Nam,
8193 In_State => In_State);
8194
8195 -- Install an implicit pragma Prag_Nam when the static model is in
8196 -- effect.
8197
8198 else
8199 pragma Assert (Static_Elaboration_Checks);
8200
8201 Ensure_Prior_Elaboration_Static
8202 (N => N,
8203 Unit_Id => Unit_Id,
8204 Prag_Nam => Prag_Nam,
8205 In_State => In_State);
8206 end if;
8207 end Ensure_Prior_Elaboration;
8208
8209 --------------------------------------
8210 -- Ensure_Prior_Elaboration_Dynamic --
8211 --------------------------------------
8212
8213 procedure Ensure_Prior_Elaboration_Dynamic
8214 (N : Node_Id;
8215 Unit_Id : Entity_Id;
8216 Prag_Nam : Name_Id;
8217 In_State : Processing_In_State)
8218 is
8219 procedure Info_Missing_Pragma;
8220 pragma Inline (Info_Missing_Pragma);
8221 -- Output information concerning missing Elaborate or Elaborate_All
8222 -- pragma with name Prag_Nam for scenario N, which would ensure the
8223 -- prior elaboration of Unit_Id.
8224
8225 -------------------------
8226 -- Info_Missing_Pragma --
8227 -------------------------
8228
8229 procedure Info_Missing_Pragma is
8230 begin
8231 -- Internal units are ignored as they cause unnecessary noise
8232
8233 if not In_Internal_Unit (Unit_Id) then
8234
8235 -- The name of the unit subjected to the elaboration pragma is
8236 -- fully qualified to improve the clarity of the info message.
8237
8238 Error_Msg_Name_1 := Prag_Nam;
8239 Error_Msg_Qual_Level := Nat'Last;
8240
8241 Error_Msg_NE ("info: missing pragma % for unit &", N, Unit_Id);
8242 Error_Msg_Qual_Level := 0;
8243 end if;
8244 end Info_Missing_Pragma;
8245
8246 -- Local variables
8247
8248 EA_Id : constant Elaboration_Attributes_Id :=
8249 Elaboration_Attributes_Of (Unit_Id);
8250 N_Lvl : Enclosing_Level_Kind;
8251 N_Rep : Scenario_Rep_Id;
8252
8253 -- Start of processing for Ensure_Prior_Elaboration_Dynamic
8254
8255 begin
8256 -- Nothing to do when the unit is guaranteed prior elaboration by
8257 -- means of a source Elaborate[_All] pragma.
8258
8259 if Present (Elab_Pragma (EA_Id)) then
8260 return;
8261 end if;
8262
8263 -- Output extra information on a missing Elaborate[_All] pragma when
8264 -- switch -gnatel (info messages on implicit Elaborate[_All] pragmas
8265 -- is in effect.
8266
8267 if Elab_Info_Messages
8268 and then not In_State.Suppress_Info_Messages
8269 then
8270 N_Rep := Scenario_Representation_Of (N, In_State);
8271 N_Lvl := Level (N_Rep);
8272
8273 -- Declaration-level scenario
8274
8275 if (Is_Suitable_Call (N) or else Is_Suitable_Instantiation (N))
8276 and then N_Lvl = Declaration_Level
8277 then
8278 null;
8279
8280 -- Library-level scenario
8281
8282 elsif N_Lvl in Library_Level then
8283 null;
8284
8285 -- Instantiation library-level scenario
8286
8287 elsif N_Lvl = Instantiation_Level then
8288 null;
8289
8290 -- Otherwise the scenario does not appear at the proper level
8291
8292 else
8293 return;
8294 end if;
8295
8296 Info_Missing_Pragma;
8297 end if;
8298 end Ensure_Prior_Elaboration_Dynamic;
8299
8300 -------------------------------------
8301 -- Ensure_Prior_Elaboration_Static --
8302 -------------------------------------
8303
8304 procedure Ensure_Prior_Elaboration_Static
8305 (N : Node_Id;
8306 Unit_Id : Entity_Id;
8307 Prag_Nam : Name_Id;
8308 In_State : Processing_In_State)
8309 is
8310 function Find_With_Clause
8311 (Items : List_Id;
8312 Withed_Id : Entity_Id) return Node_Id;
8313 pragma Inline (Find_With_Clause);
8314 -- Find a nonlimited with clause in the list of context items Items
8315 -- that withs unit Withed_Id. Return Empty if no such clause exists.
8316
8317 procedure Info_Implicit_Pragma;
8318 pragma Inline (Info_Implicit_Pragma);
8319 -- Output information concerning an implicitly generated Elaborate
8320 -- or Elaborate_All pragma with name Prag_Nam for scenario N which
8321 -- ensures the prior elaboration of unit Unit_Id.
8322
8323 ----------------------
8324 -- Find_With_Clause --
8325 ----------------------
8326
8327 function Find_With_Clause
8328 (Items : List_Id;
8329 Withed_Id : Entity_Id) return Node_Id
8330 is
8331 Item : Node_Id;
8332
8333 begin
8334 -- Examine the context clauses looking for a suitable with. Note
8335 -- that limited clauses do not affect the elaboration order.
8336
8337 Item := First (Items);
8338 while Present (Item) loop
8339 if Nkind (Item) = N_With_Clause
8340 and then not Error_Posted (Item)
8341 and then not Limited_Present (Item)
8342 and then Entity (Name (Item)) = Withed_Id
8343 then
8344 return Item;
8345 end if;
8346
8347 Next (Item);
8348 end loop;
8349
8350 return Empty;
8351 end Find_With_Clause;
8352
8353 --------------------------
8354 -- Info_Implicit_Pragma --
8355 --------------------------
8356
8357 procedure Info_Implicit_Pragma is
8358 begin
8359 -- Internal units are ignored as they cause unnecessary noise
8360
8361 if not In_Internal_Unit (Unit_Id) then
8362
8363 -- The name of the unit subjected to the elaboration pragma is
8364 -- fully qualified to improve the clarity of the info message.
8365
8366 Error_Msg_Name_1 := Prag_Nam;
8367 Error_Msg_Qual_Level := Nat'Last;
8368
8369 Error_Msg_NE
8370 ("info: implicit pragma % generated for unit &", N, Unit_Id);
8371
8372 Error_Msg_Qual_Level := 0;
8373 Output_Active_Scenarios (N, In_State);
8374 end if;
8375 end Info_Implicit_Pragma;
8376
8377 -- Local variables
8378
8379 EA_Id : constant Elaboration_Attributes_Id :=
8380 Elaboration_Attributes_Of (Unit_Id);
8381
8382 Main_Cunit : constant Node_Id := Cunit (Main_Unit);
8383 Loc : constant Source_Ptr := Sloc (Main_Cunit);
8384 Unit_Cunit : constant Node_Id := Compilation_Unit (Unit_Id);
8385 Unit_Prag : constant Node_Id := Elab_Pragma (EA_Id);
8386 Unit_With : constant Node_Id := With_Clause (EA_Id);
8387
8388 Clause : Node_Id;
8389 Items : List_Id;
8390
8391 -- Start of processing for Ensure_Prior_Elaboration_Static
8392
8393 begin
8394 -- Nothing to do when the caller has suppressed the generation of
8395 -- implicit Elaborate[_All] pragmas.
8396
8397 if In_State.Suppress_Implicit_Pragmas then
8398 return;
8399
8400 -- Nothing to do when the unit is guaranteed prior elaboration by
8401 -- means of a source Elaborate[_All] pragma.
8402
8403 elsif Present (Unit_Prag) then
8404 return;
8405
8406 -- Nothing to do when the unit has an existing implicit Elaborate or
8407 -- Elaborate_All pragma installed by a previous scenario.
8408
8409 elsif Present (Unit_With) then
8410
8411 -- The unit is already guaranteed prior elaboration by means of an
8412 -- implicit Elaborate pragma, however the current scenario imposes
8413 -- a stronger requirement of Elaborate_All. "Upgrade" the existing
8414 -- pragma to match this new requirement.
8415
8416 if Elaborate_Desirable (Unit_With)
8417 and then Prag_Nam = Name_Elaborate_All
8418 then
8419 Set_Elaborate_All_Desirable (Unit_With);
8420 Set_Elaborate_Desirable (Unit_With, False);
8421 end if;
8422
8423 return;
8424 end if;
8425
8426 -- At this point it is known that the unit has no prior elaboration
8427 -- according to pragmas and hierarchical relationships.
8428
8429 Items := Context_Items (Main_Cunit);
8430
8431 if No (Items) then
8432 Items := New_List;
8433 Set_Context_Items (Main_Cunit, Items);
8434 end if;
8435
8436 -- Locate the with clause for the unit. Note that there may not be a
8437 -- clause if the unit is visible through a subunit-body, body-spec,
8438 -- or spec-parent relationship.
8439
8440 Clause :=
8441 Find_With_Clause
8442 (Items => Items,
8443 Withed_Id => Unit_Id);
8444
8445 -- Generate:
8446 -- with Id;
8447
8448 -- Note that adding implicit with clauses is safe because analysis,
8449 -- resolution, and expansion have already taken place and it is not
8450 -- possible to interfere with visibility.
8451
8452 if No (Clause) then
8453 Clause :=
8454 Make_With_Clause (Loc,
8455 Name => New_Occurrence_Of (Unit_Id, Loc));
8456
8457 Set_Implicit_With (Clause);
8458 Set_Library_Unit (Clause, Unit_Cunit);
8459
8460 Append_To (Items, Clause);
8461 end if;
8462
8463 -- Mark the with clause depending on the pragma required
8464
8465 if Prag_Nam = Name_Elaborate then
8466 Set_Elaborate_Desirable (Clause);
8467 else
8468 Set_Elaborate_All_Desirable (Clause);
8469 end if;
8470
8471 -- The implicit Elaborate[_All] ensures the prior elaboration of
8472 -- the unit. Include the unit in the elaboration context of the
8473 -- main unit.
8474
8475 Set_With_Clause (EA_Id, Clause);
8476
8477 -- Output extra information on an implicit Elaborate[_All] pragma
8478 -- when switch -gnatel (info messages on implicit Elaborate[_All]
8479 -- pragmas is in effect.
8480
8481 if Elab_Info_Messages then
8482 Info_Implicit_Pragma;
8483 end if;
8484 end Ensure_Prior_Elaboration_Static;
8485
8486 -------------------------------
8487 -- Finalize_Elaborated_Units --
8488 -------------------------------
8489
8490 procedure Finalize_Elaborated_Units is
8491 begin
8492 UA_Map.Destroy (Unit_To_Attributes_Map);
8493 end Finalize_Elaborated_Units;
8494
8495 ---------------------------
8496 -- Has_Prior_Elaboration --
8497 ---------------------------
8498
8499 function Has_Prior_Elaboration
8500 (Unit_Id : Entity_Id;
8501 Context_OK : Boolean := False;
8502 Elab_Body_OK : Boolean := False;
8503 Same_Unit_OK : Boolean := False) return Boolean
8504 is
8505 EA_Id : constant Elaboration_Attributes_Id :=
8506 Elaboration_Attributes_Of (Unit_Id);
8507
8508 Main_Id : constant Entity_Id := Cunit_Entity (Main_Unit);
8509 Unit_Prag : constant Node_Id := Elab_Pragma (EA_Id);
8510 Unit_With : constant Node_Id := With_Clause (EA_Id);
8511
8512 begin
8513 -- A preelaborated unit is always elaborated prior to the main unit
8514
8515 if Is_Preelaborated_Unit (Unit_Id) then
8516 return True;
8517
8518 -- An internal unit is always elaborated prior to a non-internal main
8519 -- unit.
8520
8521 elsif In_Internal_Unit (Unit_Id)
8522 and then not In_Internal_Unit (Main_Id)
8523 then
8524 return True;
8525
8526 -- A unit has prior elaboration if it appears within the context
8527 -- of the main unit. Consider this case only when requested by the
8528 -- caller.
8529
8530 elsif Context_OK
8531 and then (Present (Unit_Prag) or else Present (Unit_With))
8532 then
8533 return True;
8534
8535 -- A unit whose body is elaborated together with its spec has prior
8536 -- elaboration except with respect to itself. Consider this case only
8537 -- when requested by the caller.
8538
8539 elsif Elab_Body_OK
8540 and then Has_Pragma_Elaborate_Body (Unit_Id)
8541 and then not Is_Same_Unit (Unit_Id, Main_Id)
8542 then
8543 return True;
8544
8545 -- A unit has no prior elaboration with respect to itself, but does
8546 -- not require any means of ensuring its own elaboration either.
8547 -- Treat this case as valid prior elaboration only when requested by
8548 -- the caller.
8549
8550 elsif Same_Unit_OK and then Is_Same_Unit (Unit_Id, Main_Id) then
8551 return True;
8552 end if;
8553
8554 return False;
8555 end Has_Prior_Elaboration;
8556
8557 ---------------------------------
8558 -- Initialize_Elaborated_Units --
8559 ---------------------------------
8560
8561 procedure Initialize_Elaborated_Units is
8562 begin
8563 Unit_To_Attributes_Map := UA_Map.Create (250);
8564 end Initialize_Elaborated_Units;
8565
8566 ----------------------------------
8567 -- Meet_Elaboration_Requirement --
8568 ----------------------------------
8569
8570 procedure Meet_Elaboration_Requirement
8571 (N : Node_Id;
8572 Targ_Id : Entity_Id;
8573 Req_Nam : Name_Id;
8574 In_State : Processing_In_State)
8575 is
8576 pragma Assert (Nam_In (Req_Nam, Name_Elaborate, Name_Elaborate_All));
8577
8578 Main_Id : constant Entity_Id := Cunit_Entity (Main_Unit);
8579 Unit_Id : constant Entity_Id := Find_Top_Unit (Targ_Id);
8580
8581 procedure Elaboration_Requirement_Error;
8582 pragma Inline (Elaboration_Requirement_Error);
8583 -- Emit an error concerning scenario N which has failed to meet the
8584 -- elaboration requirement.
8585
8586 function Find_Preelaboration_Pragma
8587 (Prag_Nam : Name_Id) return Node_Id;
8588 pragma Inline (Find_Preelaboration_Pragma);
8589 -- Traverse the visible declarations of unit Unit_Id and locate a
8590 -- source preelaboration-related pragma with name Prag_Nam.
8591
8592 procedure Info_Requirement_Met (Prag : Node_Id);
8593 pragma Inline (Info_Requirement_Met);
8594 -- Output information concerning pragma Prag which meets requirement
8595 -- Req_Nam.
8596
8597 -----------------------------------
8598 -- Elaboration_Requirement_Error --
8599 -----------------------------------
8600
8601 procedure Elaboration_Requirement_Error is
8602 begin
8603 if Is_Suitable_Call (N) then
8604 Info_Call
8605 (Call => N,
8606 Subp_Id => Targ_Id,
8607 Info_Msg => False,
8608 In_SPARK => True);
8609
8610 elsif Is_Suitable_Instantiation (N) then
8611 Info_Instantiation
8612 (Inst => N,
8613 Gen_Id => Targ_Id,
8614 Info_Msg => False,
8615 In_SPARK => True);
8616
8617 elsif Is_Suitable_SPARK_Refined_State_Pragma (N) then
8618 Error_Msg_N
8619 ("read of refinement constituents during elaboration in "
8620 & "SPARK", N);
8621
8622 elsif Is_Suitable_Variable_Reference (N) then
8623 Info_Variable_Reference
8624 (Ref => N,
8625 Var_Id => Targ_Id,
8626 Info_Msg => False,
8627 In_SPARK => True);
8628
8629 -- No other scenario may impose a requirement on the context of
8630 -- the main unit.
8631
8632 else
8633 pragma Assert (False);
8634 return;
8635 end if;
8636
8637 Error_Msg_Name_1 := Req_Nam;
8638 Error_Msg_Node_2 := Unit_Id;
8639 Error_Msg_NE ("\\unit & requires pragma % for &", N, Main_Id);
8640
8641 Output_Active_Scenarios (N, In_State);
8642 end Elaboration_Requirement_Error;
8643
8644 --------------------------------
8645 -- Find_Preelaboration_Pragma --
8646 --------------------------------
8647
8648 function Find_Preelaboration_Pragma
8649 (Prag_Nam : Name_Id) return Node_Id
8650 is
8651 Spec : constant Node_Id := Parent (Unit_Id);
8652 Decl : Node_Id;
8653
8654 begin
8655 -- A preelaboration-related pragma comes from source and appears
8656 -- at the top of the visible declarations of a package.
8657
8658 if Nkind (Spec) = N_Package_Specification then
8659 Decl := First (Visible_Declarations (Spec));
8660 while Present (Decl) loop
8661 if Comes_From_Source (Decl) then
8662 if Nkind (Decl) = N_Pragma
8663 and then Pragma_Name (Decl) = Prag_Nam
8664 then
8665 return Decl;
8666
8667 -- Otherwise the construct terminates the region where
8668 -- the preelaboration-related pragma may appear.
8669
8670 else
8671 exit;
8672 end if;
8673 end if;
8674
8675 Next (Decl);
8676 end loop;
8677 end if;
8678
8679 return Empty;
8680 end Find_Preelaboration_Pragma;
8681
8682 --------------------------
8683 -- Info_Requirement_Met --
8684 --------------------------
8685
8686 procedure Info_Requirement_Met (Prag : Node_Id) is
8687 pragma Assert (Present (Prag));
8688
8689 begin
8690 Error_Msg_Name_1 := Req_Nam;
8691 Error_Msg_Sloc := Sloc (Prag);
8692 Error_Msg_NE
8693 ("\\% requirement for unit & met by pragma #", N, Unit_Id);
8694 end Info_Requirement_Met;
8695
8696 -- Local variables
8697
8698 EA_Id : Elaboration_Attributes_Id;
8699 Elab_Nam : Name_Id;
8700 Req_Met : Boolean;
8701 Unit_Prag : Node_Id;
8702
8703 -- Start of processing for Meet_Elaboration_Requirement
8704
8705 begin
8706 -- Assume that the requirement has not been met
8707
8708 Req_Met := False;
8709
8710 -- If the target is within the main unit, either at the source level
8711 -- or through an instantiation, then there is no real requirement to
8712 -- meet because the main unit cannot force its own elaboration by
8713 -- means of an Elaborate[_All] pragma. Treat this case as valid
8714 -- coverage.
8715
8716 if In_Extended_Main_Code_Unit (Targ_Id) then
8717 Req_Met := True;
8718
8719 -- Otherwise the target resides in an external unit
8720
8721 -- The requirement is met when the target comes from an internal unit
8722 -- because such a unit is elaborated prior to a non-internal unit.
8723
8724 elsif In_Internal_Unit (Unit_Id)
8725 and then not In_Internal_Unit (Main_Id)
8726 then
8727 Req_Met := True;
8728
8729 -- The requirement is met when the target comes from a preelaborated
8730 -- unit. This portion must parallel predicate Is_Preelaborated_Unit.
8731
8732 elsif Is_Preelaborated_Unit (Unit_Id) then
8733 Req_Met := True;
8734
8735 -- Output extra information when switch -gnatel (info messages on
8736 -- implicit Elaborate[_All] pragmas.
8737
8738 if Elab_Info_Messages
8739 and then not In_State.Suppress_Info_Messages
8740 then
8741 if Is_Preelaborated (Unit_Id) then
8742 Elab_Nam := Name_Preelaborate;
8743
8744 elsif Is_Pure (Unit_Id) then
8745 Elab_Nam := Name_Pure;
8746
8747 elsif Is_Remote_Call_Interface (Unit_Id) then
8748 Elab_Nam := Name_Remote_Call_Interface;
8749
8750 elsif Is_Remote_Types (Unit_Id) then
8751 Elab_Nam := Name_Remote_Types;
8752
8753 else
8754 pragma Assert (Is_Shared_Passive (Unit_Id));
8755 Elab_Nam := Name_Shared_Passive;
8756 end if;
8757
8758 Info_Requirement_Met (Find_Preelaboration_Pragma (Elab_Nam));
8759 end if;
8760
8761 -- Determine whether the context of the main unit has a pragma strong
8762 -- enough to meet the requirement.
8763
8764 else
8765 EA_Id := Elaboration_Attributes_Of (Unit_Id);
8766 Unit_Prag := Elab_Pragma (EA_Id);
8767
8768 -- The pragma must be either Elaborate_All or be as strong as the
8769 -- requirement.
8770
8771 if Present (Unit_Prag)
8772 and then Nam_In (Pragma_Name (Unit_Prag), Name_Elaborate_All,
8773 Req_Nam)
8774 then
8775 Req_Met := True;
8776
8777 -- Output extra information when switch -gnatel (info messages
8778 -- on implicit Elaborate[_All] pragmas.
8779
8780 if Elab_Info_Messages
8781 and then not In_State.Suppress_Info_Messages
8782 then
8783 Info_Requirement_Met (Unit_Prag);
8784 end if;
8785 end if;
8786 end if;
8787
8788 -- The requirement was not met by the context of the main unit, issue
8789 -- an error.
8790
8791 if not Req_Met then
8792 Elaboration_Requirement_Error;
8793 end if;
8794 end Meet_Elaboration_Requirement;
8795
8796 -------------
8797 -- Present --
8798 -------------
8799
8800 function Present (EA_Id : Elaboration_Attributes_Id) return Boolean is
8801 begin
8802 return EA_Id /= No_Elaboration_Attributes;
8803 end Present;
8804
8805 ---------------------
8806 -- Set_Elab_Pragma --
8807 ---------------------
8808
8809 procedure Set_Elab_Pragma
8810 (EA_Id : Elaboration_Attributes_Id;
8811 Prag : Node_Id)
8812 is
8813 pragma Assert (Present (EA_Id));
8814 begin
8815 Elaboration_Attributes.Table (EA_Id).Elab_Pragma := Prag;
8816 end Set_Elab_Pragma;
8817
8818 ---------------------
8819 -- Set_With_Clause --
8820 ---------------------
8821
8822 procedure Set_With_Clause
8823 (EA_Id : Elaboration_Attributes_Id;
8824 Clause : Node_Id)
8825 is
8826 pragma Assert (Present (EA_Id));
8827 begin
8828 Elaboration_Attributes.Table (EA_Id).With_Clause := Clause;
8829 end Set_With_Clause;
8830
8831 -----------------
8832 -- With_Clause --
8833 -----------------
8834
8835 function With_Clause
8836 (EA_Id : Elaboration_Attributes_Id) return Node_Id
8837 is
8838 pragma Assert (Present (EA_Id));
8839 begin
8840 return Elaboration_Attributes.Table (EA_Id).With_Clause;
8841 end With_Clause;
8842 end Elaborated_Units;
8843
8844 ------------------------------
8845 -- Elaboration_Phase_Active --
8846 ------------------------------
8847
8848 function Elaboration_Phase_Active return Boolean is
8849 begin
8850 return Elaboration_Phase = Active;
8851 end Elaboration_Phase_Active;
8852
8853 ----------------------------------
8854 -- Finalize_All_Data_Structures --
8855 ----------------------------------
8856
8857 procedure Finalize_All_Data_Structures is
8858 begin
8859 Finalize_Body_Processor;
8860 Finalize_Early_Call_Region_Processor;
8861 Finalize_Elaborated_Units;
8862 Finalize_Internal_Representation;
8863 Finalize_Invocation_Graph;
8864 Finalize_Scenario_Storage;
8865 end Finalize_All_Data_Structures;
8866
8867 -----------------------------
8868 -- Find_Enclosing_Instance --
8869 -----------------------------
8870
8871 function Find_Enclosing_Instance (N : Node_Id) return Node_Id is
8872 Par : Node_Id;
8873
8874 begin
8875 -- Climb the parent chain looking for an enclosing instance spec or body
8876
8877 Par := N;
8878 while Present (Par) loop
8879 if Nkind_In (Par, N_Package_Body,
8880 N_Package_Declaration,
8881 N_Subprogram_Body,
8882 N_Subprogram_Declaration)
8883 and then Is_Generic_Instance (Unique_Defining_Entity (Par))
8884 then
8885 return Par;
8886 end if;
8887
8888 Par := Parent (Par);
8889 end loop;
8890
8891 return Empty;
8892 end Find_Enclosing_Instance;
8893
8894 --------------------------
8895 -- Find_Enclosing_Level --
8896 --------------------------
8897
8898 function Find_Enclosing_Level (N : Node_Id) return Enclosing_Level_Kind is
8899 function Level_Of (Unit : Node_Id) return Enclosing_Level_Kind;
8900 pragma Inline (Level_Of);
8901 -- Obtain the corresponding level of unit Unit
8902
8903 --------------
8904 -- Level_Of --
8905 --------------
8906
8907 function Level_Of (Unit : Node_Id) return Enclosing_Level_Kind is
8908 Spec_Id : Entity_Id;
8909
8910 begin
8911 if Nkind (Unit) in N_Generic_Instantiation then
8912 return Instantiation_Level;
8913
8914 elsif Nkind (Unit) = N_Generic_Package_Declaration then
8915 return Generic_Spec_Level;
8916
8917 elsif Nkind (Unit) = N_Package_Declaration then
8918 return Library_Spec_Level;
8919
8920 elsif Nkind (Unit) = N_Package_Body then
8921 Spec_Id := Corresponding_Spec (Unit);
8922
8923 -- The body belongs to a generic package
8924
8925 if Present (Spec_Id)
8926 and then Ekind (Spec_Id) = E_Generic_Package
8927 then
8928 return Generic_Body_Level;
8929
8930 -- Otherwise the body belongs to a non-generic package. This also
8931 -- treats an illegal package body without a corresponding spec as
8932 -- a non-generic package body.
8933
8934 else
8935 return Library_Body_Level;
8936 end if;
8937 end if;
8938
8939 return No_Level;
8940 end Level_Of;
8941
8942 -- Local variables
8943
8944 Context : Node_Id;
8945 Curr : Node_Id;
8946 Prev : Node_Id;
8947
8948 -- Start of processing for Find_Enclosing_Level
8949
8950 begin
8951 -- Call markers and instantiations which appear at the declaration level
8952 -- but are later relocated in a different context retain their original
8953 -- declaration level.
8954
8955 if Nkind_In (N, N_Call_Marker,
8956 N_Function_Instantiation,
8957 N_Package_Instantiation,
8958 N_Procedure_Instantiation)
8959 and then Is_Declaration_Level_Node (N)
8960 then
8961 return Declaration_Level;
8962 end if;
8963
8964 -- Climb the parent chain looking at the enclosing levels
8965
8966 Prev := N;
8967 Curr := Parent (Prev);
8968 while Present (Curr) loop
8969
8970 -- A traversal from a subunit continues via the corresponding stub
8971
8972 if Nkind (Curr) = N_Subunit then
8973 Curr := Corresponding_Stub (Curr);
8974
8975 -- The current construct is a package. Packages are ignored because
8976 -- they are always elaborated when the enclosing context is invoked
8977 -- or elaborated.
8978
8979 elsif Nkind_In (Curr, N_Package_Body, N_Package_Declaration) then
8980 null;
8981
8982 -- The current construct is a block statement
8983
8984 elsif Nkind (Curr) = N_Block_Statement then
8985
8986 -- Ignore internally generated blocks created by the expander for
8987 -- various purposes such as abort defer/undefer.
8988
8989 if not Comes_From_Source (Curr) then
8990 null;
8991
8992 -- If the traversal came from the handled sequence of statments,
8993 -- then the node appears at the level of the enclosing construct.
8994 -- This is a more reliable test because transients scopes within
8995 -- the declarative region of the encapsulator are hard to detect.
8996
8997 elsif Nkind (Prev) = N_Handled_Sequence_Of_Statements
8998 and then Handled_Statement_Sequence (Curr) = Prev
8999 then
9000 return Find_Enclosing_Level (Parent (Curr));
9001
9002 -- Otherwise the traversal came from the declarations, the node is
9003 -- at the declaration level.
9004
9005 else
9006 return Declaration_Level;
9007 end if;
9008
9009 -- The current construct is a declaration-level encapsulator
9010
9011 elsif Nkind_In (Curr, N_Entry_Body,
9012 N_Subprogram_Body,
9013 N_Task_Body)
9014 then
9015 -- If the traversal came from the handled sequence of statments,
9016 -- then the node cannot possibly appear at any level. This is
9017 -- a more reliable test because transients scopes within the
9018 -- declarative region of the encapsulator are hard to detect.
9019
9020 if Nkind (Prev) = N_Handled_Sequence_Of_Statements
9021 and then Handled_Statement_Sequence (Curr) = Prev
9022 then
9023 return No_Level;
9024
9025 -- Otherwise the traversal came from the declarations, the node is
9026 -- at the declaration level.
9027
9028 else
9029 return Declaration_Level;
9030 end if;
9031
9032 -- The current construct is a non-library-level encapsulator which
9033 -- indicates that the node cannot possibly appear at any level. Note
9034 -- that the check must come after the declaration-level check because
9035 -- both predicates share certain nodes.
9036
9037 elsif Is_Non_Library_Level_Encapsulator (Curr) then
9038 Context := Parent (Curr);
9039
9040 -- The sole exception is when the encapsulator is the compilation
9041 -- utit itself because the compilation unit node requires special
9042 -- processing (see below).
9043
9044 if Present (Context)
9045 and then Nkind (Context) = N_Compilation_Unit
9046 then
9047 null;
9048
9049 -- Otherwise the node is not at any level
9050
9051 else
9052 return No_Level;
9053 end if;
9054
9055 -- The current construct is a compilation unit. The node appears at
9056 -- the [generic] library level when the unit is a [generic] package.
9057
9058 elsif Nkind (Curr) = N_Compilation_Unit then
9059 return Level_Of (Unit (Curr));
9060 end if;
9061
9062 Prev := Curr;
9063 Curr := Parent (Prev);
9064 end loop;
9065
9066 return No_Level;
9067 end Find_Enclosing_Level;
9068
9069 -------------------
9070 -- Find_Top_Unit --
9071 -------------------
9072
9073 function Find_Top_Unit (N : Node_Or_Entity_Id) return Entity_Id is
9074 begin
9075 return Find_Unit_Entity (Unit (Cunit (Get_Top_Level_Code_Unit (N))));
9076 end Find_Top_Unit;
9077
9078 ----------------------
9079 -- Find_Unit_Entity --
9080 ----------------------
9081
9082 function Find_Unit_Entity (N : Node_Id) return Entity_Id is
9083 Context : constant Node_Id := Parent (N);
9084 Orig_N : constant Node_Id := Original_Node (N);
9085
9086 begin
9087 -- The unit denotes a package body of an instantiation which acts as
9088 -- a compilation unit. The proper entity is that of the package spec.
9089
9090 if Nkind (N) = N_Package_Body
9091 and then Nkind (Orig_N) = N_Package_Instantiation
9092 and then Nkind (Context) = N_Compilation_Unit
9093 then
9094 return Corresponding_Spec (N);
9095
9096 -- The unit denotes an anonymous package created to wrap a subprogram
9097 -- instantiation which acts as a compilation unit. The proper entity is
9098 -- that of the "related instance".
9099
9100 elsif Nkind (N) = N_Package_Declaration
9101 and then Nkind_In (Orig_N, N_Function_Instantiation,
9102 N_Procedure_Instantiation)
9103 and then Nkind (Context) = N_Compilation_Unit
9104 then
9105 return
9106 Related_Instance (Defining_Entity (N, Concurrent_Subunit => True));
9107
9108 -- Otherwise the proper entity is the defining entity
9109
9110 else
9111 return Defining_Entity (N, Concurrent_Subunit => True);
9112 end if;
9113 end Find_Unit_Entity;
9114
9115 -----------------------
9116 -- First_Formal_Type --
9117 -----------------------
9118
9119 function First_Formal_Type (Subp_Id : Entity_Id) return Entity_Id is
9120 Formal_Id : constant Entity_Id := First_Formal (Subp_Id);
9121 Typ : Entity_Id;
9122
9123 begin
9124 if Present (Formal_Id) then
9125 Typ := Etype (Formal_Id);
9126
9127 -- Handle various combinations of concurrent and private types
9128
9129 loop
9130 if Ekind_In (Typ, E_Protected_Type, E_Task_Type)
9131 and then Present (Anonymous_Object (Typ))
9132 then
9133 Typ := Anonymous_Object (Typ);
9134
9135 elsif Is_Concurrent_Record_Type (Typ) then
9136 Typ := Corresponding_Concurrent_Type (Typ);
9137
9138 elsif Is_Private_Type (Typ) and then Present (Full_View (Typ)) then
9139 Typ := Full_View (Typ);
9140
9141 else
9142 exit;
9143 end if;
9144 end loop;
9145
9146 return Typ;
9147 end if;
9148
9149 return Empty;
9150 end First_Formal_Type;
9151
9152 ------------------------------
9153 -- Guaranteed_ABE_Processor --
9154 ------------------------------
9155
9156 package body Guaranteed_ABE_Processor is
9157 function Is_Guaranteed_ABE
9158 (N : Node_Id;
9159 Target_Decl : Node_Id;
9160 Target_Body : Node_Id) return Boolean;
9161 pragma Inline (Is_Guaranteed_ABE);
9162 -- Determine whether scenario N with a target described by its initial
9163 -- declaration Target_Decl and body Target_Decl results in a guaranteed
9164 -- ABE.
9165
9166 procedure Process_Guaranteed_ABE_Activation
9167 (Call : Node_Id;
9168 Call_Rep : Scenario_Rep_Id;
9169 Obj_Id : Entity_Id;
9170 Obj_Rep : Target_Rep_Id;
9171 Task_Typ : Entity_Id;
9172 Task_Rep : Target_Rep_Id;
9173 In_State : Processing_In_State);
9174 pragma Inline (Process_Guaranteed_ABE_Activation);
9175 -- Perform common guaranteed ABE checks and diagnostics for activation
9176 -- call Call which activates object Obj_Id of task type Task_Typ. Formal
9177 -- Call_Rep denotes the representation of the call. Obj_Rep denotes the
9178 -- representation of the object. Task_Rep denotes the representation of
9179 -- the task type. In_State is the current state of the Processing phase.
9180
9181 procedure Process_Guaranteed_ABE_Call
9182 (Call : Node_Id;
9183 Call_Rep : Scenario_Rep_Id;
9184 In_State : Processing_In_State);
9185 pragma Inline (Process_Guaranteed_ABE_Call);
9186 -- Perform common guaranteed ABE checks and diagnostics for call Call
9187 -- with representation Call_Rep. In_State denotes the current state of
9188 -- the Processing phase.
9189
9190 procedure Process_Guaranteed_ABE_Instantiation
9191 (Inst : Node_Id;
9192 Inst_Rep : Scenario_Rep_Id;
9193 In_State : Processing_In_State);
9194 pragma Inline (Process_Guaranteed_ABE_Instantiation);
9195 -- Perform common guaranteed ABE checks and diagnostics for instance
9196 -- Inst with representation Inst_Rep. In_State is the current state of
9197 -- the Processing phase.
9198
9199 -----------------------
9200 -- Is_Guaranteed_ABE --
9201 -----------------------
9202
9203 function Is_Guaranteed_ABE
9204 (N : Node_Id;
9205 Target_Decl : Node_Id;
9206 Target_Body : Node_Id) return Boolean
9207 is
9208 begin
9209 -- Avoid cascaded errors if there were previous serious infractions.
9210 -- As a result the scenario will not be treated as a guaranteed ABE.
9211 -- This behaviour parallels that of the old ABE mechanism.
9212
9213 if Serious_Errors_Detected > 0 then
9214 return False;
9215
9216 -- The scenario and the target appear in the same context ignoring
9217 -- enclosing library levels.
9218
9219 elsif In_Same_Context (N, Target_Decl) then
9220
9221 -- The target body has already been encountered. The scenario
9222 -- results in a guaranteed ABE if it appears prior to the body.
9223
9224 if Present (Target_Body) then
9225 return Earlier_In_Extended_Unit (N, Target_Body);
9226
9227 -- Otherwise the body has not been encountered yet. The scenario
9228 -- is a guaranteed ABE since the body will appear later. It is
9229 -- assumed that the caller has already ensured that the scenario
9230 -- is ABE-safe because optional bodies are not considered here.
9231
9232 else
9233 return True;
9234 end if;
9235 end if;
9236
9237 return False;
9238 end Is_Guaranteed_ABE;
9239
9240 ----------------------------
9241 -- Process_Guaranteed_ABE --
9242 ----------------------------
9243
9244 procedure Process_Guaranteed_ABE
9245 (N : Node_Id;
9246 In_State : Processing_In_State)
9247 is
9248 Scen : constant Node_Id := Scenario (N);
9249 Scen_Rep : Scenario_Rep_Id;
9250
9251 begin
9252 -- Add the current scenario to the stack of active scenarios
9253
9254 Push_Active_Scenario (Scen);
9255
9256 -- Only calls, instantiations, and task activations may result in a
9257 -- guaranteed ABE.
9258
9259 -- Call or task activation
9260
9261 if Is_Suitable_Call (Scen) then
9262 Scen_Rep := Scenario_Representation_Of (Scen, In_State);
9263
9264 if Kind (Scen_Rep) = Call_Scenario then
9265 Process_Guaranteed_ABE_Call
9266 (Call => Scen,
9267 Call_Rep => Scen_Rep,
9268 In_State => In_State);
9269
9270 else
9271 pragma Assert (Kind (Scen_Rep) = Task_Activation_Scenario);
9272
9273 Process_Activation
9274 (Call => Scen,
9275 Call_Rep => Scenario_Representation_Of (Scen, In_State),
9276 Processor => Process_Guaranteed_ABE_Activation'Access,
9277 In_State => In_State);
9278 end if;
9279
9280 -- Instantiation
9281
9282 elsif Is_Suitable_Instantiation (Scen) then
9283 Process_Guaranteed_ABE_Instantiation
9284 (Inst => Scen,
9285 Inst_Rep => Scenario_Representation_Of (Scen, In_State),
9286 In_State => In_State);
9287 end if;
9288
9289 -- Remove the current scenario from the stack of active scenarios
9290 -- once all ABE diagnostics and checks have been performed.
9291
9292 Pop_Active_Scenario (Scen);
9293 end Process_Guaranteed_ABE;
9294
9295 ---------------------------------------
9296 -- Process_Guaranteed_ABE_Activation --
9297 ---------------------------------------
9298
9299 procedure Process_Guaranteed_ABE_Activation
9300 (Call : Node_Id;
9301 Call_Rep : Scenario_Rep_Id;
9302 Obj_Id : Entity_Id;
9303 Obj_Rep : Target_Rep_Id;
9304 Task_Typ : Entity_Id;
9305 Task_Rep : Target_Rep_Id;
9306 In_State : Processing_In_State)
9307 is
9308 Spec_Decl : constant Node_Id := Spec_Declaration (Task_Rep);
9309
9310 Check_OK : constant Boolean :=
9311 not In_State.Suppress_Checks
9312 and then Ghost_Mode_Of (Obj_Rep) /= Is_Ignored
9313 and then Ghost_Mode_Of (Task_Rep) /= Is_Ignored
9314 and then Elaboration_Checks_OK (Obj_Rep)
9315 and then Elaboration_Checks_OK (Task_Rep);
9316 -- A run-time ABE check may be installed only when the object and the
9317 -- task type have active elaboration checks, and both are not ignored
9318 -- Ghost constructs.
9319
9320 begin
9321 -- Nothing to do when the root scenario appears at the declaration
9322 -- level and the task is in the same unit, but outside this context.
9323 --
9324 -- task type Task_Typ; -- task declaration
9325 --
9326 -- procedure Proc is
9327 -- function A ... is
9328 -- begin
9329 -- if Some_Condition then
9330 -- declare
9331 -- T : Task_Typ;
9332 -- begin
9333 -- <activation call> -- activation site
9334 -- end;
9335 -- ...
9336 -- end A;
9337 --
9338 -- X : ... := A; -- root scenario
9339 -- ...
9340 --
9341 -- task body Task_Typ is
9342 -- ...
9343 -- end Task_Typ;
9344 --
9345 -- In the example above, the context of X is the declarative list
9346 -- of Proc. The "elaboration" of X may reach the activation of T
9347 -- whose body is defined outside of X's context. The task body is
9348 -- relevant only when Proc is invoked, but this happens only in
9349 -- "normal" elaboration, therefore the task body must not be
9350 -- considered if this is not the case.
9351
9352 if Is_Up_Level_Target
9353 (Targ_Decl => Spec_Decl,
9354 In_State => In_State)
9355 then
9356 return;
9357
9358 -- Nothing to do when the activation is ABE-safe
9359 --
9360 -- generic
9361 -- package Gen is
9362 -- task type Task_Typ;
9363 -- end Gen;
9364 --
9365 -- package body Gen is
9366 -- task body Task_Typ is
9367 -- begin
9368 -- ...
9369 -- end Task_Typ;
9370 -- end Gen;
9371 --
9372 -- with Gen;
9373 -- procedure Main is
9374 -- package Nested is
9375 -- package Inst is new Gen;
9376 -- T : Inst.Task_Typ;
9377 -- end Nested; -- safe activation
9378 -- ...
9379
9380 elsif Is_Safe_Activation (Call, Task_Rep) then
9381 return;
9382
9383 -- An activation call leads to a guaranteed ABE when the activation
9384 -- call and the task appear within the same context ignoring library
9385 -- levels, and the body of the task has not been seen yet or appears
9386 -- after the activation call.
9387 --
9388 -- procedure Guaranteed_ABE is
9389 -- task type Task_Typ;
9390 --
9391 -- package Nested is
9392 -- T : Task_Typ;
9393 -- <activation call> -- guaranteed ABE
9394 -- end Nested;
9395 --
9396 -- task body Task_Typ is
9397 -- ...
9398 -- end Task_Typ;
9399 -- ...
9400
9401 elsif Is_Guaranteed_ABE
9402 (N => Call,
9403 Target_Decl => Spec_Decl,
9404 Target_Body => Body_Declaration (Task_Rep))
9405 then
9406 if Elaboration_Warnings_OK (Call_Rep) then
9407 Error_Msg_Sloc := Sloc (Call);
9408 Error_Msg_N
9409 ("??task & will be activated # before elaboration of its "
9410 & "body", Obj_Id);
9411 Error_Msg_N
9412 ("\Program_Error will be raised at run time", Obj_Id);
9413 end if;
9414
9415 -- Mark the activation call as a guaranteed ABE
9416
9417 Set_Is_Known_Guaranteed_ABE (Call);
9418
9419 -- Install a run-time ABE failue because this activation call will
9420 -- always result in an ABE.
9421
9422 if Check_OK then
9423 Install_Scenario_ABE_Failure
9424 (N => Call,
9425 Targ_Id => Task_Typ,
9426 Targ_Rep => Task_Rep,
9427 Disable => Obj_Rep);
9428 end if;
9429 end if;
9430 end Process_Guaranteed_ABE_Activation;
9431
9432 ---------------------------------
9433 -- Process_Guaranteed_ABE_Call --
9434 ---------------------------------
9435
9436 procedure Process_Guaranteed_ABE_Call
9437 (Call : Node_Id;
9438 Call_Rep : Scenario_Rep_Id;
9439 In_State : Processing_In_State)
9440 is
9441 Subp_Id : constant Entity_Id := Target (Call_Rep);
9442 Subp_Rep : constant Target_Rep_Id :=
9443 Target_Representation_Of (Subp_Id, In_State);
9444 Spec_Decl : constant Node_Id := Spec_Declaration (Subp_Rep);
9445
9446 Check_OK : constant Boolean :=
9447 not In_State.Suppress_Checks
9448 and then Ghost_Mode_Of (Call_Rep) /= Is_Ignored
9449 and then Ghost_Mode_Of (Subp_Rep) /= Is_Ignored
9450 and then Elaboration_Checks_OK (Call_Rep)
9451 and then Elaboration_Checks_OK (Subp_Rep);
9452 -- A run-time ABE check may be installed only when both the call
9453 -- and the target have active elaboration checks, and both are not
9454 -- ignored Ghost constructs.
9455
9456 begin
9457 -- Nothing to do when the root scenario appears at the declaration
9458 -- level and the target is in the same unit but outside this context.
9459 --
9460 -- function B ...; -- target declaration
9461 --
9462 -- procedure Proc is
9463 -- function A ... is
9464 -- begin
9465 -- if Some_Condition then
9466 -- return B; -- call site
9467 -- ...
9468 -- end A;
9469 --
9470 -- X : ... := A; -- root scenario
9471 -- ...
9472 --
9473 -- function B ... is
9474 -- ...
9475 -- end B;
9476 --
9477 -- In the example above, the context of X is the declarative region
9478 -- of Proc. The "elaboration" of X may eventually reach B which is
9479 -- defined outside of X's context. B is relevant only when Proc is
9480 -- invoked, but this happens only by means of "normal" elaboration,
9481 -- therefore B must not be considered if this is not the case.
9482
9483 if Is_Up_Level_Target
9484 (Targ_Decl => Spec_Decl,
9485 In_State => In_State)
9486 then
9487 return;
9488
9489 -- Nothing to do when the call is ABE-safe
9490 --
9491 -- generic
9492 -- function Gen ...;
9493 --
9494 -- function Gen ... is
9495 -- begin
9496 -- ...
9497 -- end Gen;
9498 --
9499 -- with Gen;
9500 -- procedure Main is
9501 -- function Inst is new Gen;
9502 -- X : ... := Inst; -- safe call
9503 -- ...
9504
9505 elsif Is_Safe_Call (Call, Subp_Id, Subp_Rep) then
9506 return;
9507
9508 -- A call leads to a guaranteed ABE when the call and the target
9509 -- appear within the same context ignoring library levels, and the
9510 -- body of the target has not been seen yet or appears after the
9511 -- call.
9512 --
9513 -- procedure Guaranteed_ABE is
9514 -- function Func ...;
9515 --
9516 -- package Nested is
9517 -- Obj : ... := Func; -- guaranteed ABE
9518 -- end Nested;
9519 --
9520 -- function Func ... is
9521 -- ...
9522 -- end Func;
9523 -- ...
9524
9525 elsif Is_Guaranteed_ABE
9526 (N => Call,
9527 Target_Decl => Spec_Decl,
9528 Target_Body => Body_Declaration (Subp_Rep))
9529 then
9530 if Elaboration_Warnings_OK (Call_Rep) then
9531 Error_Msg_NE
9532 ("??cannot call & before body seen", Call, Subp_Id);
9533 Error_Msg_N ("\Program_Error will be raised at run time", Call);
9534 end if;
9535
9536 -- Mark the call as a guarnateed ABE
9537
9538 Set_Is_Known_Guaranteed_ABE (Call);
9539
9540 -- Install a run-time ABE failure because the call will always
9541 -- result in an ABE.
9542
9543 if Check_OK then
9544 Install_Scenario_ABE_Failure
9545 (N => Call,
9546 Targ_Id => Subp_Id,
9547 Targ_Rep => Subp_Rep,
9548 Disable => Call_Rep);
9549 end if;
9550 end if;
9551 end Process_Guaranteed_ABE_Call;
9552
9553 ------------------------------------------
9554 -- Process_Guaranteed_ABE_Instantiation --
9555 ------------------------------------------
9556
9557 procedure Process_Guaranteed_ABE_Instantiation
9558 (Inst : Node_Id;
9559 Inst_Rep : Scenario_Rep_Id;
9560 In_State : Processing_In_State)
9561 is
9562 Gen_Id : constant Entity_Id := Target (Inst_Rep);
9563 Gen_Rep : constant Target_Rep_Id :=
9564 Target_Representation_Of (Gen_Id, In_State);
9565 Spec_Decl : constant Node_Id := Spec_Declaration (Gen_Rep);
9566
9567 Check_OK : constant Boolean :=
9568 not In_State.Suppress_Checks
9569 and then Ghost_Mode_Of (Inst_Rep) /= Is_Ignored
9570 and then Ghost_Mode_Of (Gen_Rep) /= Is_Ignored
9571 and then Elaboration_Checks_OK (Inst_Rep)
9572 and then Elaboration_Checks_OK (Gen_Rep);
9573 -- A run-time ABE check may be installed only when both the instance
9574 -- and the generic have active elaboration checks and both are not
9575 -- ignored Ghost constructs.
9576
9577 begin
9578 -- Nothing to do when the root scenario appears at the declaration
9579 -- level and the generic is in the same unit, but outside this
9580 -- context.
9581 --
9582 -- generic
9583 -- procedure Gen is ...; -- generic declaration
9584 --
9585 -- procedure Proc is
9586 -- function A ... is
9587 -- begin
9588 -- if Some_Condition then
9589 -- declare
9590 -- procedure I is new Gen; -- instantiation site
9591 -- ...
9592 -- ...
9593 -- end A;
9594 --
9595 -- X : ... := A; -- root scenario
9596 -- ...
9597 --
9598 -- procedure Gen is
9599 -- ...
9600 -- end Gen;
9601 --
9602 -- In the example above, the context of X is the declarative region
9603 -- of Proc. The "elaboration" of X may eventually reach Gen which
9604 -- appears outside of X's context. Gen is relevant only when Proc is
9605 -- invoked, but this happens only by means of "normal" elaboration,
9606 -- therefore Gen must not be considered if this is not the case.
9607
9608 if Is_Up_Level_Target
9609 (Targ_Decl => Spec_Decl,
9610 In_State => In_State)
9611 then
9612 return;
9613
9614 -- Nothing to do when the instantiation is ABE-safe
9615 --
9616 -- generic
9617 -- package Gen is
9618 -- ...
9619 -- end Gen;
9620 --
9621 -- package body Gen is
9622 -- ...
9623 -- end Gen;
9624 --
9625 -- with Gen;
9626 -- procedure Main is
9627 -- package Inst is new Gen (ABE); -- safe instantiation
9628 -- ...
9629
9630 elsif Is_Safe_Instantiation (Inst, Gen_Id, Gen_Rep) then
9631 return;
9632
9633 -- An instantiation leads to a guaranteed ABE when the instantiation
9634 -- and the generic appear within the same context ignoring library
9635 -- levels, and the body of the generic has not been seen yet or
9636 -- appears after the instantiation.
9637 --
9638 -- procedure Guaranteed_ABE is
9639 -- generic
9640 -- procedure Gen;
9641 --
9642 -- package Nested is
9643 -- procedure Inst is new Gen; -- guaranteed ABE
9644 -- end Nested;
9645 --
9646 -- procedure Gen is
9647 -- ...
9648 -- end Gen;
9649 -- ...
9650
9651 elsif Is_Guaranteed_ABE
9652 (N => Inst,
9653 Target_Decl => Spec_Decl,
9654 Target_Body => Body_Declaration (Gen_Rep))
9655 then
9656 if Elaboration_Warnings_OK (Inst_Rep) then
9657 Error_Msg_NE
9658 ("??cannot instantiate & before body seen", Inst, Gen_Id);
9659 Error_Msg_N ("\Program_Error will be raised at run time", Inst);
9660 end if;
9661
9662 -- Mark the instantiation as a guarantee ABE. This automatically
9663 -- suppresses the instantiation of the generic body.
9664
9665 Set_Is_Known_Guaranteed_ABE (Inst);
9666
9667 -- Install a run-time ABE failure because the instantiation will
9668 -- always result in an ABE.
9669
9670 if Check_OK then
9671 Install_Scenario_ABE_Failure
9672 (N => Inst,
9673 Targ_Id => Gen_Id,
9674 Targ_Rep => Gen_Rep,
9675 Disable => Inst_Rep);
9676 end if;
9677 end if;
9678 end Process_Guaranteed_ABE_Instantiation;
9679 end Guaranteed_ABE_Processor;
9680
9681 --------------
9682 -- Has_Body --
9683 --------------
9684
9685 function Has_Body (Pack_Decl : Node_Id) return Boolean is
9686 function Find_Corresponding_Body (Spec_Id : Entity_Id) return Node_Id;
9687 pragma Inline (Find_Corresponding_Body);
9688 -- Try to locate the corresponding body of spec Spec_Id. If no body is
9689 -- found, return Empty.
9690
9691 function Find_Body
9692 (Spec_Id : Entity_Id;
9693 From : Node_Id) return Node_Id;
9694 pragma Inline (Find_Body);
9695 -- Try to locate the corresponding body of spec Spec_Id in the node list
9696 -- which follows arbitrary node From. If no body is found, return Empty.
9697
9698 function Load_Package_Body (Unit_Nam : Unit_Name_Type) return Node_Id;
9699 pragma Inline (Load_Package_Body);
9700 -- Attempt to load the body of unit Unit_Nam. If the load failed, return
9701 -- Empty. If the compilation will not generate code, return Empty.
9702
9703 -----------------------------
9704 -- Find_Corresponding_Body --
9705 -----------------------------
9706
9707 function Find_Corresponding_Body (Spec_Id : Entity_Id) return Node_Id is
9708 Context : constant Entity_Id := Scope (Spec_Id);
9709 Spec_Decl : constant Node_Id := Unit_Declaration_Node (Spec_Id);
9710 Body_Decl : Node_Id;
9711 Body_Id : Entity_Id;
9712
9713 begin
9714 if Is_Compilation_Unit (Spec_Id) then
9715 Body_Id := Corresponding_Body (Spec_Decl);
9716
9717 if Present (Body_Id) then
9718 return Unit_Declaration_Node (Body_Id);
9719
9720 -- The package is at the library and requires a body. Load the
9721 -- corresponding body because the optional body may be declared
9722 -- there.
9723
9724 elsif Unit_Requires_Body (Spec_Id) then
9725 return
9726 Load_Package_Body
9727 (Get_Body_Name (Unit_Name (Get_Source_Unit (Spec_Decl))));
9728
9729 -- Otherwise there is no optional body
9730
9731 else
9732 return Empty;
9733 end if;
9734
9735 -- The immediate context is a package. The optional body may be
9736 -- within the body of that package.
9737
9738 -- procedure Proc is
9739 -- package Nested_1 is
9740 -- package Nested_2 is
9741 -- generic
9742 -- package Pack is
9743 -- end Pack;
9744 -- end Nested_2;
9745 -- end Nested_1;
9746
9747 -- package body Nested_1 is
9748 -- package body Nested_2 is separate;
9749 -- end Nested_1;
9750
9751 -- separate (Proc.Nested_1.Nested_2)
9752 -- package body Nested_2 is
9753 -- package body Pack is -- optional body
9754 -- ...
9755 -- end Pack;
9756 -- end Nested_2;
9757
9758 elsif Is_Package_Or_Generic_Package (Context) then
9759 Body_Decl := Find_Corresponding_Body (Context);
9760
9761 -- The optional body is within the body of the enclosing package
9762
9763 if Present (Body_Decl) then
9764 return
9765 Find_Body
9766 (Spec_Id => Spec_Id,
9767 From => First (Declarations (Body_Decl)));
9768
9769 -- Otherwise the enclosing package does not have a body. This may
9770 -- be the result of an error or a genuine lack of a body.
9771
9772 else
9773 return Empty;
9774 end if;
9775
9776 -- Otherwise the immediate context is a body. The optional body may
9777 -- be within the same list as the spec.
9778
9779 -- procedure Proc is
9780 -- generic
9781 -- package Pack is
9782 -- end Pack;
9783
9784 -- package body Pack is -- optional body
9785 -- ...
9786 -- end Pack;
9787
9788 else
9789 return
9790 Find_Body
9791 (Spec_Id => Spec_Id,
9792 From => Next (Spec_Decl));
9793 end if;
9794 end Find_Corresponding_Body;
9795
9796 ---------------
9797 -- Find_Body --
9798 ---------------
9799
9800 function Find_Body
9801 (Spec_Id : Entity_Id;
9802 From : Node_Id) return Node_Id
9803 is
9804 Spec_Nam : constant Name_Id := Chars (Spec_Id);
9805 Item : Node_Id;
9806 Lib_Unit : Node_Id;
9807
9808 begin
9809 Item := From;
9810 while Present (Item) loop
9811
9812 -- The current item denotes the optional body
9813
9814 if Nkind (Item) = N_Package_Body
9815 and then Chars (Defining_Entity (Item)) = Spec_Nam
9816 then
9817 return Item;
9818
9819 -- The current item denotes a stub, the optional body may be in
9820 -- the subunit.
9821
9822 elsif Nkind (Item) = N_Package_Body_Stub
9823 and then Chars (Defining_Entity (Item)) = Spec_Nam
9824 then
9825 Lib_Unit := Library_Unit (Item);
9826
9827 -- The corresponding subunit was previously loaded
9828
9829 if Present (Lib_Unit) then
9830 return Lib_Unit;
9831
9832 -- Otherwise attempt to load the corresponding subunit
9833
9834 else
9835 return Load_Package_Body (Get_Unit_Name (Item));
9836 end if;
9837 end if;
9838
9839 Next (Item);
9840 end loop;
9841
9842 return Empty;
9843 end Find_Body;
9844
9845 -----------------------
9846 -- Load_Package_Body --
9847 -----------------------
9848
9849 function Load_Package_Body (Unit_Nam : Unit_Name_Type) return Node_Id is
9850 Body_Decl : Node_Id;
9851 Unit_Num : Unit_Number_Type;
9852
9853 begin
9854 -- The load is performed only when the compilation will generate code
9855
9856 if Operating_Mode = Generate_Code then
9857 Unit_Num :=
9858 Load_Unit
9859 (Load_Name => Unit_Nam,
9860 Required => False,
9861 Subunit => False,
9862 Error_Node => Pack_Decl);
9863
9864 -- The load failed most likely because the physical file is
9865 -- missing.
9866
9867 if Unit_Num = No_Unit then
9868 return Empty;
9869
9870 -- Otherwise the load was successful, return the body of the unit
9871
9872 else
9873 Body_Decl := Unit (Cunit (Unit_Num));
9874
9875 -- If the unit is a subunit with an available proper body,
9876 -- return the proper body.
9877
9878 if Nkind (Body_Decl) = N_Subunit
9879 and then Present (Proper_Body (Body_Decl))
9880 then
9881 Body_Decl := Proper_Body (Body_Decl);
9882 end if;
9883
9884 return Body_Decl;
9885 end if;
9886 end if;
9887
9888 return Empty;
9889 end Load_Package_Body;
9890
9891 -- Local variables
9892
9893 Pack_Id : constant Entity_Id := Defining_Entity (Pack_Decl);
9894
9895 -- Start of processing for Has_Body
9896
9897 begin
9898 -- The body is available
9899
9900 if Present (Corresponding_Body (Pack_Decl)) then
9901 return True;
9902
9903 -- The body is required if the package spec contains a construct which
9904 -- requires a completion in a body.
9905
9906 elsif Unit_Requires_Body (Pack_Id) then
9907 return True;
9908
9909 -- The body may be optional
9910
9911 else
9912 return Present (Find_Corresponding_Body (Pack_Id));
9913 end if;
9914 end Has_Body;
9915
9916 ----------
9917 -- Hash --
9918 ----------
9919
9920 function Hash (NE : Node_Or_Entity_Id) return Bucket_Range_Type is
9921 pragma Assert (Present (NE));
9922 begin
9923 return Bucket_Range_Type (NE);
9924 end Hash;
9925
9926 --------------------------
9927 -- In_External_Instance --
9928 --------------------------
9929
9930 function In_External_Instance
9931 (N : Node_Id;
9932 Target_Decl : Node_Id) return Boolean
9933 is
9934 Inst : Node_Id;
9935 Inst_Body : Node_Id;
9936 Inst_Spec : Node_Id;
9937
9938 begin
9939 Inst := Find_Enclosing_Instance (Target_Decl);
9940
9941 -- The target declaration appears within an instance spec. Visibility is
9942 -- ignored because internally generated primitives for private types may
9943 -- reside in the private declarations and still be invoked from outside.
9944
9945 if Present (Inst) and then Nkind (Inst) = N_Package_Declaration then
9946
9947 -- The scenario comes from the main unit and the instance does not
9948
9949 if In_Extended_Main_Code_Unit (N)
9950 and then not In_Extended_Main_Code_Unit (Inst)
9951 then
9952 return True;
9953
9954 -- Otherwise the scenario must not appear within the instance spec or
9955 -- body.
9956
9957 else
9958 Spec_And_Body_From_Node
9959 (N => Inst,
9960 Spec_Decl => Inst_Spec,
9961 Body_Decl => Inst_Body);
9962
9963 return not In_Subtree
9964 (N => N,
9965 Root1 => Inst_Spec,
9966 Root2 => Inst_Body);
9967 end if;
9968 end if;
9969
9970 return False;
9971 end In_External_Instance;
9972
9973 ---------------------
9974 -- In_Main_Context --
9975 ---------------------
9976
9977 function In_Main_Context (N : Node_Id) return Boolean is
9978 begin
9979 -- Scenarios outside the main unit are not considered because the ALI
9980 -- information supplied to binde is for the main unit only.
9981
9982 if not In_Extended_Main_Code_Unit (N) then
9983 return False;
9984
9985 -- Scenarios within internal units are not considered unless switch
9986 -- -gnatdE (elaboration checks on predefined units) is in effect.
9987
9988 elsif not Debug_Flag_EE and then In_Internal_Unit (N) then
9989 return False;
9990 end if;
9991
9992 return True;
9993 end In_Main_Context;
9994
9995 ---------------------
9996 -- In_Same_Context --
9997 ---------------------
9998
9999 function In_Same_Context
10000 (N1 : Node_Id;
10001 N2 : Node_Id;
10002 Nested_OK : Boolean := False) return Boolean
10003 is
10004 function Find_Enclosing_Context (N : Node_Id) return Node_Id;
10005 pragma Inline (Find_Enclosing_Context);
10006 -- Return the nearest enclosing non-library-level or compilation unit
10007 -- node which which encapsulates arbitrary node N. Return Empty is no
10008 -- such context is available.
10009
10010 function In_Nested_Context
10011 (Outer : Node_Id;
10012 Inner : Node_Id) return Boolean;
10013 pragma Inline (In_Nested_Context);
10014 -- Determine whether arbitrary node Outer encapsulates arbitrary node
10015 -- Inner.
10016
10017 ----------------------------
10018 -- Find_Enclosing_Context --
10019 ----------------------------
10020
10021 function Find_Enclosing_Context (N : Node_Id) return Node_Id is
10022 Context : Node_Id;
10023 Par : Node_Id;
10024
10025 begin
10026 Par := Parent (N);
10027 while Present (Par) loop
10028
10029 -- A traversal from a subunit continues via the corresponding stub
10030
10031 if Nkind (Par) = N_Subunit then
10032 Par := Corresponding_Stub (Par);
10033
10034 -- Stop the traversal when the nearest enclosing non-library-level
10035 -- encapsulator has been reached.
10036
10037 elsif Is_Non_Library_Level_Encapsulator (Par) then
10038 Context := Parent (Par);
10039
10040 -- The sole exception is when the encapsulator is the unit of
10041 -- compilation because this case requires special processing
10042 -- (see below).
10043
10044 if Present (Context)
10045 and then Nkind (Context) = N_Compilation_Unit
10046 then
10047 null;
10048
10049 else
10050 return Par;
10051 end if;
10052
10053 -- Reaching a compilation unit node without hitting a non-library-
10054 -- level encapsulator indicates that N is at the library level in
10055 -- which case the compilation unit is the context.
10056
10057 elsif Nkind (Par) = N_Compilation_Unit then
10058 return Par;
10059 end if;
10060
10061 Par := Parent (Par);
10062 end loop;
10063
10064 return Empty;
10065 end Find_Enclosing_Context;
10066
10067 -----------------------
10068 -- In_Nested_Context --
10069 -----------------------
10070
10071 function In_Nested_Context
10072 (Outer : Node_Id;
10073 Inner : Node_Id) return Boolean
10074 is
10075 Par : Node_Id;
10076
10077 begin
10078 Par := Inner;
10079 while Present (Par) loop
10080
10081 -- A traversal from a subunit continues via the corresponding stub
10082
10083 if Nkind (Par) = N_Subunit then
10084 Par := Corresponding_Stub (Par);
10085
10086 elsif Par = Outer then
10087 return True;
10088 end if;
10089
10090 Par := Parent (Par);
10091 end loop;
10092
10093 return False;
10094 end In_Nested_Context;
10095
10096 -- Local variables
10097
10098 Context_1 : constant Node_Id := Find_Enclosing_Context (N1);
10099 Context_2 : constant Node_Id := Find_Enclosing_Context (N2);
10100
10101 -- Start of processing for In_Same_Context
10102
10103 begin
10104 -- Both nodes appear within the same context
10105
10106 if Context_1 = Context_2 then
10107 return True;
10108
10109 -- Both nodes appear in compilation units. Determine whether one unit
10110 -- is the body of the other.
10111
10112 elsif Nkind (Context_1) = N_Compilation_Unit
10113 and then Nkind (Context_2) = N_Compilation_Unit
10114 then
10115 return
10116 Is_Same_Unit
10117 (Unit_1 => Defining_Entity (Unit (Context_1)),
10118 Unit_2 => Defining_Entity (Unit (Context_2)));
10119
10120 -- The context of N1 encloses the context of N2
10121
10122 elsif Nested_OK and then In_Nested_Context (Context_1, Context_2) then
10123 return True;
10124 end if;
10125
10126 return False;
10127 end In_Same_Context;
10128
10129 ----------------
10130 -- Initialize --
10131 ----------------
10132
10133 procedure Initialize is
10134 begin
10135 -- Set the soft link which enables Atree.Rewrite to update a scenario
10136 -- each time it is transformed into another node.
10137
10138 Set_Rewriting_Proc (Update_Elaboration_Scenario'Access);
10139
10140 -- Create all internal data structures and activate the elaboration
10141 -- phase of the compiler.
10142
10143 Initialize_All_Data_Structures;
10144 Set_Elaboration_Phase (Active);
10145 end Initialize;
10146
10147 ------------------------------------
10148 -- Initialize_All_Data_Structures --
10149 ------------------------------------
10150
10151 procedure Initialize_All_Data_Structures is
10152 begin
10153 Initialize_Body_Processor;
10154 Initialize_Early_Call_Region_Processor;
10155 Initialize_Elaborated_Units;
10156 Initialize_Internal_Representation;
10157 Initialize_Invocation_Graph;
10158 Initialize_Scenario_Storage;
10159 end Initialize_All_Data_Structures;
10160
10161 --------------------------
10162 -- Instantiated_Generic --
10163 --------------------------
10164
10165 function Instantiated_Generic (Inst : Node_Id) return Entity_Id is
10166 begin
10167 -- Traverse a possible chain of renamings to obtain the original generic
10168 -- being instantiatied.
10169
10170 return Get_Renamed_Entity (Entity (Name (Inst)));
10171 end Instantiated_Generic;
10172
10173 -----------------------------
10174 -- Internal_Representation --
10175 -----------------------------
10176
10177 package body Internal_Representation is
10178
10179 -----------
10180 -- Types --
10181 -----------
10182
10183 -- The following type represents the contents of a scenario
10184
10185 type Scenario_Rep_Record is record
10186 Elab_Checks_OK : Boolean := False;
10187 -- The status of elaboration checks for the scenario
10188
10189 Elab_Warnings_OK : Boolean := False;
10190 -- The status of elaboration warnings for the scenario
10191
10192 GM : Extended_Ghost_Mode := Is_Checked_Or_Not_Specified;
10193 -- The Ghost mode of the scenario
10194
10195 Kind : Scenario_Kind := No_Scenario;
10196 -- The nature of the scenario
10197
10198 Level : Enclosing_Level_Kind := No_Level;
10199 -- The enclosing level where the scenario resides
10200
10201 SM : Extended_SPARK_Mode := Is_Off_Or_Not_Specified;
10202 -- The SPARK mode of the scenario
10203
10204 Target : Entity_Id := Empty;
10205 -- The target of the scenario
10206
10207 -- The following attributes are multiplexed and depend on the Kind of
10208 -- the scenario. They are mapped as follows:
10209 --
10210 -- Call_Scenario
10211 -- Is_Dispatching_Call (Flag_1)
10212 --
10213 -- Task_Activation_Scenario
10214 -- Activated_Task_Objects (List_1)
10215 -- Activated_Task_Type (Field_1)
10216 --
10217 -- Variable_Reference
10218 -- Is_Read_Reference (Flag_1)
10219
10220 Flag_1 : Boolean := False;
10221 Field_1 : Node_Or_Entity_Id := Empty;
10222 List_1 : NE_List.Doubly_Linked_List := NE_List.Nil;
10223 end record;
10224
10225 -- The following type represents the contents of a target
10226
10227 type Target_Rep_Record is record
10228 Body_Decl : Node_Id := Empty;
10229 -- The declaration of the target body
10230
10231 Elab_Checks_OK : Boolean := False;
10232 -- The status of elaboration checks for the target
10233
10234 Elab_Warnings_OK : Boolean := False;
10235 -- The status of elaboration warnings for the target
10236
10237 GM : Extended_Ghost_Mode := Is_Checked_Or_Not_Specified;
10238 -- The Ghost mode of the target
10239
10240 Kind : Target_Kind := No_Target;
10241 -- The nature of the target
10242
10243 SM : Extended_SPARK_Mode := Is_Off_Or_Not_Specified;
10244 -- The SPARK mode of the target
10245
10246 Spec_Decl : Node_Id := Empty;
10247 -- The declaration of the target spec
10248
10249 Unit : Entity_Id := Empty;
10250 -- The top unit where the target is declared
10251
10252 Version : Representation_Kind := No_Representation;
10253 -- The version of the target representation
10254
10255 -- The following attributes are multiplexed and depend on the Kind of
10256 -- the target. They are mapped as follows:
10257 --
10258 -- Subprogram_Target
10259 -- Barrier_Body_Declaration (Field_1)
10260 --
10261 -- Variable_Target
10262 -- Variable_Declaration (Field_1)
10263
10264 Field_1 : Node_Or_Entity_Id := Empty;
10265 end record;
10266
10267 ---------------------
10268 -- Data structures --
10269 ---------------------
10270
10271 procedure Destroy (T_Id : in out Target_Rep_Id);
10272 -- Destroy a target representation T_Id
10273
10274 package ETT_Map is new Dynamic_Hash_Tables
10275 (Key_Type => Entity_Id,
10276 Value_Type => Target_Rep_Id,
10277 No_Value => No_Target_Rep,
10278 Expansion_Threshold => 1.5,
10279 Expansion_Factor => 2,
10280 Compression_Threshold => 0.3,
10281 Compression_Factor => 2,
10282 "=" => "=",
10283 Destroy_Value => Destroy,
10284 Hash => Hash);
10285
10286 -- The following map relates target representations to entities
10287
10288 Entity_To_Target_Map : ETT_Map.Dynamic_Hash_Table := ETT_Map.Nil;
10289
10290 procedure Destroy (S_Id : in out Scenario_Rep_Id);
10291 -- Destroy a scenario representation S_Id
10292
10293 package NTS_Map is new Dynamic_Hash_Tables
10294 (Key_Type => Node_Id,
10295 Value_Type => Scenario_Rep_Id,
10296 No_Value => No_Scenario_Rep,
10297 Expansion_Threshold => 1.5,
10298 Expansion_Factor => 2,
10299 Compression_Threshold => 0.3,
10300 Compression_Factor => 2,
10301 "=" => "=",
10302 Destroy_Value => Destroy,
10303 Hash => Hash);
10304
10305 -- The following map relates scenario representations to nodes
10306
10307 Node_To_Scenario_Map : NTS_Map.Dynamic_Hash_Table := NTS_Map.Nil;
10308
10309 -- The following table stores all scenario representations
10310
10311 package Scenario_Reps is new Table.Table
10312 (Table_Index_Type => Scenario_Rep_Id,
10313 Table_Component_Type => Scenario_Rep_Record,
10314 Table_Low_Bound => First_Scenario_Rep,
10315 Table_Initial => 1000,
10316 Table_Increment => 200,
10317 Table_Name => "Scenario_Reps");
10318
10319 -- The following table stores all target representations
10320
10321 package Target_Reps is new Table.Table
10322 (Table_Index_Type => Target_Rep_Id,
10323 Table_Component_Type => Target_Rep_Record,
10324 Table_Low_Bound => First_Target_Rep,
10325 Table_Initial => 1000,
10326 Table_Increment => 200,
10327 Table_Name => "Target_Reps");
10328
10329 --------------
10330 -- Builders --
10331 --------------
10332
10333 function Create_Access_Taken_Rep
10334 (Attr : Node_Id) return Scenario_Rep_Record;
10335 pragma Inline (Create_Access_Taken_Rep);
10336 -- Create the representation of 'Access attribute Attr
10337
10338 function Create_Call_Or_Task_Activation_Rep
10339 (Call : Node_Id) return Scenario_Rep_Record;
10340 pragma Inline (Create_Call_Or_Task_Activation_Rep);
10341 -- Create the representation of call or task activation Call
10342
10343 function Create_Derived_Type_Rep
10344 (Typ_Decl : Node_Id) return Scenario_Rep_Record;
10345 pragma Inline (Create_Derived_Type_Rep);
10346 -- Create the representation of a derived type described by declaration
10347 -- Typ_Decl.
10348
10349 function Create_Generic_Rep
10350 (Gen_Id : Entity_Id) return Target_Rep_Record;
10351 pragma Inline (Create_Generic_Rep);
10352 -- Create the representation of generic Gen_Id
10353
10354 function Create_Instantiation_Rep
10355 (Inst : Node_Id) return Scenario_Rep_Record;
10356 pragma Inline (Create_Instantiation_Rep);
10357 -- Create the representation of instantiation Inst
10358
10359 function Create_Protected_Entry_Rep
10360 (PE_Id : Entity_Id) return Target_Rep_Record;
10361 pragma Inline (Create_Protected_Entry_Rep);
10362 -- Create the representation of protected entry PE_Id
10363
10364 function Create_Protected_Subprogram_Rep
10365 (PS_Id : Entity_Id) return Target_Rep_Record;
10366 pragma Inline (Create_Protected_Subprogram_Rep);
10367 -- Create the representation of protected subprogram PS_Id
10368
10369 function Create_Refined_State_Pragma_Rep
10370 (Prag : Node_Id) return Scenario_Rep_Record;
10371 pragma Inline (Create_Refined_State_Pragma_Rep);
10372 -- Create the representation of Refined_State pragma Prag
10373
10374 function Create_Scenario_Rep
10375 (N : Node_Id;
10376 In_State : Processing_In_State) return Scenario_Rep_Record;
10377 pragma Inline (Create_Scenario_Rep);
10378 -- Top level dispatcher. Create the representation of elaboration
10379 -- scenario N. In_State is the current state of the Processing phase.
10380
10381 function Create_Subprogram_Rep
10382 (Subp_Id : Entity_Id) return Target_Rep_Record;
10383 pragma Inline (Create_Subprogram_Rep);
10384 -- Create the representation of entry, operator, or subprogram Subp_Id
10385
10386 function Create_Target_Rep
10387 (Id : Entity_Id;
10388 In_State : Processing_In_State) return Target_Rep_Record;
10389 pragma Inline (Create_Target_Rep);
10390 -- Top level dispatcher. Create the representation of elaboration target
10391 -- Id. In_State is the current state of the Processing phase.
10392
10393 function Create_Task_Entry_Rep
10394 (TE_Id : Entity_Id) return Target_Rep_Record;
10395 pragma Inline (Create_Task_Entry_Rep);
10396 -- Create the representation of task entry TE_Id
10397
10398 function Create_Task_Rep (Task_Typ : Entity_Id) return Target_Rep_Record;
10399 pragma Inline (Create_Task_Rep);
10400 -- Create the representation of task type Typ
10401
10402 function Create_Variable_Assignment_Rep
10403 (Asmt : Node_Id) return Scenario_Rep_Record;
10404 pragma Inline (Create_Variable_Assignment_Rep);
10405 -- Create the representation of variable assignment Asmt
10406
10407 function Create_Variable_Reference_Rep
10408 (Ref : Node_Id) return Scenario_Rep_Record;
10409 pragma Inline (Create_Variable_Reference_Rep);
10410 -- Create the representation of variable reference Ref
10411
10412 function Create_Variable_Rep
10413 (Var_Id : Entity_Id) return Target_Rep_Record;
10414 pragma Inline (Create_Variable_Rep);
10415 -- Create the representation of variable Var_Id
10416
10417 -----------------------
10418 -- Local subprograms --
10419 -----------------------
10420
10421 function Ghost_Mode_Of_Entity
10422 (Id : Entity_Id) return Extended_Ghost_Mode;
10423 pragma Inline (Ghost_Mode_Of_Entity);
10424 -- Obtain the extended Ghost mode of arbitrary entity Id
10425
10426 function Ghost_Mode_Of_Node (N : Node_Id) return Extended_Ghost_Mode;
10427 pragma Inline (Ghost_Mode_Of_Node);
10428 -- Obtain the extended Ghost mode of arbitrary node N
10429
10430 function Present (S_Id : Scenario_Rep_Id) return Boolean;
10431 pragma Inline (Present);
10432 -- Determine whether scenario representation S_Id exists
10433
10434 function Present (T_Id : Target_Rep_Id) return Boolean;
10435 pragma Inline (Present);
10436 -- Determine whether target representation T_Id exists
10437
10438 function SPARK_Mode_Of_Entity
10439 (Id : Entity_Id) return Extended_SPARK_Mode;
10440 pragma Inline (SPARK_Mode_Of_Entity);
10441 -- Obtain the extended SPARK mode of arbitrary entity Id
10442
10443 function SPARK_Mode_Of_Node (N : Node_Id) return Extended_SPARK_Mode;
10444 pragma Inline (SPARK_Mode_Of_Node);
10445 -- Obtain the extended SPARK mode of arbitrary node N
10446
10447 function To_Ghost_Mode
10448 (Ignored_Status : Boolean) return Extended_Ghost_Mode;
10449 pragma Inline (To_Ghost_Mode);
10450 -- Convert a Ghost mode indicated by Ignored_Status into its extended
10451 -- equivalent.
10452
10453 function To_SPARK_Mode (On_Status : Boolean) return Extended_SPARK_Mode;
10454 pragma Inline (To_SPARK_Mode);
10455 -- Convert a SPARK mode indicated by On_Status into its extended
10456 -- equivalent.
10457
10458 function Version (T_Id : Target_Rep_Id) return Representation_Kind;
10459 pragma Inline (Version);
10460 -- Obtain the version of target representation T_Id
10461
10462 ----------------------------
10463 -- Activated_Task_Objects --
10464 ----------------------------
10465
10466 function Activated_Task_Objects
10467 (S_Id : Scenario_Rep_Id) return NE_List.Doubly_Linked_List
10468 is
10469 pragma Assert (Present (S_Id));
10470 pragma Assert (Kind (S_Id) = Task_Activation_Scenario);
10471
10472 begin
10473 return Scenario_Reps.Table (S_Id).List_1;
10474 end Activated_Task_Objects;
10475
10476 -------------------------
10477 -- Activated_Task_Type --
10478 -------------------------
10479
10480 function Activated_Task_Type
10481 (S_Id : Scenario_Rep_Id) return Entity_Id
10482 is
10483 pragma Assert (Present (S_Id));
10484 pragma Assert (Kind (S_Id) = Task_Activation_Scenario);
10485
10486 begin
10487 return Scenario_Reps.Table (S_Id).Field_1;
10488 end Activated_Task_Type;
10489
10490 ------------------------------
10491 -- Barrier_Body_Declaration --
10492 ------------------------------
10493
10494 function Barrier_Body_Declaration
10495 (T_Id : Target_Rep_Id) return Node_Id
10496 is
10497 pragma Assert (Present (T_Id));
10498 pragma Assert (Kind (T_Id) = Subprogram_Target);
10499
10500 begin
10501 return Target_Reps.Table (T_Id).Field_1;
10502 end Barrier_Body_Declaration;
10503
10504 ----------------------
10505 -- Body_Declaration --
10506 ----------------------
10507
10508 function Body_Declaration (T_Id : Target_Rep_Id) return Node_Id is
10509 pragma Assert (Present (T_Id));
10510 begin
10511 return Target_Reps.Table (T_Id).Body_Decl;
10512 end Body_Declaration;
10513
10514 -----------------------------
10515 -- Create_Access_Taken_Rep --
10516 -----------------------------
10517
10518 function Create_Access_Taken_Rep
10519 (Attr : Node_Id) return Scenario_Rep_Record
10520 is
10521 Rec : Scenario_Rep_Record;
10522
10523 begin
10524 Rec.Elab_Checks_OK := Is_Elaboration_Checks_OK_Node (Attr);
10525 Rec.Elab_Warnings_OK := Is_Elaboration_Warnings_OK_Node (Attr);
10526 Rec.GM := Is_Checked_Or_Not_Specified;
10527 Rec.SM := SPARK_Mode_Of_Node (Attr);
10528 Rec.Kind := Access_Taken_Scenario;
10529 Rec.Target := Canonical_Subprogram (Entity (Prefix (Attr)));
10530
10531 return Rec;
10532 end Create_Access_Taken_Rep;
10533
10534 ----------------------------------------
10535 -- Create_Call_Or_Task_Activation_Rep --
10536 ----------------------------------------
10537
10538 function Create_Call_Or_Task_Activation_Rep
10539 (Call : Node_Id) return Scenario_Rep_Record
10540 is
10541 Subp_Id : constant Entity_Id := Canonical_Subprogram (Target (Call));
10542 Kind : Scenario_Kind;
10543 Rec : Scenario_Rep_Record;
10544
10545 begin
10546 if Is_Activation_Proc (Subp_Id) then
10547 Kind := Task_Activation_Scenario;
10548 else
10549 Kind := Call_Scenario;
10550 end if;
10551
10552 Rec.Elab_Checks_OK := Is_Elaboration_Checks_OK_Node (Call);
10553 Rec.Elab_Warnings_OK := Is_Elaboration_Warnings_OK_Node (Call);
10554 Rec.GM := Ghost_Mode_Of_Node (Call);
10555 Rec.SM := SPARK_Mode_Of_Node (Call);
10556 Rec.Kind := Kind;
10557 Rec.Target := Subp_Id;
10558
10559 -- Scenario-specific attributes
10560
10561 Rec.Flag_1 := Is_Dispatching_Call (Call); -- Dispatching_Call
10562
10563 return Rec;
10564 end Create_Call_Or_Task_Activation_Rep;
10565
10566 -----------------------------
10567 -- Create_Derived_Type_Rep --
10568 -----------------------------
10569
10570 function Create_Derived_Type_Rep
10571 (Typ_Decl : Node_Id) return Scenario_Rep_Record
10572 is
10573 Typ : constant Entity_Id := Defining_Entity (Typ_Decl);
10574 Rec : Scenario_Rep_Record;
10575
10576 begin
10577 Rec.Elab_Checks_OK := False; -- not relevant
10578 Rec.Elab_Warnings_OK := False; -- not relevant
10579 Rec.GM := Ghost_Mode_Of_Entity (Typ);
10580 Rec.SM := SPARK_Mode_Of_Entity (Typ);
10581 Rec.Kind := Derived_Type_Scenario;
10582 Rec.Target := Typ;
10583
10584 return Rec;
10585 end Create_Derived_Type_Rep;
10586
10587 ------------------------
10588 -- Create_Generic_Rep --
10589 ------------------------
10590
10591 function Create_Generic_Rep
10592 (Gen_Id : Entity_Id) return Target_Rep_Record
10593 is
10594 Rec : Target_Rep_Record;
10595
10596 begin
10597 Rec.Kind := Generic_Target;
10598
10599 Spec_And_Body_From_Entity
10600 (Id => Gen_Id,
10601 Body_Decl => Rec.Body_Decl,
10602 Spec_Decl => Rec.Spec_Decl);
10603
10604 return Rec;
10605 end Create_Generic_Rep;
10606
10607 ------------------------------
10608 -- Create_Instantiation_Rep --
10609 ------------------------------
10610
10611 function Create_Instantiation_Rep
10612 (Inst : Node_Id) return Scenario_Rep_Record
10613 is
10614 Rec : Scenario_Rep_Record;
10615
10616 begin
10617 Rec.Elab_Checks_OK := Is_Elaboration_Checks_OK_Node (Inst);
10618 Rec.Elab_Warnings_OK := Is_Elaboration_Warnings_OK_Node (Inst);
10619 Rec.GM := Ghost_Mode_Of_Node (Inst);
10620 Rec.SM := SPARK_Mode_Of_Node (Inst);
10621 Rec.Kind := Instantiation_Scenario;
10622 Rec.Target := Instantiated_Generic (Inst);
10623
10624 return Rec;
10625 end Create_Instantiation_Rep;
10626
10627 --------------------------------
10628 -- Create_Protected_Entry_Rep --
10629 --------------------------------
10630
10631 function Create_Protected_Entry_Rep
10632 (PE_Id : Entity_Id) return Target_Rep_Record
10633 is
10634 Prot_Id : constant Entity_Id := Protected_Body_Subprogram (PE_Id);
10635
10636 Barf_Id : Entity_Id;
10637 Dummy : Node_Id;
10638 Rec : Target_Rep_Record;
10639 Spec_Id : Entity_Id;
10640
10641 begin
10642 -- When the entry [family] has already been expanded, it carries both
10643 -- the procedure which emulates the behavior of the entry [family] as
10644 -- well as the barrier function.
10645
10646 if Present (Prot_Id) then
10647 Barf_Id := Barrier_Function (PE_Id);
10648 Spec_Id := Prot_Id;
10649
10650 -- Otherwise no expansion took place
10651
10652 else
10653 Barf_Id := Empty;
10654 Spec_Id := PE_Id;
10655 end if;
10656
10657 Rec.Kind := Subprogram_Target;
10658
10659 Spec_And_Body_From_Entity
10660 (Id => Spec_Id,
10661 Body_Decl => Rec.Body_Decl,
10662 Spec_Decl => Rec.Spec_Decl);
10663
10664 -- Target-specific attributes
10665
10666 if Present (Barf_Id) then
10667 Spec_And_Body_From_Entity
10668 (Id => Barf_Id,
10669 Body_Decl => Rec.Field_1, -- Barrier_Body_Declaration
10670 Spec_Decl => Dummy);
10671 end if;
10672
10673 return Rec;
10674 end Create_Protected_Entry_Rep;
10675
10676 -------------------------------------
10677 -- Create_Protected_Subprogram_Rep --
10678 -------------------------------------
10679
10680 function Create_Protected_Subprogram_Rep
10681 (PS_Id : Entity_Id) return Target_Rep_Record
10682 is
10683 Prot_Id : constant Entity_Id := Protected_Body_Subprogram (PS_Id);
10684 Rec : Target_Rep_Record;
10685 Spec_Id : Entity_Id;
10686
10687 begin
10688 -- When the protected subprogram has already been expanded, it
10689 -- carries the subprogram which seizes the lock and invokes the
10690 -- original statements.
10691
10692 if Present (Prot_Id) then
10693 Spec_Id := Prot_Id;
10694
10695 -- Otherwise no expansion took place
10696
10697 else
10698 Spec_Id := PS_Id;
10699 end if;
10700
10701 Rec.Kind := Subprogram_Target;
10702
10703 Spec_And_Body_From_Entity
10704 (Id => Spec_Id,
10705 Body_Decl => Rec.Body_Decl,
10706 Spec_Decl => Rec.Spec_Decl);
10707
10708 return Rec;
10709 end Create_Protected_Subprogram_Rep;
10710
10711 -------------------------------------
10712 -- Create_Refined_State_Pragma_Rep --
10713 -------------------------------------
10714
10715 function Create_Refined_State_Pragma_Rep
10716 (Prag : Node_Id) return Scenario_Rep_Record
10717 is
10718 Rec : Scenario_Rep_Record;
10719
10720 begin
10721 Rec.Elab_Checks_OK := False; -- not relevant
10722 Rec.Elab_Warnings_OK := False; -- not relevant
10723 Rec.GM :=
10724 To_Ghost_Mode (Is_Ignored_Ghost_Pragma (Prag));
10725 Rec.SM := Is_Off_Or_Not_Specified;
10726 Rec.Kind := Refined_State_Pragma_Scenario;
10727 Rec.Target := Empty;
10728
10729 return Rec;
10730 end Create_Refined_State_Pragma_Rep;
10731
10732 -------------------------
10733 -- Create_Scenario_Rep --
10734 -------------------------
10735
10736 function Create_Scenario_Rep
10737 (N : Node_Id;
10738 In_State : Processing_In_State) return Scenario_Rep_Record
10739 is
10740 pragma Unreferenced (In_State);
10741
10742 Rec : Scenario_Rep_Record;
10743
10744 begin
10745 if Is_Suitable_Access_Taken (N) then
10746 Rec := Create_Access_Taken_Rep (N);
10747
10748 elsif Is_Suitable_Call (N) then
10749 Rec := Create_Call_Or_Task_Activation_Rep (N);
10750
10751 elsif Is_Suitable_Instantiation (N) then
10752 Rec := Create_Instantiation_Rep (N);
10753
10754 elsif Is_Suitable_SPARK_Derived_Type (N) then
10755 Rec := Create_Derived_Type_Rep (N);
10756
10757 elsif Is_Suitable_SPARK_Refined_State_Pragma (N) then
10758 Rec := Create_Refined_State_Pragma_Rep (N);
10759
10760 elsif Is_Suitable_Variable_Assignment (N) then
10761 Rec := Create_Variable_Assignment_Rep (N);
10762
10763 elsif Is_Suitable_Variable_Reference (N) then
10764 Rec := Create_Variable_Reference_Rep (N);
10765
10766 else
10767 pragma Assert (False);
10768 return Rec;
10769 end if;
10770
10771 -- Common scenario attributes
10772
10773 Rec.Level := Find_Enclosing_Level (N);
10774
10775 return Rec;
10776 end Create_Scenario_Rep;
10777
10778 ---------------------------
10779 -- Create_Subprogram_Rep --
10780 ---------------------------
10781
10782 function Create_Subprogram_Rep
10783 (Subp_Id : Entity_Id) return Target_Rep_Record
10784 is
10785 Rec : Target_Rep_Record;
10786 Spec_Id : Entity_Id;
10787
10788 begin
10789 Spec_Id := Subp_Id;
10790
10791 -- The elaboration target denotes an internal function that returns a
10792 -- constrained array type in a SPARK-to-C compilation. In this case
10793 -- the function receives a corresponding procedure which has an out
10794 -- parameter. The proper body for ABE checks and diagnostics is that
10795 -- of the procedure.
10796
10797 if Ekind (Spec_Id) = E_Function
10798 and then Rewritten_For_C (Spec_Id)
10799 then
10800 Spec_Id := Corresponding_Procedure (Spec_Id);
10801 end if;
10802
10803 Rec.Kind := Subprogram_Target;
10804
10805 Spec_And_Body_From_Entity
10806 (Id => Spec_Id,
10807 Body_Decl => Rec.Body_Decl,
10808 Spec_Decl => Rec.Spec_Decl);
10809
10810 return Rec;
10811 end Create_Subprogram_Rep;
10812
10813 -----------------------
10814 -- Create_Target_Rep --
10815 -----------------------
10816
10817 function Create_Target_Rep
10818 (Id : Entity_Id;
10819 In_State : Processing_In_State) return Target_Rep_Record
10820 is
10821 Rec : Target_Rep_Record;
10822
10823 begin
10824 if Is_Generic_Unit (Id) then
10825 Rec := Create_Generic_Rep (Id);
10826
10827 elsif Is_Protected_Entry (Id) then
10828 Rec := Create_Protected_Entry_Rep (Id);
10829
10830 elsif Is_Protected_Subp (Id) then
10831 Rec := Create_Protected_Subprogram_Rep (Id);
10832
10833 elsif Is_Task_Entry (Id) then
10834 Rec := Create_Task_Entry_Rep (Id);
10835
10836 elsif Is_Task_Type (Id) then
10837 Rec := Create_Task_Rep (Id);
10838
10839 elsif Ekind_In (Id, E_Constant, E_Variable) then
10840 Rec := Create_Variable_Rep (Id);
10841
10842 elsif Ekind_In (Id, E_Entry,
10843 E_Function,
10844 E_Operator,
10845 E_Procedure)
10846 then
10847 Rec := Create_Subprogram_Rep (Id);
10848
10849 else
10850 pragma Assert (False);
10851 return Rec;
10852 end if;
10853
10854 -- Common target attributes
10855
10856 Rec.Elab_Checks_OK := Is_Elaboration_Checks_OK_Id (Id);
10857 Rec.Elab_Warnings_OK := Is_Elaboration_Warnings_OK_Id (Id);
10858 Rec.GM := Ghost_Mode_Of_Entity (Id);
10859 Rec.SM := SPARK_Mode_Of_Entity (Id);
10860 Rec.Unit := Find_Top_Unit (Id);
10861 Rec.Version := In_State.Representation;
10862
10863 return Rec;
10864 end Create_Target_Rep;
10865
10866 ---------------------------
10867 -- Create_Task_Entry_Rep --
10868 ---------------------------
10869
10870 function Create_Task_Entry_Rep
10871 (TE_Id : Entity_Id) return Target_Rep_Record
10872 is
10873 Task_Typ : constant Entity_Id := Non_Private_View (Scope (TE_Id));
10874 Task_Body_Id : constant Entity_Id := Task_Body_Procedure (Task_Typ);
10875
10876 Rec : Target_Rep_Record;
10877 Spec_Id : Entity_Id;
10878
10879 begin
10880 -- The the task type has already been expanded, it carries the
10881 -- procedure which emulates the behavior of the task body.
10882
10883 if Present (Task_Body_Id) then
10884 Spec_Id := Task_Body_Id;
10885
10886 -- Otherwise no expansion took place
10887
10888 else
10889 Spec_Id := TE_Id;
10890 end if;
10891
10892 Rec.Kind := Subprogram_Target;
10893
10894 Spec_And_Body_From_Entity
10895 (Id => Spec_Id,
10896 Body_Decl => Rec.Body_Decl,
10897 Spec_Decl => Rec.Spec_Decl);
10898
10899 return Rec;
10900 end Create_Task_Entry_Rep;
10901
10902 ---------------------
10903 -- Create_Task_Rep --
10904 ---------------------
10905
10906 function Create_Task_Rep
10907 (Task_Typ : Entity_Id) return Target_Rep_Record
10908 is
10909 Task_Body_Id : constant Entity_Id := Task_Body_Procedure (Task_Typ);
10910
10911 Rec : Target_Rep_Record;
10912 Spec_Id : Entity_Id;
10913
10914 begin
10915 -- The the task type has already been expanded, it carries the
10916 -- procedure which emulates the behavior of the task body.
10917
10918 if Present (Task_Body_Id) then
10919 Spec_Id := Task_Body_Id;
10920
10921 -- Otherwise no expansion took place
10922
10923 else
10924 Spec_Id := Task_Typ;
10925 end if;
10926
10927 Rec.Kind := Task_Target;
10928
10929 Spec_And_Body_From_Entity
10930 (Id => Spec_Id,
10931 Body_Decl => Rec.Body_Decl,
10932 Spec_Decl => Rec.Spec_Decl);
10933
10934 return Rec;
10935 end Create_Task_Rep;
10936
10937 ------------------------------------
10938 -- Create_Variable_Assignment_Rep --
10939 ------------------------------------
10940
10941 function Create_Variable_Assignment_Rep
10942 (Asmt : Node_Id) return Scenario_Rep_Record
10943 is
10944 Var_Id : constant Entity_Id := Entity (Assignment_Target (Asmt));
10945 Rec : Scenario_Rep_Record;
10946
10947 begin
10948 Rec.Elab_Checks_OK := Is_Elaboration_Checks_OK_Node (Asmt);
10949 Rec.Elab_Warnings_OK := Is_Elaboration_Warnings_OK_Id (Var_Id);
10950 Rec.GM := Ghost_Mode_Of_Node (Asmt);
10951 Rec.SM := SPARK_Mode_Of_Node (Asmt);
10952 Rec.Kind := Variable_Assignment_Scenario;
10953 Rec.Target := Var_Id;
10954
10955 return Rec;
10956 end Create_Variable_Assignment_Rep;
10957
10958 -----------------------------------
10959 -- Create_Variable_Reference_Rep --
10960 -----------------------------------
10961
10962 function Create_Variable_Reference_Rep
10963 (Ref : Node_Id) return Scenario_Rep_Record
10964 is
10965 Rec : Scenario_Rep_Record;
10966
10967 begin
10968 Rec.Elab_Checks_OK := Is_Elaboration_Checks_OK_Node (Ref);
10969 Rec.Elab_Warnings_OK := Is_Elaboration_Warnings_OK_Node (Ref);
10970 Rec.GM := Ghost_Mode_Of_Node (Ref);
10971 Rec.SM := SPARK_Mode_Of_Node (Ref);
10972 Rec.Kind := Variable_Reference_Scenario;
10973 Rec.Target := Target (Ref);
10974
10975 -- Scenario-specific attributes
10976
10977 Rec.Flag_1 := Is_Read (Ref); -- Is_Read_Reference
10978
10979 return Rec;
10980 end Create_Variable_Reference_Rep;
10981
10982 -------------------------
10983 -- Create_Variable_Rep --
10984 -------------------------
10985
10986 function Create_Variable_Rep
10987 (Var_Id : Entity_Id) return Target_Rep_Record
10988 is
10989 Rec : Target_Rep_Record;
10990
10991 begin
10992 Rec.Kind := Variable_Target;
10993
10994 -- Target-specific attributes
10995
10996 Rec.Field_1 := Declaration_Node (Var_Id); -- Variable_Declaration
10997
10998 return Rec;
10999 end Create_Variable_Rep;
11000
11001 -------------
11002 -- Destroy --
11003 -------------
11004
11005 procedure Destroy (S_Id : in out Scenario_Rep_Id) is
11006 pragma Unreferenced (S_Id);
11007 begin
11008 null;
11009 end Destroy;
11010
11011 -------------
11012 -- Destroy --
11013 -------------
11014
11015 procedure Destroy (T_Id : in out Target_Rep_Id) is
11016 pragma Unreferenced (T_Id);
11017 begin
11018 null;
11019 end Destroy;
11020
11021 --------------------------------
11022 -- Disable_Elaboration_Checks --
11023 --------------------------------
11024
11025 procedure Disable_Elaboration_Checks (S_Id : Scenario_Rep_Id) is
11026 pragma Assert (Present (S_Id));
11027 begin
11028 Scenario_Reps.Table (S_Id).Elab_Checks_OK := False;
11029 end Disable_Elaboration_Checks;
11030
11031 --------------------------------
11032 -- Disable_Elaboration_Checks --
11033 --------------------------------
11034
11035 procedure Disable_Elaboration_Checks (T_Id : Target_Rep_Id) is
11036 pragma Assert (Present (T_Id));
11037 begin
11038 Target_Reps.Table (T_Id).Elab_Checks_OK := False;
11039 end Disable_Elaboration_Checks;
11040
11041 ---------------------------
11042 -- Elaboration_Checks_OK --
11043 ---------------------------
11044
11045 function Elaboration_Checks_OK (S_Id : Scenario_Rep_Id) return Boolean is
11046 pragma Assert (Present (S_Id));
11047 begin
11048 return Scenario_Reps.Table (S_Id).Elab_Checks_OK;
11049 end Elaboration_Checks_OK;
11050
11051 ---------------------------
11052 -- Elaboration_Checks_OK --
11053 ---------------------------
11054
11055 function Elaboration_Checks_OK (T_Id : Target_Rep_Id) return Boolean is
11056 pragma Assert (Present (T_Id));
11057 begin
11058 return Target_Reps.Table (T_Id).Elab_Checks_OK;
11059 end Elaboration_Checks_OK;
11060
11061 -----------------------------
11062 -- Elaboration_Warnings_OK --
11063 -----------------------------
11064
11065 function Elaboration_Warnings_OK
11066 (S_Id : Scenario_Rep_Id) return Boolean
11067 is
11068 pragma Assert (Present (S_Id));
11069 begin
11070 return Scenario_Reps.Table (S_Id).Elab_Warnings_OK;
11071 end Elaboration_Warnings_OK;
11072
11073 -----------------------------
11074 -- Elaboration_Warnings_OK --
11075 -----------------------------
11076
11077 function Elaboration_Warnings_OK (T_Id : Target_Rep_Id) return Boolean is
11078 pragma Assert (Present (T_Id));
11079 begin
11080 return Target_Reps.Table (T_Id).Elab_Warnings_OK;
11081 end Elaboration_Warnings_OK;
11082
11083 --------------------------------------
11084 -- Finalize_Internal_Representation --
11085 --------------------------------------
11086
11087 procedure Finalize_Internal_Representation is
11088 begin
11089 ETT_Map.Destroy (Entity_To_Target_Map);
11090 NTS_Map.Destroy (Node_To_Scenario_Map);
11091 end Finalize_Internal_Representation;
11092
11093 -------------------
11094 -- Ghost_Mode_Of --
11095 -------------------
11096
11097 function Ghost_Mode_Of
11098 (S_Id : Scenario_Rep_Id) return Extended_Ghost_Mode
11099 is
11100 pragma Assert (Present (S_Id));
11101 begin
11102 return Scenario_Reps.Table (S_Id).GM;
11103 end Ghost_Mode_Of;
11104
11105 -------------------
11106 -- Ghost_Mode_Of --
11107 -------------------
11108
11109 function Ghost_Mode_Of
11110 (T_Id : Target_Rep_Id) return Extended_Ghost_Mode
11111 is
11112 pragma Assert (Present (T_Id));
11113 begin
11114 return Target_Reps.Table (T_Id).GM;
11115 end Ghost_Mode_Of;
11116
11117 --------------------------
11118 -- Ghost_Mode_Of_Entity --
11119 --------------------------
11120
11121 function Ghost_Mode_Of_Entity
11122 (Id : Entity_Id) return Extended_Ghost_Mode
11123 is
11124 begin
11125 return To_Ghost_Mode (Is_Ignored_Ghost_Entity (Id));
11126 end Ghost_Mode_Of_Entity;
11127
11128 ------------------------
11129 -- Ghost_Mode_Of_Node --
11130 ------------------------
11131
11132 function Ghost_Mode_Of_Node (N : Node_Id) return Extended_Ghost_Mode is
11133 begin
11134 return To_Ghost_Mode (Is_Ignored_Ghost_Node (N));
11135 end Ghost_Mode_Of_Node;
11136
11137 ----------------------------------------
11138 -- Initialize_Internal_Representation --
11139 ----------------------------------------
11140
11141 procedure Initialize_Internal_Representation is
11142 begin
11143 Entity_To_Target_Map := ETT_Map.Create (500);
11144 Node_To_Scenario_Map := NTS_Map.Create (500);
11145 end Initialize_Internal_Representation;
11146
11147 -------------------------
11148 -- Is_Dispatching_Call --
11149 -------------------------
11150
11151 function Is_Dispatching_Call (S_Id : Scenario_Rep_Id) return Boolean is
11152 pragma Assert (Present (S_Id));
11153 pragma Assert (Kind (S_Id) = Call_Scenario);
11154
11155 begin
11156 return Scenario_Reps.Table (S_Id).Flag_1;
11157 end Is_Dispatching_Call;
11158
11159 -----------------------
11160 -- Is_Read_Reference --
11161 -----------------------
11162
11163 function Is_Read_Reference (S_Id : Scenario_Rep_Id) return Boolean is
11164 pragma Assert (Present (S_Id));
11165 pragma Assert (Kind (S_Id) = Variable_Reference_Scenario);
11166
11167 begin
11168 return Scenario_Reps.Table (S_Id).Flag_1;
11169 end Is_Read_Reference;
11170
11171 ----------
11172 -- Kind --
11173 ----------
11174
11175 function Kind (S_Id : Scenario_Rep_Id) return Scenario_Kind is
11176 pragma Assert (Present (S_Id));
11177 begin
11178 return Scenario_Reps.Table (S_Id).Kind;
11179 end Kind;
11180
11181 ----------
11182 -- Kind --
11183 ----------
11184
11185 function Kind (T_Id : Target_Rep_Id) return Target_Kind is
11186 pragma Assert (Present (T_Id));
11187 begin
11188 return Target_Reps.Table (T_Id).Kind;
11189 end Kind;
11190
11191 -----------
11192 -- Level --
11193 -----------
11194
11195 function Level (S_Id : Scenario_Rep_Id) return Enclosing_Level_Kind is
11196 pragma Assert (Present (S_Id));
11197 begin
11198 return Scenario_Reps.Table (S_Id).Level;
11199 end Level;
11200
11201 -------------
11202 -- Present --
11203 -------------
11204
11205 function Present (S_Id : Scenario_Rep_Id) return Boolean is
11206 begin
11207 return S_Id /= No_Scenario_Rep;
11208 end Present;
11209
11210 -------------
11211 -- Present --
11212 -------------
11213
11214 function Present (T_Id : Target_Rep_Id) return Boolean is
11215 begin
11216 return T_Id /= No_Target_Rep;
11217 end Present;
11218
11219 --------------------------------
11220 -- Scenario_Representation_Of --
11221 --------------------------------
11222
11223 function Scenario_Representation_Of
11224 (N : Node_Id;
11225 In_State : Processing_In_State) return Scenario_Rep_Id
11226 is
11227 S_Id : Scenario_Rep_Id;
11228
11229 begin
11230 S_Id := NTS_Map.Get (Node_To_Scenario_Map, N);
11231
11232 -- The elaboration scenario lacks a representation. This indicates
11233 -- that the scenario is encountered for the first time. Create the
11234 -- representation of it.
11235
11236 if not Present (S_Id) then
11237 Scenario_Reps.Append (Create_Scenario_Rep (N, In_State));
11238 S_Id := Scenario_Reps.Last;
11239
11240 -- Associate the internal representation with the elaboration
11241 -- scenario.
11242
11243 NTS_Map.Put (Node_To_Scenario_Map, N, S_Id);
11244 end if;
11245
11246 pragma Assert (Present (S_Id));
11247
11248 return S_Id;
11249 end Scenario_Representation_Of;
11250
11251 --------------------------------
11252 -- Set_Activated_Task_Objects --
11253 --------------------------------
11254
11255 procedure Set_Activated_Task_Objects
11256 (S_Id : Scenario_Rep_Id;
11257 Task_Objs : NE_List.Doubly_Linked_List)
11258 is
11259 pragma Assert (Present (S_Id));
11260 pragma Assert (Kind (S_Id) = Task_Activation_Scenario);
11261
11262 begin
11263 Scenario_Reps.Table (S_Id).List_1 := Task_Objs;
11264 end Set_Activated_Task_Objects;
11265
11266 -----------------------------
11267 -- Set_Activated_Task_Type --
11268 -----------------------------
11269
11270 procedure Set_Activated_Task_Type
11271 (S_Id : Scenario_Rep_Id;
11272 Task_Typ : Entity_Id)
11273 is
11274 pragma Assert (Present (S_Id));
11275 pragma Assert (Kind (S_Id) = Task_Activation_Scenario);
11276
11277 begin
11278 Scenario_Reps.Table (S_Id).Field_1 := Task_Typ;
11279 end Set_Activated_Task_Type;
11280
11281 -------------------
11282 -- SPARK_Mode_Of --
11283 -------------------
11284
11285 function SPARK_Mode_Of
11286 (S_Id : Scenario_Rep_Id) return Extended_SPARK_Mode
11287 is
11288 pragma Assert (Present (S_Id));
11289 begin
11290 return Scenario_Reps.Table (S_Id).SM;
11291 end SPARK_Mode_Of;
11292
11293 -------------------
11294 -- SPARK_Mode_Of --
11295 -------------------
11296
11297 function SPARK_Mode_Of
11298 (T_Id : Target_Rep_Id) return Extended_SPARK_Mode
11299 is
11300 pragma Assert (Present (T_Id));
11301 begin
11302 return Target_Reps.Table (T_Id).SM;
11303 end SPARK_Mode_Of;
11304
11305 --------------------------
11306 -- SPARK_Mode_Of_Entity --
11307 --------------------------
11308
11309 function SPARK_Mode_Of_Entity
11310 (Id : Entity_Id) return Extended_SPARK_Mode
11311 is
11312 Prag : constant Node_Id := SPARK_Pragma (Id);
11313
11314 begin
11315 return
11316 To_SPARK_Mode
11317 (Present (Prag)
11318 and then Get_SPARK_Mode_From_Annotation (Prag) = On);
11319 end SPARK_Mode_Of_Entity;
11320
11321 ------------------------
11322 -- SPARK_Mode_Of_Node --
11323 ------------------------
11324
11325 function SPARK_Mode_Of_Node (N : Node_Id) return Extended_SPARK_Mode is
11326 begin
11327 return To_SPARK_Mode (Is_SPARK_Mode_On_Node (N));
11328 end SPARK_Mode_Of_Node;
11329
11330 ----------------------
11331 -- Spec_Declaration --
11332 ----------------------
11333
11334 function Spec_Declaration (T_Id : Target_Rep_Id) return Node_Id is
11335 pragma Assert (Present (T_Id));
11336 begin
11337 return Target_Reps.Table (T_Id).Spec_Decl;
11338 end Spec_Declaration;
11339
11340 ------------
11341 -- Target --
11342 ------------
11343
11344 function Target (S_Id : Scenario_Rep_Id) return Entity_Id is
11345 pragma Assert (Present (S_Id));
11346 begin
11347 return Scenario_Reps.Table (S_Id).Target;
11348 end Target;
11349
11350 ------------------------------
11351 -- Target_Representation_Of --
11352 ------------------------------
11353
11354 function Target_Representation_Of
11355 (Id : Entity_Id;
11356 In_State : Processing_In_State) return Target_Rep_Id
11357 is
11358 T_Id : Target_Rep_Id;
11359
11360 begin
11361 T_Id := ETT_Map.Get (Entity_To_Target_Map, Id);
11362
11363 -- The elaboration target lacks an internal representation. This
11364 -- indicates that the target is encountered for the first time.
11365 -- Create the internal representation of it.
11366
11367 if not Present (T_Id) then
11368 Target_Reps.Append (Create_Target_Rep (Id, In_State));
11369 T_Id := Target_Reps.Last;
11370
11371 -- Associate the internal representation with the elaboration
11372 -- target.
11373
11374 ETT_Map.Put (Entity_To_Target_Map, Id, T_Id);
11375
11376 -- The Processing phase is working with a partially analyzed tree,
11377 -- where various attributes become available as analysis continues.
11378 -- This case arrises in the context of guaranteed ABE processing.
11379 -- Update the existing representation by including new attributes.
11380
11381 elsif In_State.Representation = Inconsistent_Representation then
11382 Target_Reps.Table (T_Id) := Create_Target_Rep (Id, In_State);
11383
11384 -- Otherwise the Processing phase imposes a particular representation
11385 -- version which is not satisfied by the target. This case arrises
11386 -- when the Processing phase switches from guaranteed ABE checks and
11387 -- diagnostics to some other mode of operation. Update the existing
11388 -- representation to include all attributes.
11389
11390 elsif In_State.Representation /= Version (T_Id) then
11391 Target_Reps.Table (T_Id) := Create_Target_Rep (Id, In_State);
11392 end if;
11393
11394 pragma Assert (Present (T_Id));
11395
11396 return T_Id;
11397 end Target_Representation_Of;
11398
11399 -------------------
11400 -- To_Ghost_Mode --
11401 -------------------
11402
11403 function To_Ghost_Mode
11404 (Ignored_Status : Boolean) return Extended_Ghost_Mode
11405 is
11406 begin
11407 if Ignored_Status then
11408 return Is_Ignored;
11409 else
11410 return Is_Checked_Or_Not_Specified;
11411 end if;
11412 end To_Ghost_Mode;
11413
11414 -------------------
11415 -- To_SPARK_Mode --
11416 -------------------
11417
11418 function To_SPARK_Mode
11419 (On_Status : Boolean) return Extended_SPARK_Mode
11420 is
11421 begin
11422 if On_Status then
11423 return Is_On;
11424 else
11425 return Is_Off_Or_Not_Specified;
11426 end if;
11427 end To_SPARK_Mode;
11428
11429 ----------
11430 -- Unit --
11431 ----------
11432
11433 function Unit (T_Id : Target_Rep_Id) return Entity_Id is
11434 pragma Assert (Present (T_Id));
11435 begin
11436 return Target_Reps.Table (T_Id).Unit;
11437 end Unit;
11438
11439 --------------------------
11440 -- Variable_Declaration --
11441 --------------------------
11442
11443 function Variable_Declaration (T_Id : Target_Rep_Id) return Node_Id is
11444 pragma Assert (Present (T_Id));
11445 pragma Assert (Kind (T_Id) = Variable_Target);
11446
11447 begin
11448 return Target_Reps.Table (T_Id).Field_1;
11449 end Variable_Declaration;
11450
11451 -------------
11452 -- Version --
11453 -------------
11454
11455 function Version (T_Id : Target_Rep_Id) return Representation_Kind is
11456 pragma Assert (Present (T_Id));
11457 begin
11458 return Target_Reps.Table (T_Id).Version;
11459 end Version;
11460 end Internal_Representation;
11461
11462 ----------------------
11463 -- Invocation_Graph --
11464 ----------------------
11465
11466 package body Invocation_Graph is
11467
11468 -----------
11469 -- Types --
11470 -----------
11471
11472 -- The following type represents simplified version of an invocation
11473 -- relation.
11474
11475 type Invoker_Target_Relation is record
11476 Invoker : Entity_Id := Empty;
11477 Target : Entity_Id := Empty;
11478 end record;
11479
11480 -- The following variables define the entities of the dummy elaboration
11481 -- procedures used as origins of library level paths.
11482
11483 Elab_Body_Id : Entity_Id := Empty;
11484 Elab_Spec_Id : Entity_Id := Empty;
11485
11486 ---------------------
11487 -- Data structures --
11488 ---------------------
11489
11490 -- The following set contains all declared invocation constructs. It
11491 -- ensures that the same construct is not declared multiple times in
11492 -- the ALI file of the main unit.
11493
11494 Saved_Constructs_Set : NE_Set.Membership_Set := NE_Set.Nil;
11495
11496 function Hash (Key : Invoker_Target_Relation) return Bucket_Range_Type;
11497 -- Obtain the hash value of pair Key
11498
11499 package IR_Set is new Membership_Sets
11500 (Element_Type => Invoker_Target_Relation,
11501 "=" => "=",
11502 Hash => Hash);
11503
11504 -- The following set contains all recorded simple invocation relations.
11505 -- It ensures that multiple relations involving the same invoker and
11506 -- target do not appear in the ALI file of the main unit.
11507
11508 Saved_Relations_Set : IR_Set.Membership_Set := IR_Set.Nil;
11509
11510 --------------
11511 -- Builders --
11512 --------------
11513
11514 function Signature_Of (Id : Entity_Id) return Invocation_Signature_Id;
11515 pragma Inline (Signature_Of);
11516 -- Obtain the invication signature id of arbitrary entity Id
11517
11518 -----------------------
11519 -- Local subprograms --
11520 -----------------------
11521
11522 procedure Build_Elaborate_Body_Procedure;
11523 pragma Inline (Build_Elaborate_Body_Procedure);
11524 -- Create a dummy elaborate body procedure and store its entity in
11525 -- Elab_Body_Id.
11526
11527 procedure Build_Elaborate_Procedure
11528 (Proc_Id : out Entity_Id;
11529 Proc_Nam : Name_Id;
11530 Loc : Source_Ptr);
11531 pragma Inline (Build_Elaborate_Procedure);
11532 -- Create a dummy elaborate procedure with name Proc_Nam and source
11533 -- location Loc. The entity is returned in Proc_Id.
11534
11535 procedure Build_Elaborate_Spec_Procedure;
11536 pragma Inline (Build_Elaborate_Spec_Procedure);
11537 -- Create a dummy elaborate spec procedure and store its entity in
11538 -- Elab_Spec_Id.
11539
11540 function Build_Subprogram_Invocation
11541 (Subp_Id : Entity_Id) return Node_Id;
11542 pragma Inline (Build_Subprogram_Invocation);
11543 -- Create a dummy call marker that invokes subprogram Subp_Id
11544
11545 function Build_Task_Activation
11546 (Task_Typ : Entity_Id;
11547 In_State : Processing_In_State) return Node_Id;
11548 pragma Inline (Build_Task_Activation);
11549 -- Create a dummy call marker that activates an anonymous task object of
11550 -- type Task_Typ.
11551
11552 procedure Declare_Invocation_Construct
11553 (Constr_Id : Entity_Id;
11554 In_State : Processing_In_State);
11555 pragma Inline (Declare_Invocation_Construct);
11556 -- Declare invocation construct Constr_Id by creating a declaration for
11557 -- it in the ALI file of the main unit. In_State is the current state of
11558 -- the Processing phase.
11559
11560 function Invocation_Graph_Recording_OK return Boolean;
11561 pragma Inline (Invocation_Graph_Recording_OK);
11562 -- Determine whether the invocation graph can be recorded
11563
11564 function Is_Invocation_Scenario (N : Node_Id) return Boolean;
11565 pragma Inline (Is_Invocation_Scenario);
11566 -- Determine whether node N is a suitable scenario for invocation graph
11567 -- recording purposes.
11568
11569 function Is_Invocation_Target (Id : Entity_Id) return Boolean;
11570 pragma Inline (Is_Invocation_Target);
11571 -- Determine whether arbitrary entity Id denotes an invocation target
11572
11573 function Is_Saved_Construct (Constr : Entity_Id) return Boolean;
11574 pragma Inline (Is_Saved_Construct);
11575 -- Determine whether invocation construct Constr has already been
11576 -- declared in the ALI file of the main unit.
11577
11578 function Is_Saved_Relation
11579 (Rel : Invoker_Target_Relation) return Boolean;
11580 pragma Inline (Is_Saved_Relation);
11581 -- Determine whether simple invocation relation Rel has already been
11582 -- recorded in the ALI file of the main unit.
11583
11584 procedure Process_Declarations
11585 (Decls : List_Id;
11586 In_State : Processing_In_State);
11587 pragma Inline (Process_Declarations);
11588 -- Process declaration list Decls by processing all invocation scenarios
11589 -- within it.
11590
11591 procedure Process_Freeze_Node
11592 (Fnode : Node_Id;
11593 In_State : Processing_In_State);
11594 pragma Inline (Process_Freeze_Node);
11595 -- Process freeze node Fnode by processing all invocation scenarios in
11596 -- its Actions list.
11597
11598 procedure Process_Invocation_Activation
11599 (Call : Node_Id;
11600 Call_Rep : Scenario_Rep_Id;
11601 Obj_Id : Entity_Id;
11602 Obj_Rep : Target_Rep_Id;
11603 Task_Typ : Entity_Id;
11604 Task_Rep : Target_Rep_Id;
11605 In_State : Processing_In_State);
11606 pragma Inline (Process_Invocation_Activation);
11607 -- Process activation call Call which activates object Obj_Id of task
11608 -- type Task_Typ by processing all invocation scenarios within the task
11609 -- body. Call_Rep is the representation of the call. Obj_Rep denotes the
11610 -- representation of the object. Task_Rep is the representation of the
11611 -- task type. In_State is the current state of the Processing phase.
11612
11613 procedure Process_Invocation_Body_Scenarios;
11614 pragma Inline (Process_Invocation_Body_Scenarios);
11615 -- Process all library level body scenarios
11616
11617 procedure Process_Invocation_Call
11618 (Call : Node_Id;
11619 Call_Rep : Scenario_Rep_Id;
11620 In_State : Processing_In_State);
11621 pragma Inline (Process_Invocation_Call);
11622 -- Process invocation call scenario Call with representation Call_Rep.
11623 -- In_State is the current state of the Processing phase.
11624
11625 procedure Process_Invocation_Scenario
11626 (N : Node_Id;
11627 In_State : Processing_In_State);
11628 pragma Inline (Process_Invocation_Scenario);
11629 -- Process single invocation scenario N. In_State is the current state
11630 -- of the Processing phase.
11631
11632 procedure Process_Invocation_Scenarios
11633 (Iter : in out NE_Set.Iterator;
11634 In_State : Processing_In_State);
11635 pragma Inline (Process_Invocation_Scenarios);
11636 -- Process all invocation scenarios obtained via iterator Iter. In_State
11637 -- is the current state of the Processing phase.
11638
11639 procedure Process_Invocation_Spec_Scenarios;
11640 pragma Inline (Process_Invocation_Spec_Scenarios);
11641 -- Process all library level spec scenarios
11642
11643 procedure Process_Main_Unit;
11644 pragma Inline (Process_Main_Unit);
11645 -- Process all invocation scenarios within the main unit
11646
11647 procedure Process_Package_Declaration
11648 (Pack_Decl : Node_Id;
11649 In_State : Processing_In_State);
11650 pragma Inline (Process_Package_Declaration);
11651 -- Process package declaration Pack_Decl by processing all invocation
11652 -- scenarios in its visible and private declarations. If the main unit
11653 -- contains a generic, the declarations of the body are also examined.
11654 -- In_State is the current state of the Processing phase.
11655
11656 procedure Process_Protected_Type_Declaration
11657 (Prot_Decl : Node_Id;
11658 In_State : Processing_In_State);
11659 pragma Inline (Process_Protected_Type_Declaration);
11660 -- Process the declarations of protected type Prot_Decl. In_State is the
11661 -- current state of the Processing phase.
11662
11663 procedure Process_Subprogram_Declaration
11664 (Subp_Decl : Node_Id;
11665 In_State : Processing_In_State);
11666 pragma Inline (Process_Subprogram_Declaration);
11667 -- Process subprogram declaration Subp_Decl by processing all invocation
11668 -- scenarios within its body. In_State denotes the current state of the
11669 -- Processing phase.
11670
11671 procedure Process_Subprogram_Instantiation
11672 (Inst : Node_Id;
11673 In_State : Processing_In_State);
11674 pragma Inline (Process_Subprogram_Instantiation);
11675 -- Process subprogram instantiation Inst. In_State is the current state
11676 -- of the Processing phase.
11677
11678 procedure Process_Task_Type_Declaration
11679 (Task_Decl : Node_Id;
11680 In_State : Processing_In_State);
11681 pragma Inline (Process_Task_Type_Declaration);
11682 -- Process task declaration Task_Decl by processing all invocation
11683 -- scenarios within its body. In_State is the current state of the
11684 -- Processing phase.
11685
11686 procedure Record_Full_Invocation_Path (In_State : Processing_In_State);
11687 pragma Inline (Record_Full_Invocation_Path);
11688 -- Record all relations between scenario pairs found in the stack of
11689 -- active scenarios. In_State is the current state of the Processing
11690 -- phase.
11691
11692 procedure Record_Invocation_Graph_Encoding;
11693 pragma Inline (Record_Invocation_Graph_Encoding);
11694 -- Record the encoding format used to capture information related to
11695 -- invocation constructs and relations.
11696
11697 procedure Record_Invocation_Path (In_State : Processing_In_State);
11698 pragma Inline (Record_Invocation_Path);
11699 -- Record the invocation relations found within the path represented in
11700 -- the active scenario stack. In_State denotes the current state of the
11701 -- Processing phase.
11702
11703 procedure Record_Simple_Invocation_Path (In_State : Processing_In_State);
11704 pragma Inline (Record_Simple_Invocation_Path);
11705 -- Record a single relation from the start to the end of the stack of
11706 -- active scenarios. In_State is the current state of the Processing
11707 -- phase.
11708
11709 procedure Record_Invocation_Relation
11710 (Invk_Id : Entity_Id;
11711 Targ_Id : Entity_Id;
11712 In_State : Processing_In_State);
11713 pragma Inline (Record_Invocation_Relation);
11714 -- Record an invocation relation with invoker Invk_Id and target Targ_Id
11715 -- by creating an entry for it in the ALI file of the main unit. Formal
11716 -- In_State denotes the current state of the Processing phase.
11717
11718 procedure Set_Is_Saved_Construct
11719 (Constr : Entity_Id;
11720 Val : Boolean := True);
11721 pragma Inline (Set_Is_Saved_Construct);
11722 -- Mark invocation construct Constr as declared in the ALI file of the
11723 -- main unit depending on value Val.
11724
11725 procedure Set_Is_Saved_Relation
11726 (Rel : Invoker_Target_Relation;
11727 Val : Boolean := True);
11728 pragma Inline (Set_Is_Saved_Relation);
11729 -- Mark simple invocation relation Rel as recorded in the ALI file of
11730 -- the main unit depending on value Val.
11731
11732 function Target_Of
11733 (Pos : Active_Scenario_Pos;
11734 In_State : Processing_In_State) return Entity_Id;
11735 pragma Inline (Target_Of);
11736 -- Given position within the active scenario stack Pos, obtain the
11737 -- target of the indicated scenario. In_State is the current state
11738 -- of the Processing phase.
11739
11740 procedure Traverse_Invocation_Body
11741 (N : Node_Id;
11742 In_State : Processing_In_State);
11743 pragma Inline (Traverse_Invocation_Body);
11744 -- Traverse subprogram body N looking for suitable invocation scenarios
11745 -- that need to be processed for invocation graph recording purposes.
11746 -- In_State is the current state of the Processing phase.
11747
11748 procedure Write_Invocation_Path (In_State : Processing_In_State);
11749 pragma Inline (Write_Invocation_Path);
11750 -- Write out a path represented by the active scenario on the stack to
11751 -- standard output. In_State denotes the current state of the Processing
11752 -- phase.
11753
11754 ------------------------------------
11755 -- Build_Elaborate_Body_Procedure --
11756 ------------------------------------
11757
11758 procedure Build_Elaborate_Body_Procedure is
11759 Body_Decl : Node_Id;
11760 Spec_Decl : Node_Id;
11761
11762 begin
11763 -- Nothing to do when a previous call already created the procedure
11764
11765 if Present (Elab_Body_Id) then
11766 return;
11767 end if;
11768
11769 Spec_And_Body_From_Entity
11770 (Id => Cunit_Entity (Main_Unit),
11771 Body_Decl => Body_Decl,
11772 Spec_Decl => Spec_Decl);
11773
11774 pragma Assert (Present (Body_Decl));
11775
11776 Build_Elaborate_Procedure
11777 (Proc_Id => Elab_Body_Id,
11778 Proc_Nam => Name_B,
11779 Loc => Sloc (Body_Decl));
11780 end Build_Elaborate_Body_Procedure;
11781
11782 -------------------------------
11783 -- Build_Elaborate_Procedure --
11784 -------------------------------
11785
11786 procedure Build_Elaborate_Procedure
11787 (Proc_Id : out Entity_Id;
11788 Proc_Nam : Name_Id;
11789 Loc : Source_Ptr)
11790 is
11791 Proc_Decl : Node_Id;
11792 pragma Unreferenced (Proc_Decl);
11793
11794 begin
11795 Proc_Id := Make_Defining_Identifier (Loc, Proc_Nam);
11796
11797 -- Partially decorate the elaboration procedure because it will not
11798 -- be insertred into the tree and analyzed.
11799
11800 Set_Ekind (Proc_Id, E_Procedure);
11801 Set_Etype (Proc_Id, Standard_Void_Type);
11802 Set_Scope (Proc_Id, Unique_Entity (Cunit_Entity (Main_Unit)));
11803
11804 -- Create a dummy declaration for the elaboration procedure. The
11805 -- declaration does not need to be syntactically legal, but must
11806 -- carry an accurate source location.
11807
11808 Proc_Decl :=
11809 Make_Subprogram_Body (Loc,
11810 Specification =>
11811 Make_Procedure_Specification (Loc,
11812 Defining_Unit_Name => Proc_Id),
11813 Declarations => No_List,
11814 Handled_Statement_Sequence => Empty);
11815 end Build_Elaborate_Procedure;
11816
11817 ------------------------------------
11818 -- Build_Elaborate_Spec_Procedure --
11819 ------------------------------------
11820
11821 procedure Build_Elaborate_Spec_Procedure is
11822 Body_Decl : Node_Id;
11823 Spec_Decl : Node_Id;
11824
11825 begin
11826 -- Nothing to do when a previous call already created the procedure
11827
11828 if Present (Elab_Spec_Id) then
11829 return;
11830 end if;
11831
11832 Spec_And_Body_From_Entity
11833 (Id => Cunit_Entity (Main_Unit),
11834 Body_Decl => Body_Decl,
11835 Spec_Decl => Spec_Decl);
11836
11837 pragma Assert (Present (Spec_Decl));
11838
11839 Build_Elaborate_Procedure
11840 (Proc_Id => Elab_Spec_Id,
11841 Proc_Nam => Name_S,
11842 Loc => Sloc (Spec_Decl));
11843 end Build_Elaborate_Spec_Procedure;
11844
11845 ---------------------------------
11846 -- Build_Subprogram_Invocation --
11847 ---------------------------------
11848
11849 function Build_Subprogram_Invocation
11850 (Subp_Id : Entity_Id) return Node_Id
11851 is
11852 Marker : constant Node_Id := Make_Call_Marker (Sloc (Subp_Id));
11853 Subp_Decl : constant Node_Id := Unit_Declaration_Node (Subp_Id);
11854
11855 begin
11856 -- Create a dummy call marker which invokes the subprogram
11857
11858 Set_Is_Declaration_Level_Node (Marker, False);
11859 Set_Is_Dispatching_Call (Marker, False);
11860 Set_Is_Elaboration_Checks_OK_Node (Marker, False);
11861 Set_Is_Elaboration_Warnings_OK_Node (Marker, False);
11862 Set_Is_Ignored_Ghost_Node (Marker, False);
11863 Set_Is_Source_Call (Marker, False);
11864 Set_Is_SPARK_Mode_On_Node (Marker, False);
11865
11866 -- Invoke the uniform canonical entity of the subprogram
11867
11868 Set_Target (Marker, Canonical_Subprogram (Subp_Id));
11869
11870 -- Partially insert the marker into the tree
11871
11872 Set_Parent (Marker, Parent (Subp_Decl));
11873
11874 return Marker;
11875 end Build_Subprogram_Invocation;
11876
11877 ---------------------------
11878 -- Build_Task_Activation --
11879 ---------------------------
11880
11881 function Build_Task_Activation
11882 (Task_Typ : Entity_Id;
11883 In_State : Processing_In_State) return Node_Id
11884 is
11885 Loc : constant Source_Ptr := Sloc (Task_Typ);
11886 Marker : constant Node_Id := Make_Call_Marker (Loc);
11887 Task_Decl : constant Node_Id := Unit_Declaration_Node (Task_Typ);
11888
11889 Activ_Id : Entity_Id;
11890 Marker_Rep_Id : Scenario_Rep_Id;
11891 Task_Obj : Entity_Id;
11892 Task_Objs : NE_List.Doubly_Linked_List;
11893
11894 begin
11895 -- Create a dummy call marker which activates some tasks
11896
11897 Set_Is_Declaration_Level_Node (Marker, False);
11898 Set_Is_Dispatching_Call (Marker, False);
11899 Set_Is_Elaboration_Checks_OK_Node (Marker, False);
11900 Set_Is_Elaboration_Warnings_OK_Node (Marker, False);
11901 Set_Is_Ignored_Ghost_Node (Marker, False);
11902 Set_Is_Source_Call (Marker, False);
11903 Set_Is_SPARK_Mode_On_Node (Marker, False);
11904
11905 -- Invoke the appropriate version of Activate_Tasks
11906
11907 if Restricted_Profile then
11908 Activ_Id := RTE (RE_Activate_Restricted_Tasks);
11909 else
11910 Activ_Id := RTE (RE_Activate_Tasks);
11911 end if;
11912
11913 Set_Target (Marker, Activ_Id);
11914
11915 -- Partially insert the marker into the tree
11916
11917 Set_Parent (Marker, Parent (Task_Decl));
11918
11919 -- Create a dummy task object. Partially decorate the object because
11920 -- it will not be inserted into the tree and analyzed.
11921
11922 Task_Obj := Make_Temporary (Loc, 'T');
11923 Set_Ekind (Task_Obj, E_Variable);
11924 Set_Etype (Task_Obj, Task_Typ);
11925
11926 -- Associate the dummy task object with the activation call
11927
11928 Task_Objs := NE_List.Create;
11929 NE_List.Append (Task_Objs, Task_Obj);
11930
11931 Marker_Rep_Id := Scenario_Representation_Of (Marker, In_State);
11932 Set_Activated_Task_Objects (Marker_Rep_Id, Task_Objs);
11933 Set_Activated_Task_Type (Marker_Rep_Id, Task_Typ);
11934
11935 return Marker;
11936 end Build_Task_Activation;
11937
11938 ----------------------------------
11939 -- Declare_Invocation_Construct --
11940 ----------------------------------
11941
11942 procedure Declare_Invocation_Construct
11943 (Constr_Id : Entity_Id;
11944 In_State : Processing_In_State)
11945 is
11946 function Body_Placement_Of
11947 (Id : Entity_Id) return Declaration_Placement_Kind;
11948 pragma Inline (Body_Placement_Of);
11949 -- Obtain the placement of arbitrary entity Id's body
11950
11951 function Declaration_Placement_Of_Node
11952 (N : Node_Id) return Declaration_Placement_Kind;
11953 pragma Inline (Declaration_Placement_Of_Node);
11954 -- Obtain the placement of arbitrary node N
11955
11956 function Kind_Of (Id : Entity_Id) return Invocation_Construct_Kind;
11957 pragma Inline (Kind_Of);
11958 -- Obtain the invocation construct kind of arbitrary entity Id
11959
11960 function Spec_Placement_Of
11961 (Id : Entity_Id) return Declaration_Placement_Kind;
11962 pragma Inline (Spec_Placement_Of);
11963 -- Obtain the placement of arbitrary entity Id's spec
11964
11965 -----------------------
11966 -- Body_Placement_Of --
11967 -----------------------
11968
11969 function Body_Placement_Of
11970 (Id : Entity_Id) return Declaration_Placement_Kind
11971 is
11972 Id_Rep : constant Target_Rep_Id :=
11973 Target_Representation_Of (Id, In_State);
11974 Body_Decl : constant Node_Id := Body_Declaration (Id_Rep);
11975 Spec_Decl : constant Node_Id := Spec_Declaration (Id_Rep);
11976
11977 begin
11978 -- The entity has a body
11979
11980 if Present (Body_Decl) then
11981 return Declaration_Placement_Of_Node (Body_Decl);
11982
11983 -- Otherwise the entity must have a spec
11984
11985 else
11986 pragma Assert (Present (Spec_Decl));
11987 return Declaration_Placement_Of_Node (Spec_Decl);
11988 end if;
11989 end Body_Placement_Of;
11990
11991 -----------------------------------
11992 -- Declaration_Placement_Of_Node --
11993 -----------------------------------
11994
11995 function Declaration_Placement_Of_Node
11996 (N : Node_Id) return Declaration_Placement_Kind
11997 is
11998 Main_Unit_Id : constant Entity_Id := Cunit_Entity (Main_Unit);
11999 N_Unit_Id : constant Entity_Id := Find_Top_Unit (N);
12000
12001 begin
12002 -- The node is in the main unit, its placement depends on the main
12003 -- unit kind.
12004
12005 if N_Unit_Id = Main_Unit_Id then
12006
12007 -- The main unit is a body
12008
12009 if Ekind_In (Main_Unit_Id, E_Package_Body,
12010 E_Subprogram_Body)
12011 then
12012 return In_Body;
12013
12014 -- The main unit is a stand-alone subprogram body
12015
12016 elsif Ekind_In (Main_Unit_Id, E_Function, E_Procedure)
12017 and then Nkind (Unit_Declaration_Node (Main_Unit_Id)) =
12018 N_Subprogram_Body
12019 then
12020 return In_Body;
12021
12022 -- Otherwise the main unit is a spec
12023
12024 else
12025 return In_Spec;
12026 end if;
12027
12028 -- Otherwise the node is in the complementary unit of the main
12029 -- unit. The main unit is a body, the node is in the spec.
12030
12031 elsif Ekind_In (Main_Unit_Id, E_Package_Body,
12032 E_Subprogram_Body)
12033 then
12034 return In_Spec;
12035
12036 -- The main unit is a spec, the node is in the body
12037
12038 else
12039 return In_Body;
12040 end if;
12041 end Declaration_Placement_Of_Node;
12042
12043 -------------
12044 -- Kind_Of --
12045 -------------
12046
12047 function Kind_Of (Id : Entity_Id) return Invocation_Construct_Kind is
12048 begin
12049 if Id = Elab_Body_Id then
12050 return Elaborate_Body_Procedure;
12051
12052 elsif Id = Elab_Spec_Id then
12053 return Elaborate_Spec_Procedure;
12054
12055 else
12056 return Regular_Construct;
12057 end if;
12058 end Kind_Of;
12059
12060 -----------------------
12061 -- Spec_Placement_Of --
12062 -----------------------
12063
12064 function Spec_Placement_Of
12065 (Id : Entity_Id) return Declaration_Placement_Kind
12066 is
12067 Id_Rep : constant Target_Rep_Id :=
12068 Target_Representation_Of (Id, In_State);
12069 Body_Decl : constant Node_Id := Body_Declaration (Id_Rep);
12070 Spec_Decl : constant Node_Id := Spec_Declaration (Id_Rep);
12071
12072 begin
12073 -- The entity has a spec
12074
12075 if Present (Spec_Decl) then
12076 return Declaration_Placement_Of_Node (Spec_Decl);
12077
12078 -- Otherwise the entity must have a body
12079
12080 else
12081 pragma Assert (Present (Body_Decl));
12082 return Declaration_Placement_Of_Node (Body_Decl);
12083 end if;
12084 end Spec_Placement_Of;
12085
12086 -- Start of processing for Declare_Invocation_Construct
12087
12088 begin
12089 -- Nothing to do when the construct has already been declared in the
12090 -- ALI file.
12091
12092 if Is_Saved_Construct (Constr_Id) then
12093 return;
12094 end if;
12095
12096 -- Mark the construct as declared in the ALI file
12097
12098 Set_Is_Saved_Construct (Constr_Id);
12099
12100 -- Add the construct in the ALI file
12101
12102 Add_Invocation_Construct
12103 (Body_Placement => Body_Placement_Of (Constr_Id),
12104 Kind => Kind_Of (Constr_Id),
12105 Signature => Signature_Of (Constr_Id),
12106 Spec_Placement => Spec_Placement_Of (Constr_Id),
12107 Update_Units => False);
12108 end Declare_Invocation_Construct;
12109
12110 -------------------------------
12111 -- Finalize_Invocation_Graph --
12112 -------------------------------
12113
12114 procedure Finalize_Invocation_Graph is
12115 begin
12116 NE_Set.Destroy (Saved_Constructs_Set);
12117 IR_Set.Destroy (Saved_Relations_Set);
12118 end Finalize_Invocation_Graph;
12119
12120 ----------
12121 -- Hash --
12122 ----------
12123
12124 function Hash (Key : Invoker_Target_Relation) return Bucket_Range_Type is
12125 pragma Assert (Present (Key.Invoker));
12126 pragma Assert (Present (Key.Target));
12127
12128 begin
12129 return
12130 Hash_Two_Keys
12131 (Bucket_Range_Type (Key.Invoker),
12132 Bucket_Range_Type (Key.Target));
12133 end Hash;
12134
12135 ---------------------------------
12136 -- Initialize_Invocation_Graph --
12137 ---------------------------------
12138
12139 procedure Initialize_Invocation_Graph is
12140 begin
12141 Saved_Constructs_Set := NE_Set.Create (100);
12142 Saved_Relations_Set := IR_Set.Create (200);
12143 end Initialize_Invocation_Graph;
12144
12145 -----------------------------------
12146 -- Invocation_Graph_Recording_OK --
12147 -----------------------------------
12148
12149 function Invocation_Graph_Recording_OK return Boolean is
12150 Main_Cunit : constant Node_Id := Cunit (Main_Unit);
12151
12152 begin
12153 -- Nothing to do when switch -gnatd_G (encode invocation graph in ALI
12154 -- files) is not in effect.
12155
12156 if not Debug_Flag_Underscore_GG then
12157 return False;
12158
12159 -- Nothing to do when compiling for GNATprove because the invocation
12160 -- graph is not needed.
12161
12162 elsif GNATprove_Mode then
12163 return False;
12164
12165 -- Nothing to do when the compilation will not produce an ALI file
12166
12167 elsif Serious_Errors_Detected > 0 then
12168 return False;
12169
12170 -- Nothing to do when the main unit requires a body. Processing the
12171 -- completing body will create the ALI file for the unit and record
12172 -- the invocation graph.
12173
12174 elsif Body_Required (Main_Cunit) then
12175 return False;
12176 end if;
12177
12178 return True;
12179 end Invocation_Graph_Recording_OK;
12180
12181 ----------------------------
12182 -- Is_Invocation_Scenario --
12183 ----------------------------
12184
12185 function Is_Invocation_Scenario (N : Node_Id) return Boolean is
12186 begin
12187 return
12188 Is_Suitable_Access_Taken (N)
12189 or else Is_Suitable_Call (N)
12190 or else Is_Suitable_Instantiation (N);
12191 end Is_Invocation_Scenario;
12192
12193 --------------------------
12194 -- Is_Invocation_Target --
12195 --------------------------
12196
12197 function Is_Invocation_Target (Id : Entity_Id) return Boolean is
12198 begin
12199 -- To qualify, the entity must either come from source, or denote an
12200 -- Ada, bridge, or SPARK target.
12201
12202 return
12203 Comes_From_Source (Id)
12204 or else Is_Ada_Semantic_Target (Id)
12205 or else Is_Bridge_Target (Id)
12206 or else Is_SPARK_Semantic_Target (Id);
12207 end Is_Invocation_Target;
12208
12209 ------------------------
12210 -- Is_Saved_Construct --
12211 ------------------------
12212
12213 function Is_Saved_Construct (Constr : Entity_Id) return Boolean is
12214 pragma Assert (Present (Constr));
12215 begin
12216 return NE_Set.Contains (Saved_Constructs_Set, Constr);
12217 end Is_Saved_Construct;
12218
12219 -----------------------
12220 -- Is_Saved_Relation --
12221 -----------------------
12222
12223 function Is_Saved_Relation
12224 (Rel : Invoker_Target_Relation) return Boolean
12225 is
12226 pragma Assert (Present (Rel.Invoker));
12227 pragma Assert (Present (Rel.Target));
12228
12229 begin
12230 return IR_Set.Contains (Saved_Relations_Set, Rel);
12231 end Is_Saved_Relation;
12232
12233 --------------------------
12234 -- Process_Declarations --
12235 --------------------------
12236
12237 procedure Process_Declarations
12238 (Decls : List_Id;
12239 In_State : Processing_In_State)
12240 is
12241 Decl : Node_Id;
12242
12243 begin
12244 Decl := First (Decls);
12245 while Present (Decl) loop
12246
12247 -- Freeze node
12248
12249 if Nkind (Decl) = N_Freeze_Entity then
12250 Process_Freeze_Node
12251 (Fnode => Decl,
12252 In_State => In_State);
12253
12254 -- Package (nested)
12255
12256 elsif Nkind (Decl) = N_Package_Declaration then
12257 Process_Package_Declaration
12258 (Pack_Decl => Decl,
12259 In_State => In_State);
12260
12261 -- Protected type
12262
12263 elsif Nkind_In (Decl, N_Protected_Type_Declaration,
12264 N_Single_Protected_Declaration)
12265 then
12266 Process_Protected_Type_Declaration
12267 (Prot_Decl => Decl,
12268 In_State => In_State);
12269
12270 -- Subprogram or entry
12271
12272 elsif Nkind_In (Decl, N_Entry_Declaration,
12273 N_Subprogram_Declaration)
12274 then
12275 Process_Subprogram_Declaration
12276 (Subp_Decl => Decl,
12277 In_State => In_State);
12278
12279 -- Subprogram body (stand alone)
12280
12281 elsif Nkind (Decl) = N_Subprogram_Body
12282 and then No (Corresponding_Spec (Decl))
12283 then
12284 Process_Subprogram_Declaration
12285 (Subp_Decl => Decl,
12286 In_State => In_State);
12287
12288 -- Subprogram instantiation
12289
12290 elsif Nkind (Decl) in N_Subprogram_Instantiation then
12291 Process_Subprogram_Instantiation
12292 (Inst => Decl,
12293 In_State => In_State);
12294
12295 -- Task type
12296
12297 elsif Nkind_In (Decl, N_Single_Task_Declaration,
12298 N_Task_Type_Declaration)
12299 then
12300 Process_Task_Type_Declaration
12301 (Task_Decl => Decl,
12302 In_State => In_State);
12303
12304 -- Task type (derived)
12305
12306 elsif Nkind (Decl) = N_Full_Type_Declaration
12307 and then Is_Task_Type (Defining_Entity (Decl))
12308 then
12309 Process_Task_Type_Declaration
12310 (Task_Decl => Decl,
12311 In_State => In_State);
12312 end if;
12313
12314 Next (Decl);
12315 end loop;
12316 end Process_Declarations;
12317
12318 -------------------------
12319 -- Process_Freeze_Node --
12320 -------------------------
12321
12322 procedure Process_Freeze_Node
12323 (Fnode : Node_Id;
12324 In_State : Processing_In_State)
12325 is
12326 begin
12327 Process_Declarations
12328 (Decls => Actions (Fnode),
12329 In_State => In_State);
12330 end Process_Freeze_Node;
12331
12332 -----------------------------------
12333 -- Process_Invocation_Activation --
12334 -----------------------------------
12335
12336 procedure Process_Invocation_Activation
12337 (Call : Node_Id;
12338 Call_Rep : Scenario_Rep_Id;
12339 Obj_Id : Entity_Id;
12340 Obj_Rep : Target_Rep_Id;
12341 Task_Typ : Entity_Id;
12342 Task_Rep : Target_Rep_Id;
12343 In_State : Processing_In_State)
12344 is
12345 pragma Unreferenced (Call);
12346 pragma Unreferenced (Call_Rep);
12347 pragma Unreferenced (Obj_Id);
12348 pragma Unreferenced (Obj_Rep);
12349
12350 begin
12351 -- Nothing to do when the task type appears within an internal unit
12352
12353 if In_Internal_Unit (Task_Typ) then
12354 return;
12355 end if;
12356
12357 -- The task type being activated is within the main unit. Extend the
12358 -- DFS traversal into its body.
12359
12360 if In_Extended_Main_Code_Unit (Task_Typ) then
12361 Traverse_Invocation_Body
12362 (N => Body_Declaration (Task_Rep),
12363 In_State => In_State);
12364
12365 -- The task type being activated resides within an external unit
12366 --
12367 -- Main unit External unit
12368 -- +-----------+ +-------------+
12369 -- | | | |
12370 -- | Start ------------> Task_Typ |
12371 -- | | | |
12372 -- +-----------+ +-------------+
12373 --
12374 -- Record the invocation path which originates from Start and reaches
12375 -- the task type.
12376
12377 else
12378 Record_Invocation_Path (In_State);
12379 end if;
12380 end Process_Invocation_Activation;
12381
12382 ---------------------------------------
12383 -- Process_Invocation_Body_Scenarios --
12384 ---------------------------------------
12385
12386 procedure Process_Invocation_Body_Scenarios is
12387 Iter : NE_Set.Iterator := Iterate_Library_Body_Scenarios;
12388 begin
12389 Process_Invocation_Scenarios
12390 (Iter => Iter,
12391 In_State => Invocation_Body_State);
12392 end Process_Invocation_Body_Scenarios;
12393
12394 -----------------------------
12395 -- Process_Invocation_Call --
12396 -----------------------------
12397
12398 procedure Process_Invocation_Call
12399 (Call : Node_Id;
12400 Call_Rep : Scenario_Rep_Id;
12401 In_State : Processing_In_State)
12402 is
12403 pragma Unreferenced (Call);
12404
12405 Subp_Id : constant Entity_Id := Target (Call_Rep);
12406 Subp_Rep : constant Target_Rep_Id :=
12407 Target_Representation_Of (Subp_Id, In_State);
12408
12409 begin
12410 -- Nothing to do when the subprogram appears within an internal unit
12411
12412 if In_Internal_Unit (Subp_Id) then
12413 return;
12414
12415 -- Nothing to do for an abstract subprogram because it has no body to
12416 -- examine.
12417
12418 elsif Ekind_In (Subp_Id, E_Function, E_Procedure)
12419 and then Is_Abstract_Subprogram (Subp_Id)
12420 then
12421 return;
12422
12423 -- Nothin to do for a formal subprogram because it has no body to
12424 -- examine.
12425
12426 elsif Is_Formal_Subprogram (Subp_Id) then
12427 return;
12428 end if;
12429
12430 -- The subprogram being called is within the main unit. Extend the
12431 -- DFS traversal into its barrier function and body.
12432
12433 if In_Extended_Main_Code_Unit (Subp_Id) then
12434 if Ekind_In (Subp_Id, E_Entry, E_Entry_Family, E_Procedure) then
12435 Traverse_Invocation_Body
12436 (N => Barrier_Body_Declaration (Subp_Rep),
12437 In_State => In_State);
12438 end if;
12439
12440 Traverse_Invocation_Body
12441 (N => Body_Declaration (Subp_Rep),
12442 In_State => In_State);
12443
12444 -- The subprogram being called resides within an external unit
12445 --
12446 -- Main unit External unit
12447 -- +-----------+ +-------------+
12448 -- | | | |
12449 -- | Start ------------> Subp_Id |
12450 -- | | | |
12451 -- +-----------+ +-------------+
12452 --
12453 -- Record the invocation path which originates from Start and reaches
12454 -- the subprogram.
12455
12456 else
12457 Record_Invocation_Path (In_State);
12458 end if;
12459 end Process_Invocation_Call;
12460
12461 ---------------------------------
12462 -- Process_Invocation_Scenario --
12463 ---------------------------------
12464
12465 procedure Process_Invocation_Scenario
12466 (N : Node_Id;
12467 In_State : Processing_In_State)
12468 is
12469 Scen : constant Node_Id := Scenario (N);
12470 Scen_Rep : Scenario_Rep_Id;
12471
12472 begin
12473 -- Add the current scenario to the stack of active scenarios
12474
12475 Push_Active_Scenario (Scen);
12476
12477 -- Call or task activation
12478
12479 if Is_Suitable_Call (Scen) then
12480 Scen_Rep := Scenario_Representation_Of (Scen, In_State);
12481
12482 -- Routine Build_Call_Marker creates call markers regardless of
12483 -- whether the call occurs within the main unit or not. This way
12484 -- the serialization of internal names is kept consistent. Only
12485 -- call markers found within the main unit must be processed.
12486
12487 if In_Main_Context (Scen) then
12488 Scen_Rep := Scenario_Representation_Of (Scen, In_State);
12489
12490 if Kind (Scen_Rep) = Call_Scenario then
12491 Process_Invocation_Call
12492 (Call => Scen,
12493 Call_Rep => Scen_Rep,
12494 In_State => In_State);
12495
12496 else
12497 pragma Assert (Kind (Scen_Rep) = Task_Activation_Scenario);
12498
12499 Process_Activation
12500 (Call => Scen,
12501 Call_Rep => Scen_Rep,
12502 Processor => Process_Invocation_Activation'Access,
12503 In_State => In_State);
12504 end if;
12505 end if;
12506 end if;
12507
12508 -- Remove the current scenario from the stack of active scenarios
12509 -- once all invocation constructs and paths have been saved.
12510
12511 Pop_Active_Scenario (Scen);
12512 end Process_Invocation_Scenario;
12513
12514 ----------------------------------
12515 -- Process_Invocation_Scenarios --
12516 ----------------------------------
12517
12518 procedure Process_Invocation_Scenarios
12519 (Iter : in out NE_Set.Iterator;
12520 In_State : Processing_In_State)
12521 is
12522 N : Node_Id;
12523
12524 begin
12525 while NE_Set.Has_Next (Iter) loop
12526 NE_Set.Next (Iter, N);
12527
12528 -- Reset the traversed status of all subprogram bodies because the
12529 -- current invocation scenario acts as a new DFS traversal root.
12530
12531 Reset_Traversed_Bodies;
12532
12533 Process_Invocation_Scenario (N, In_State);
12534 end loop;
12535 end Process_Invocation_Scenarios;
12536
12537 ---------------------------------------
12538 -- Process_Invocation_Spec_Scenarios --
12539 ---------------------------------------
12540
12541 procedure Process_Invocation_Spec_Scenarios is
12542 Iter : NE_Set.Iterator := Iterate_Library_Spec_Scenarios;
12543 begin
12544 Process_Invocation_Scenarios
12545 (Iter => Iter,
12546 In_State => Invocation_Spec_State);
12547 end Process_Invocation_Spec_Scenarios;
12548
12549 -----------------------
12550 -- Process_Main_Unit --
12551 -----------------------
12552
12553 procedure Process_Main_Unit is
12554 Unit_Decl : constant Node_Id := Unit (Cunit (Main_Unit));
12555 Spec_Id : Entity_Id;
12556
12557 begin
12558 -- The main unit is a [generic] package body
12559
12560 if Nkind (Unit_Decl) = N_Package_Body then
12561 Spec_Id := Corresponding_Spec (Unit_Decl);
12562 pragma Assert (Present (Spec_Id));
12563
12564 Process_Package_Declaration
12565 (Pack_Decl => Unit_Declaration_Node (Spec_Id),
12566 In_State => Invocation_Construct_State);
12567
12568 -- The main unit is a [generic] package declaration
12569
12570 elsif Nkind (Unit_Decl) = N_Package_Declaration then
12571 Process_Package_Declaration
12572 (Pack_Decl => Unit_Decl,
12573 In_State => Invocation_Construct_State);
12574
12575 -- The main unit is a [generic] subprogram body
12576
12577 elsif Nkind (Unit_Decl) = N_Subprogram_Body then
12578 Spec_Id := Corresponding_Spec (Unit_Decl);
12579
12580 -- The body completes a previous declaration
12581
12582 if Present (Spec_Id) then
12583 Process_Subprogram_Declaration
12584 (Subp_Decl => Unit_Declaration_Node (Spec_Id),
12585 In_State => Invocation_Construct_State);
12586
12587 -- Otherwise the body is stand-alone
12588
12589 else
12590 Process_Subprogram_Declaration
12591 (Subp_Decl => Unit_Decl,
12592 In_State => Invocation_Construct_State);
12593 end if;
12594
12595 -- The main unit is a subprogram instantiation
12596
12597 elsif Nkind (Unit_Decl) in N_Subprogram_Instantiation then
12598 Process_Subprogram_Instantiation
12599 (Inst => Unit_Decl,
12600 In_State => Invocation_Construct_State);
12601
12602 -- The main unit is an imported subprogram declaration
12603
12604 elsif Nkind (Unit_Decl) = N_Subprogram_Declaration then
12605 Process_Subprogram_Declaration
12606 (Subp_Decl => Unit_Decl,
12607 In_State => Invocation_Construct_State);
12608 end if;
12609 end Process_Main_Unit;
12610
12611 ---------------------------------
12612 -- Process_Package_Declaration --
12613 ---------------------------------
12614
12615 procedure Process_Package_Declaration
12616 (Pack_Decl : Node_Id;
12617 In_State : Processing_In_State)
12618 is
12619 Body_Id : constant Entity_Id := Corresponding_Body (Pack_Decl);
12620 Spec : constant Node_Id := Specification (Pack_Decl);
12621 Spec_Id : constant Entity_Id := Defining_Entity (Pack_Decl);
12622
12623 begin
12624 -- Add a declaration for the generic package in the ALI of the main
12625 -- unit in case a client unit instantiates it.
12626
12627 if Ekind (Spec_Id) = E_Generic_Package then
12628 Declare_Invocation_Construct
12629 (Constr_Id => Spec_Id,
12630 In_State => In_State);
12631
12632 -- Otherwise inspect the visible and private declarations of the
12633 -- package for invocation constructs.
12634
12635 else
12636 Process_Declarations
12637 (Decls => Visible_Declarations (Spec),
12638 In_State => In_State);
12639
12640 Process_Declarations
12641 (Decls => Private_Declarations (Spec),
12642 In_State => In_State);
12643
12644 -- The package body containst at least one generic unit or an
12645 -- inlinable subprogram. Such constructs may grant clients of
12646 -- the main unit access to the private enclosing contexts of
12647 -- the constructs. Process the main unit body to discover and
12648 -- encode relevant invocation constructs and relations that
12649 -- may ultimately reach an external unit.
12650
12651 if Present (Body_Id)
12652 and then Save_Invocation_Graph_Of_Body (Cunit (Main_Unit))
12653 then
12654 Process_Declarations
12655 (Decls => Declarations (Unit_Declaration_Node (Body_Id)),
12656 In_State => In_State);
12657 end if;
12658 end if;
12659 end Process_Package_Declaration;
12660
12661 ----------------------------------------
12662 -- Process_Protected_Type_Declaration --
12663 ----------------------------------------
12664
12665 procedure Process_Protected_Type_Declaration
12666 (Prot_Decl : Node_Id;
12667 In_State : Processing_In_State)
12668 is
12669 Prot_Def : constant Node_Id := Protected_Definition (Prot_Decl);
12670
12671 begin
12672 if Present (Prot_Def) then
12673 Process_Declarations
12674 (Decls => Visible_Declarations (Prot_Def),
12675 In_State => In_State);
12676 end if;
12677 end Process_Protected_Type_Declaration;
12678
12679 ------------------------------------
12680 -- Process_Subprogram_Declaration --
12681 ------------------------------------
12682
12683 procedure Process_Subprogram_Declaration
12684 (Subp_Decl : Node_Id;
12685 In_State : Processing_In_State)
12686 is
12687 Subp_Id : constant Entity_Id := Defining_Entity (Subp_Decl);
12688
12689 begin
12690 -- Nothing to do when the subprogram is not an invocation target
12691
12692 if not Is_Invocation_Target (Subp_Id) then
12693 return;
12694 end if;
12695
12696 -- Add a declaration for the subprogram in the ALI file of the main
12697 -- unit in case a client unit calls or instantiates it.
12698
12699 Declare_Invocation_Construct
12700 (Constr_Id => Subp_Id,
12701 In_State => In_State);
12702
12703 -- Do not process subprograms without a body because they do not
12704 -- contain any invocation scenarios.
12705
12706 if Is_Bodiless_Subprogram (Subp_Id) then
12707 null;
12708
12709 -- Do not process generic subprograms because generics must not be
12710 -- examined.
12711
12712 elsif Is_Generic_Subprogram (Subp_Id) then
12713 null;
12714
12715 -- Otherwise create a dummy scenario which calls the subprogram to
12716 -- act as a root for a DFS traversal.
12717
12718 else
12719 -- Reset the traversed status of all subprogram bodies because the
12720 -- subprogram acts as a new DFS traversal root.
12721
12722 Reset_Traversed_Bodies;
12723
12724 Process_Invocation_Scenario
12725 (N => Build_Subprogram_Invocation (Subp_Id),
12726 In_State => In_State);
12727 end if;
12728 end Process_Subprogram_Declaration;
12729
12730 --------------------------------------
12731 -- Process_Subprogram_Instantiation --
12732 --------------------------------------
12733
12734 procedure Process_Subprogram_Instantiation
12735 (Inst : Node_Id;
12736 In_State : Processing_In_State)
12737 is
12738 begin
12739 -- Add a declaration for the instantiation in the ALI file of the
12740 -- main unit in case a client unit calls it.
12741
12742 Declare_Invocation_Construct
12743 (Constr_Id => Defining_Entity (Inst),
12744 In_State => In_State);
12745 end Process_Subprogram_Instantiation;
12746
12747 -----------------------------------
12748 -- Process_Task_Type_Declaration --
12749 -----------------------------------
12750
12751 procedure Process_Task_Type_Declaration
12752 (Task_Decl : Node_Id;
12753 In_State : Processing_In_State)
12754 is
12755 Task_Typ : constant Entity_Id := Defining_Entity (Task_Decl);
12756 Task_Def : Node_Id;
12757
12758 begin
12759 -- Add a declaration for the task type the ALI file of the main unit
12760 -- in case a client unit creates a task object and activates it.
12761
12762 Declare_Invocation_Construct
12763 (Constr_Id => Task_Typ,
12764 In_State => In_State);
12765
12766 -- Process the entries of the task type because they represent valid
12767 -- entry points into the task body.
12768
12769 if Nkind_In (Task_Decl, N_Single_Task_Declaration,
12770 N_Task_Type_Declaration)
12771 then
12772 Task_Def := Task_Definition (Task_Decl);
12773
12774 if Present (Task_Def) then
12775 Process_Declarations
12776 (Decls => Visible_Declarations (Task_Def),
12777 In_State => In_State);
12778 end if;
12779 end if;
12780
12781 -- Reset the traversed status of all subprogram bodies because the
12782 -- task type acts as a new DFS traversal root.
12783
12784 Reset_Traversed_Bodies;
12785
12786 -- Create a dummy scenario which activates an anonymous object of the
12787 -- task type to acts as a root of a DFS traversal.
12788
12789 Process_Invocation_Scenario
12790 (N => Build_Task_Activation (Task_Typ, In_State),
12791 In_State => In_State);
12792 end Process_Task_Type_Declaration;
12793
12794 ---------------------------------
12795 -- Record_Full_Invocation_Path --
12796 ---------------------------------
12797
12798 procedure Record_Full_Invocation_Path (In_State : Processing_In_State) is
12799 package Scenarios renames Active_Scenario_Stack;
12800
12801 begin
12802 -- The path originates from the elaboration of the body. Add an extra
12803 -- relation from the elaboration body procedure to the first active
12804 -- scenario.
12805
12806 if In_State.Processing = Invocation_Body_Processing then
12807 Build_Elaborate_Body_Procedure;
12808
12809 Record_Invocation_Relation
12810 (Invk_Id => Elab_Body_Id,
12811 Targ_Id => Target_Of (Scenarios.First, In_State),
12812 In_State => In_State);
12813
12814 -- The path originates from the elaboration of the spec. Add an extra
12815 -- relation from the elaboration spec procedure to the first active
12816 -- scenario.
12817
12818 elsif In_State.Processing = Invocation_Spec_Processing then
12819 Build_Elaborate_Spec_Procedure;
12820
12821 Record_Invocation_Relation
12822 (Invk_Id => Elab_Spec_Id,
12823 Targ_Id => Target_Of (Scenarios.First, In_State),
12824 In_State => In_State);
12825 end if;
12826
12827 -- Record individual relations formed by pairs of scenarios
12828
12829 for Index in Scenarios.First .. Scenarios.Last - 1 loop
12830 Record_Invocation_Relation
12831 (Invk_Id => Target_Of (Index, In_State),
12832 Targ_Id => Target_Of (Index + 1, In_State),
12833 In_State => In_State);
12834 end loop;
12835 end Record_Full_Invocation_Path;
12836
12837 -----------------------------
12838 -- Record_Invocation_Graph --
12839 -----------------------------
12840
12841 procedure Record_Invocation_Graph is
12842 begin
12843 -- Nothing to do when the invocation graph is not recorded
12844
12845 if not Invocation_Graph_Recording_OK then
12846 return;
12847 end if;
12848
12849 -- Save the encoding format used to capture information about the
12850 -- invocation constructs and relations in the ALI file of the main
12851 -- unit.
12852
12853 Record_Invocation_Graph_Encoding;
12854
12855 -- Examine all library level invocation scenarios and perform DFS
12856 -- traversals from each one. Encode a path in the ALI file of the
12857 -- main unit if it reaches into an external unit.
12858
12859 Process_Invocation_Body_Scenarios;
12860 Process_Invocation_Spec_Scenarios;
12861
12862 -- Examine all invocation constructs within the spec and body of the
12863 -- main unit and perform DFS traversals from each one. Encode a path
12864 -- in the ALI file of the main unit if it reaches into an external
12865 -- unit.
12866
12867 Process_Main_Unit;
12868 end Record_Invocation_Graph;
12869
12870 --------------------------------------
12871 -- Record_Invocation_Graph_Encoding --
12872 --------------------------------------
12873
12874 procedure Record_Invocation_Graph_Encoding is
12875 Kind : Invocation_Graph_Encoding_Kind := No_Encoding;
12876
12877 begin
12878 -- Switch -gnatd_F (encode full invocation paths in ALI files) is in
12879 -- effect.
12880
12881 if Debug_Flag_Underscore_FF then
12882 Kind := Full_Path_Encoding;
12883 else
12884 Kind := Endpoints_Encoding;
12885 end if;
12886
12887 -- Save the encoding format in the ALI file of the main unit
12888
12889 Set_Invocation_Graph_Encoding
12890 (Kind => Kind,
12891 Update_Units => False);
12892 end Record_Invocation_Graph_Encoding;
12893
12894 ----------------------------
12895 -- Record_Invocation_Path --
12896 ----------------------------
12897
12898 procedure Record_Invocation_Path (In_State : Processing_In_State) is
12899 package Scenarios renames Active_Scenario_Stack;
12900
12901 begin
12902 -- Save a path when the active scenario stack contains at least one
12903 -- invocation scenario.
12904
12905 if Scenarios.Last - Scenarios.First < 0 then
12906 return;
12907 end if;
12908
12909 -- Register all relations in the path when switch -gnatd_F (encode
12910 -- full invocation paths in ALI files) is in effect.
12911
12912 if Debug_Flag_Underscore_FF then
12913 Record_Full_Invocation_Path (In_State);
12914
12915 -- Otherwise register a single relation
12916
12917 else
12918 Record_Simple_Invocation_Path (In_State);
12919 end if;
12920
12921 Write_Invocation_Path (In_State);
12922 end Record_Invocation_Path;
12923
12924 --------------------------------
12925 -- Record_Invocation_Relation --
12926 --------------------------------
12927
12928 procedure Record_Invocation_Relation
12929 (Invk_Id : Entity_Id;
12930 Targ_Id : Entity_Id;
12931 In_State : Processing_In_State)
12932 is
12933 pragma Assert (Present (Invk_Id));
12934 pragma Assert (Present (Targ_Id));
12935
12936 procedure Get_Invocation_Attributes
12937 (Extra : out Entity_Id;
12938 Kind : out Invocation_Kind);
12939 pragma Inline (Get_Invocation_Attributes);
12940 -- Return the additional entity used in error diagnostics in Extra
12941 -- and the invocation kind in Kind which pertain to the invocation
12942 -- relation with invoker Invk_Id and target Targ_Id.
12943
12944 -------------------------------
12945 -- Get_Invocation_Attributes --
12946 -------------------------------
12947
12948 procedure Get_Invocation_Attributes
12949 (Extra : out Entity_Id;
12950 Kind : out Invocation_Kind)
12951 is
12952 Targ_Rep : constant Target_Rep_Id :=
12953 Target_Representation_Of (Targ_Id, In_State);
12954 Spec_Decl : constant Node_Id := Spec_Declaration (Targ_Rep);
12955
12956 begin
12957 -- Accept within a task body
12958
12959 if Is_Accept_Alternative_Proc (Targ_Id) then
12960 Extra := Receiving_Entry (Targ_Id);
12961 Kind := Accept_Alternative;
12962
12963 -- Activation of a task object
12964
12965 elsif Is_Activation_Proc (Targ_Id)
12966 or else Is_Task_Type (Targ_Id)
12967 then
12968 Extra := Empty;
12969 Kind := Task_Activation;
12970
12971 -- Controlled adjustment actions
12972
12973 elsif Is_Controlled_Proc (Targ_Id, Name_Adjust) then
12974 Extra := First_Formal_Type (Targ_Id);
12975 Kind := Controlled_Adjustment;
12976
12977 -- Controlled finalization actions
12978
12979 elsif Is_Controlled_Proc (Targ_Id, Name_Finalize)
12980 or else Is_Finalizer_Proc (Targ_Id)
12981 then
12982 Extra := First_Formal_Type (Targ_Id);
12983 Kind := Controlled_Finalization;
12984
12985 -- Controlled initialization actions
12986
12987 elsif Is_Controlled_Proc (Targ_Id, Name_Initialize) then
12988 Extra := First_Formal_Type (Targ_Id);
12989 Kind := Controlled_Initialization;
12990
12991 -- Default_Initial_Condition verification
12992
12993 elsif Is_Default_Initial_Condition_Proc (Targ_Id) then
12994 Extra := First_Formal_Type (Targ_Id);
12995 Kind := Default_Initial_Condition_Verification;
12996
12997 -- Initialization of object
12998
12999 elsif Is_Init_Proc (Targ_Id) then
13000 Extra := First_Formal_Type (Targ_Id);
13001 Kind := Type_Initialization;
13002
13003 -- Initial_Condition verification
13004
13005 elsif Is_Initial_Condition_Proc (Targ_Id) then
13006 Extra := First_Formal_Type (Targ_Id);
13007 Kind := Initial_Condition_Verification;
13008
13009 -- Instantiation
13010
13011 elsif Is_Generic_Unit (Targ_Id) then
13012 Extra := Empty;
13013 Kind := Instantiation;
13014
13015 -- Internal controlled adjustment actions
13016
13017 elsif Is_TSS (Targ_Id, TSS_Deep_Adjust) then
13018 Extra := First_Formal_Type (Targ_Id);
13019 Kind := Internal_Controlled_Adjustment;
13020
13021 -- Internal controlled finalization actions
13022
13023 elsif Is_TSS (Targ_Id, TSS_Deep_Finalize) then
13024 Extra := First_Formal_Type (Targ_Id);
13025 Kind := Internal_Controlled_Finalization;
13026
13027 -- Internal controlled initialization actions
13028
13029 elsif Is_TSS (Targ_Id, TSS_Deep_Initialize) then
13030 Extra := First_Formal_Type (Targ_Id);
13031 Kind := Internal_Controlled_Initialization;
13032
13033 -- Invariant verification
13034
13035 elsif Is_Invariant_Proc (Targ_Id)
13036 or else Is_Partial_Invariant_Proc (Targ_Id)
13037 then
13038 Extra := First_Formal_Type (Targ_Id);
13039 Kind := Invariant_Verification;
13040
13041 -- Postcondition verification
13042
13043 elsif Is_Postconditions_Proc (Targ_Id) then
13044 Extra := Find_Enclosing_Scope (Spec_Decl);
13045 Kind := Postcondition_Verification;
13046
13047 -- Protected entry call
13048
13049 elsif Is_Protected_Entry (Targ_Id) then
13050 Extra := Empty;
13051 Kind := Protected_Entry_Call;
13052
13053 -- Protected subprogram call
13054
13055 elsif Is_Protected_Subp (Targ_Id) then
13056 Extra := Empty;
13057 Kind := Protected_Subprogram_Call;
13058
13059 -- Task entry call
13060
13061 elsif Is_Task_Entry (Targ_Id) then
13062 Extra := Empty;
13063 Kind := Task_Entry_Call;
13064
13065 -- Entry, operator, or subprogram call. This case must come last
13066 -- because most invocations above are variations of this case.
13067
13068 elsif Ekind_In (Targ_Id, E_Entry,
13069 E_Function,
13070 E_Operator,
13071 E_Procedure)
13072 then
13073 Extra := Empty;
13074 Kind := Call;
13075
13076 else
13077 pragma Assert (False);
13078 Extra := Empty;
13079 Kind := No_Invocation;
13080 end if;
13081 end Get_Invocation_Attributes;
13082
13083 -- Local variables
13084
13085 Extra : Entity_Id;
13086 Extra_Nam : Name_Id;
13087 Kind : Invocation_Kind;
13088 Rel : Invoker_Target_Relation;
13089
13090 -- Start of processing for Record_Invocation_Relation
13091
13092 begin
13093 Rel.Invoker := Invk_Id;
13094 Rel.Target := Targ_Id;
13095
13096 -- Nothing to do when the invocation relation has already been
13097 -- recorded in ALI file of the main unit.
13098
13099 if Is_Saved_Relation (Rel) then
13100 return;
13101 end if;
13102
13103 -- Mark the relation as recorded in the ALI file
13104
13105 Set_Is_Saved_Relation (Rel);
13106
13107 -- Declare the invoker in the ALI file
13108
13109 Declare_Invocation_Construct
13110 (Constr_Id => Invk_Id,
13111 In_State => In_State);
13112
13113 -- Obtain the invocation-specific attributes of the relation
13114
13115 Get_Invocation_Attributes (Extra, Kind);
13116
13117 -- Certain invocations lack an extra entity used in error diagnostics
13118
13119 if Present (Extra) then
13120 Extra_Nam := Chars (Extra);
13121 else
13122 Extra_Nam := No_Name;
13123 end if;
13124
13125 -- Add the relation in the ALI file
13126
13127 Add_Invocation_Relation
13128 (Extra => Extra_Nam,
13129 Invoker => Signature_Of (Invk_Id),
13130 Kind => Kind,
13131 Target => Signature_Of (Targ_Id),
13132 Update_Units => False);
13133 end Record_Invocation_Relation;
13134
13135 -----------------------------------
13136 -- Record_Simple_Invocation_Path --
13137 -----------------------------------
13138
13139 procedure Record_Simple_Invocation_Path
13140 (In_State : Processing_In_State)
13141 is
13142 package Scenarios renames Active_Scenario_Stack;
13143
13144 Last_Targ : constant Entity_Id :=
13145 Target_Of (Scenarios.Last, In_State);
13146 First_Targ : Entity_Id;
13147
13148 begin
13149 -- The path originates from the elaboration of the body. Add an extra
13150 -- relation from the elaboration body procedure to the first active
13151 -- scenario.
13152
13153 if In_State.Processing = Invocation_Body_Processing then
13154 Build_Elaborate_Body_Procedure;
13155 First_Targ := Elab_Body_Id;
13156
13157 -- The path originates from the elaboration of the spec. Add an extra
13158 -- relation from the elaboration spec procedure to the first active
13159 -- scenario.
13160
13161 elsif In_State.Processing = Invocation_Spec_Processing then
13162 Build_Elaborate_Spec_Procedure;
13163 First_Targ := Elab_Spec_Id;
13164
13165 else
13166 First_Targ := Target_Of (Scenarios.First, In_State);
13167 end if;
13168
13169 -- Record a single relation from the first to the last scenario
13170
13171 if First_Targ /= Last_Targ then
13172 Record_Invocation_Relation
13173 (Invk_Id => First_Targ,
13174 Targ_Id => Last_Targ,
13175 In_State => In_State);
13176 end if;
13177 end Record_Simple_Invocation_Path;
13178
13179 ----------------------------
13180 -- Set_Is_Saved_Construct --
13181 ----------------------------
13182
13183 procedure Set_Is_Saved_Construct
13184 (Constr : Entity_Id;
13185 Val : Boolean := True)
13186 is
13187 pragma Assert (Present (Constr));
13188
13189 begin
13190 if Val then
13191 NE_Set.Insert (Saved_Constructs_Set, Constr);
13192 else
13193 NE_Set.Delete (Saved_Constructs_Set, Constr);
13194 end if;
13195 end Set_Is_Saved_Construct;
13196
13197 ---------------------------
13198 -- Set_Is_Saved_Relation --
13199 ---------------------------
13200
13201 procedure Set_Is_Saved_Relation
13202 (Rel : Invoker_Target_Relation;
13203 Val : Boolean := True)
13204 is
13205 begin
13206 if Val then
13207 IR_Set.Insert (Saved_Relations_Set, Rel);
13208 else
13209 IR_Set.Delete (Saved_Relations_Set, Rel);
13210 end if;
13211 end Set_Is_Saved_Relation;
13212
13213 ------------------
13214 -- Signature_Of --
13215 ------------------
13216
13217 function Signature_Of (Id : Entity_Id) return Invocation_Signature_Id is
13218 Loc : constant Source_Ptr := Sloc (Id);
13219
13220 function Instantiation_Locations return Name_Id;
13221 pragma Inline (Instantiation_Locations);
13222 -- Create a concatenation of all lines and colums of each instance
13223 -- where source location Loc appears. Return No_Name if no instances
13224 -- exist.
13225
13226 function Qualified_Scope return Name_Id;
13227 pragma Inline (Qualified_Scope);
13228 -- Obtain the qualified name of Id's scope
13229
13230 -----------------------------
13231 -- Instantiation_Locations --
13232 -----------------------------
13233
13234 function Instantiation_Locations return Name_Id is
13235 Buffer : Bounded_String (2052);
13236 Inst : Source_Ptr;
13237 Loc_Nam : Name_Id;
13238 SFI : Source_File_Index;
13239
13240 begin
13241 SFI := Get_Source_File_Index (Loc);
13242 Inst := Instantiation (SFI);
13243
13244 -- The location is within an instance. Construct a concatenation
13245 -- of all lines and colums of each individual instance using the
13246 -- following format:
13247 --
13248 -- line1_column1_line2_column2_ ... _lineN_columnN
13249
13250 if Inst /= No_Location then
13251 loop
13252 Append (Buffer, Nat (Get_Logical_Line_Number (Inst)));
13253 Append (Buffer, '_');
13254 Append (Buffer, Nat (Get_Column_Number (Inst)));
13255
13256 SFI := Get_Source_File_Index (Inst);
13257 Inst := Instantiation (SFI);
13258
13259 exit when Inst = No_Location;
13260
13261 Append (Buffer, '_');
13262 end loop;
13263
13264 Loc_Nam := Name_Find (Buffer);
13265 return Loc_Nam;
13266
13267 -- Otherwise there no instances are involved
13268
13269 else
13270 return No_Name;
13271 end if;
13272 end Instantiation_Locations;
13273
13274 ---------------------
13275 -- Qualified_Scope --
13276 ---------------------
13277
13278 function Qualified_Scope return Name_Id is
13279 Scop : Entity_Id;
13280
13281 begin
13282 Scop := Scope (Id);
13283
13284 -- The entity appears within an anonymous concurrent type created
13285 -- for a single protected or task type declaration. Use the entity
13286 -- of the anonymous object as it represents the original scope.
13287
13288 if Is_Concurrent_Type (Scop)
13289 and then Present (Anonymous_Object (Scop))
13290 then
13291 Scop := Anonymous_Object (Scop);
13292 end if;
13293
13294 return Get_Qualified_Name (Scop);
13295 end Qualified_Scope;
13296
13297 -- Start of processing for Signature_Of
13298
13299 begin
13300 return
13301 Invocation_Signature_Of
13302 (Column => Nat (Get_Column_Number (Loc)),
13303 Line => Nat (Get_Logical_Line_Number (Loc)),
13304 Locations => Instantiation_Locations,
13305 Name => Chars (Id),
13306 Scope => Qualified_Scope);
13307 end Signature_Of;
13308
13309 ---------------
13310 -- Target_Of --
13311 ---------------
13312
13313 function Target_Of
13314 (Pos : Active_Scenario_Pos;
13315 In_State : Processing_In_State) return Entity_Id
13316 is
13317 package Scenarios renames Active_Scenario_Stack;
13318
13319 -- Ensure that the position is within the bounds of the active
13320 -- scenario stack.
13321
13322 pragma Assert (Scenarios.First <= Pos);
13323 pragma Assert (Pos <= Scenarios.Last);
13324
13325 Scen_Rep : constant Scenario_Rep_Id :=
13326 Scenario_Representation_Of
13327 (Scenarios.Table (Pos), In_State);
13328
13329 begin
13330 -- The true target of an activation call is the current task type
13331 -- rather than routine Activate_Tasks.
13332
13333 if Kind (Scen_Rep) = Task_Activation_Scenario then
13334 return Activated_Task_Type (Scen_Rep);
13335 else
13336 return Target (Scen_Rep);
13337 end if;
13338 end Target_Of;
13339
13340 ------------------------------
13341 -- Traverse_Invocation_Body --
13342 ------------------------------
13343
13344 procedure Traverse_Invocation_Body
13345 (N : Node_Id;
13346 In_State : Processing_In_State)
13347 is
13348 begin
13349 Traverse_Body
13350 (N => N,
13351 Requires_Processing => Is_Invocation_Scenario'Access,
13352 Processor => Process_Invocation_Scenario'Access,
13353 In_State => In_State);
13354 end Traverse_Invocation_Body;
13355
13356 ---------------------------
13357 -- Write_Invocation_Path --
13358 ---------------------------
13359
13360 procedure Write_Invocation_Path (In_State : Processing_In_State) is
13361 procedure Write_Target (Targ_Id : Entity_Id; Is_First : Boolean);
13362 pragma Inline (Write_Target);
13363 -- Write out invocation target Targ_Id to standard output. Flag
13364 -- Is_First should be set when the target is first in a path.
13365
13366 -------------
13367 -- Targ_Id --
13368 -------------
13369
13370 procedure Write_Target (Targ_Id : Entity_Id; Is_First : Boolean) is
13371 begin
13372 if not Is_First then
13373 Write_Str (" --> ");
13374 end if;
13375
13376 Write_Name (Get_Qualified_Name (Targ_Id));
13377 Write_Eol;
13378 end Write_Target;
13379
13380 -- Local variables
13381
13382 package Scenarios renames Active_Scenario_Stack;
13383
13384 First_Seen : Boolean := False;
13385
13386 -- Start of processing for Write_Invocation_Path
13387
13388 begin
13389 -- Nothing to do when flag -gnatd_T (output trace information on
13390 -- invocation path recording) is not in effect.
13391
13392 if not Debug_Flag_Underscore_TT then
13393 return;
13394 end if;
13395
13396 -- The path originates from the elaboration of the body. Write the
13397 -- elaboration body procedure.
13398
13399 if In_State.Processing = Invocation_Body_Processing then
13400 Write_Target (Elab_Body_Id, True);
13401 First_Seen := True;
13402
13403 -- The path originates from the elaboration of the spec. Write the
13404 -- elaboration spec procedure.
13405
13406 elsif In_State.Processing = Invocation_Spec_Processing then
13407 Write_Target (Elab_Spec_Id, True);
13408 First_Seen := True;
13409 end if;
13410
13411 -- Write each individual target invoked by its corresponding scenario
13412 -- on the active scenario stack.
13413
13414 for Index in Scenarios.First .. Scenarios.Last loop
13415 Write_Target
13416 (Targ_Id => Target_Of (Index, In_State),
13417 Is_First => Index = Scenarios.First and then not First_Seen);
13418 end loop;
13419
13420 Write_Eol;
13421 end Write_Invocation_Path;
13422 end Invocation_Graph;
13423
13424 ------------------------
13425 -- Is_Safe_Activation --
13426 ------------------------
13427
13428 function Is_Safe_Activation
13429 (Call : Node_Id;
13430 Task_Rep : Target_Rep_Id) return Boolean
13431 is
13432 begin
13433 -- The activation of a task coming from an external instance cannot
13434 -- cause an ABE because the generic was already instantiated. Note
13435 -- that the instantiation itself may lead to an ABE.
13436
13437 return
13438 In_External_Instance
13439 (N => Call,
13440 Target_Decl => Spec_Declaration (Task_Rep));
13441 end Is_Safe_Activation;
13442
13443 ------------------
13444 -- Is_Safe_Call --
13445 ------------------
13446
13447 function Is_Safe_Call
13448 (Call : Node_Id;
13449 Subp_Id : Entity_Id;
13450 Subp_Rep : Target_Rep_Id) return Boolean
13451 is
13452 Body_Decl : constant Node_Id := Body_Declaration (Subp_Rep);
13453 Spec_Decl : constant Node_Id := Spec_Declaration (Subp_Rep);
13454
13455 begin
13456 -- The target is either an abstract subprogram, formal subprogram, or
13457 -- imported, in which case it does not have a body at compile or bind
13458 -- time. Assume that the call is ABE-safe.
13459
13460 if Is_Bodiless_Subprogram (Subp_Id) then
13461 return True;
13462
13463 -- The target is an instantiation of a generic subprogram. The call
13464 -- cannot cause an ABE because the generic was already instantiated.
13465 -- Note that the instantiation itself may lead to an ABE.
13466
13467 elsif Is_Generic_Instance (Subp_Id) then
13468 return True;
13469
13470 -- The invocation of a target coming from an external instance cannot
13471 -- cause an ABE because the generic was already instantiated. Note that
13472 -- the instantiation itself may lead to an ABE.
13473
13474 elsif In_External_Instance
13475 (N => Call,
13476 Target_Decl => Spec_Decl)
13477 then
13478 return True;
13479
13480 -- The target is a subprogram body without a previous declaration. The
13481 -- call cannot cause an ABE because the body has already been seen.
13482
13483 elsif Nkind (Spec_Decl) = N_Subprogram_Body
13484 and then No (Corresponding_Spec (Spec_Decl))
13485 then
13486 return True;
13487
13488 -- The target is a subprogram body stub without a prior declaration.
13489 -- The call cannot cause an ABE because the proper body substitutes
13490 -- the stub.
13491
13492 elsif Nkind (Spec_Decl) = N_Subprogram_Body_Stub
13493 and then No (Corresponding_Spec_Of_Stub (Spec_Decl))
13494 then
13495 return True;
13496
13497 -- Subprogram bodies which wrap attribute references used as actuals
13498 -- in instantiations are always ABE-safe. These bodies are artifacts
13499 -- of expansion.
13500
13501 elsif Present (Body_Decl)
13502 and then Nkind (Body_Decl) = N_Subprogram_Body
13503 and then Was_Attribute_Reference (Body_Decl)
13504 then
13505 return True;
13506 end if;
13507
13508 return False;
13509 end Is_Safe_Call;
13510
13511 ---------------------------
13512 -- Is_Safe_Instantiation --
13513 ---------------------------
13514
13515 function Is_Safe_Instantiation
13516 (Inst : Node_Id;
13517 Gen_Id : Entity_Id;
13518 Gen_Rep : Target_Rep_Id) return Boolean
13519 is
13520 Spec_Decl : constant Node_Id := Spec_Declaration (Gen_Rep);
13521
13522 begin
13523 -- The generic is an intrinsic subprogram in which case it does not
13524 -- have a body at compile or bind time. Assume that the instantiation
13525 -- is ABE-safe.
13526
13527 if Is_Bodiless_Subprogram (Gen_Id) then
13528 return True;
13529
13530 -- The instantiation of an external nested generic cannot cause an ABE
13531 -- if the outer generic was already instantiated. Note that the instance
13532 -- of the outer generic may lead to an ABE.
13533
13534 elsif In_External_Instance
13535 (N => Inst,
13536 Target_Decl => Spec_Decl)
13537 then
13538 return True;
13539
13540 -- The generic is a package. The instantiation cannot cause an ABE when
13541 -- the package has no body.
13542
13543 elsif Ekind (Gen_Id) = E_Generic_Package
13544 and then not Has_Body (Spec_Decl)
13545 then
13546 return True;
13547 end if;
13548
13549 return False;
13550 end Is_Safe_Instantiation;
13551
13552 ------------------
13553 -- Is_Same_Unit --
13554 ------------------
13555
13556 function Is_Same_Unit
13557 (Unit_1 : Entity_Id;
13558 Unit_2 : Entity_Id) return Boolean
13559 is
13560 begin
13561 return Unit_Entity (Unit_1) = Unit_Entity (Unit_2);
13562 end Is_Same_Unit;
13563
13564 -------------------------------
13565 -- Kill_Elaboration_Scenario --
13566 -------------------------------
13567
13568 procedure Kill_Elaboration_Scenario (N : Node_Id) is
13569 begin
13570 -- Nothing to do when switch -gnatH (legacy elaboration checking mode
13571 -- enabled) is in effect because the legacy ABE lechanism does not need
13572 -- to carry out this action.
13573
13574 if Legacy_Elaboration_Checks then
13575 return;
13576
13577 -- Nothing to do when the elaboration phase of the compiler is not
13578 -- active.
13579
13580 elsif not Elaboration_Phase_Active then
13581 return;
13582 end if;
13583
13584 -- Eliminate a recorded scenario when it appears within dead code
13585 -- because it will not be executed at elaboration time.
13586
13587 if Is_Scenario (N) then
13588 Delete_Scenario (N);
13589 end if;
13590 end Kill_Elaboration_Scenario;
13591
13592 ----------------------
13593 -- Non_Private_View --
13594 ----------------------
13595
13596 function Non_Private_View (Typ : Entity_Id) return Entity_Id is
13597 begin
13598 if Is_Private_Type (Typ) and then Present (Full_View (Typ)) then
13599 return Full_View (Typ);
13600 else
13601 return Typ;
13602 end if;
13603 end Non_Private_View;
13604
13605 ---------------------------------
13606 -- Record_Elaboration_Scenario --
13607 ---------------------------------
13608
13609 procedure Record_Elaboration_Scenario (N : Node_Id) is
13610 procedure Check_Preelaborated_Call
13611 (Call : Node_Id;
13612 Call_Lvl : Enclosing_Level_Kind);
13613 pragma Inline (Check_Preelaborated_Call);
13614 -- Verify that entry, operator, or subprogram call Call with enclosing
13615 -- level Call_Lvl does not appear at the library level of preelaborated
13616 -- unit.
13617
13618 function Find_Code_Unit (Nod : Node_Or_Entity_Id) return Entity_Id;
13619 pragma Inline (Find_Code_Unit);
13620 -- Return the code unit which contains arbitrary node or entity Nod.
13621 -- This is the unit of the file which physically contains the related
13622 -- construct denoted by Nod except when Nod is within an instantiation.
13623 -- In that case the unit is that of the top-level instantiation.
13624
13625 function In_Preelaborated_Context (Nod : Node_Id) return Boolean;
13626 pragma Inline (In_Preelaborated_Context);
13627 -- Determine whether arbitrary node Nod appears within a preelaborated
13628 -- context.
13629
13630 procedure Record_Access_Taken
13631 (Attr : Node_Id;
13632 Attr_Lvl : Enclosing_Level_Kind);
13633 pragma Inline (Record_Access_Taken);
13634 -- Record 'Access scenario Attr with enclosing level Attr_Lvl
13635
13636 procedure Record_Call_Or_Task_Activation
13637 (Call : Node_Id;
13638 Call_Lvl : Enclosing_Level_Kind);
13639 pragma Inline (Record_Call_Or_Task_Activation);
13640 -- Record call scenario Call with enclosing level Call_Lvl
13641
13642 procedure Record_Instantiation
13643 (Inst : Node_Id;
13644 Inst_Lvl : Enclosing_Level_Kind);
13645 pragma Inline (Record_Instantiation);
13646 -- Record instantiation scenario Inst with enclosing level Inst_Lvl
13647
13648 procedure Record_Variable_Assignment
13649 (Asmt : Node_Id;
13650 Asmt_Lvl : Enclosing_Level_Kind);
13651 pragma Inline (Record_Variable_Assignment);
13652 -- Record variable assignment scenario Asmt with enclosing level
13653 -- Asmt_Lvl.
13654
13655 procedure Record_Variable_Reference
13656 (Ref : Node_Id;
13657 Ref_Lvl : Enclosing_Level_Kind);
13658 pragma Inline (Record_Variable_Reference);
13659 -- Record variable reference scenario Ref with enclosing level Ref_Lvl
13660
13661 ------------------------------
13662 -- Check_Preelaborated_Call --
13663 ------------------------------
13664
13665 procedure Check_Preelaborated_Call
13666 (Call : Node_Id;
13667 Call_Lvl : Enclosing_Level_Kind)
13668 is
13669 begin
13670 -- Nothing to do when the call is internally generated because it is
13671 -- assumed that it will never violate preelaboration.
13672
13673 if not Is_Source_Call (Call) then
13674 return;
13675
13676 -- Library-level calls are always considered because they are part of
13677 -- the associated unit's elaboration actions.
13678
13679 elsif Call_Lvl in Library_Level then
13680 null;
13681
13682 -- Calls at the library level of a generic package body have to be
13683 -- checked because they would render an instantiation illegal if the
13684 -- template is marked as preelaborated. Note that this does not apply
13685 -- to calls at the library level of a generic package spec.
13686
13687 elsif Call_Lvl = Generic_Body_Level then
13688 null;
13689
13690 -- Otherwise the call does not appear at the proper level and must
13691 -- not be considered for this check.
13692
13693 else
13694 return;
13695 end if;
13696
13697 -- The call appears within a preelaborated unit. Emit a warning only
13698 -- for internal uses, otherwise this is an error.
13699
13700 if In_Preelaborated_Context (Call) then
13701 Error_Msg_Warn := GNAT_Mode;
13702 Error_Msg_N
13703 ("<<non-static call not allowed in preelaborated unit", Call);
13704 end if;
13705 end Check_Preelaborated_Call;
13706
13707 --------------------
13708 -- Find_Code_Unit --
13709 --------------------
13710
13711 function Find_Code_Unit (Nod : Node_Or_Entity_Id) return Entity_Id is
13712 begin
13713 return Find_Unit_Entity (Unit (Cunit (Get_Code_Unit (Nod))));
13714 end Find_Code_Unit;
13715
13716 ------------------------------
13717 -- In_Preelaborated_Context --
13718 ------------------------------
13719
13720 function In_Preelaborated_Context (Nod : Node_Id) return Boolean is
13721 Body_Id : constant Entity_Id := Find_Code_Unit (Nod);
13722 Spec_Id : constant Entity_Id := Unique_Entity (Body_Id);
13723
13724 begin
13725 -- The node appears within a package body whose corresponding spec is
13726 -- subject to pragma Remote_Call_Interface or Remote_Types. This does
13727 -- not result in a preelaborated context because the package body may
13728 -- be on another machine.
13729
13730 if Ekind (Body_Id) = E_Package_Body
13731 and then Ekind_In (Spec_Id, E_Generic_Package, E_Package)
13732 and then (Is_Remote_Call_Interface (Spec_Id)
13733 or else Is_Remote_Types (Spec_Id))
13734 then
13735 return False;
13736
13737 -- Otherwise the node appears within a preelaborated context when the
13738 -- associated unit is preelaborated.
13739
13740 else
13741 return Is_Preelaborated_Unit (Spec_Id);
13742 end if;
13743 end In_Preelaborated_Context;
13744
13745 -------------------------
13746 -- Record_Access_Taken --
13747 -------------------------
13748
13749 procedure Record_Access_Taken
13750 (Attr : Node_Id;
13751 Attr_Lvl : Enclosing_Level_Kind)
13752 is
13753 begin
13754 -- Signal any enclosing local exception handlers that the 'Access may
13755 -- raise Program_Error due to a failed ABE check when switch -gnatd.o
13756 -- (conservative elaboration order for indirect calls) is in effect.
13757 -- Marking the exception handlers ensures proper expansion by both
13758 -- the front and back end restriction when No_Exception_Propagation
13759 -- is in effect.
13760
13761 if Debug_Flag_Dot_O then
13762 Possible_Local_Raise (Attr, Standard_Program_Error);
13763 end if;
13764
13765 -- Add 'Access to the appropriate set
13766
13767 if Attr_Lvl = Library_Body_Level then
13768 Add_Library_Body_Scenario (Attr);
13769
13770 elsif Attr_Lvl = Library_Spec_Level
13771 or else Attr_Lvl = Instantiation_Level
13772 then
13773 Add_Library_Spec_Scenario (Attr);
13774 end if;
13775
13776 -- 'Access requires a conditional ABE check when the dynamic model is
13777 -- in effect.
13778
13779 Add_Dynamic_ABE_Check_Scenario (Attr);
13780 end Record_Access_Taken;
13781
13782 ------------------------------------
13783 -- Record_Call_Or_Task_Activation --
13784 ------------------------------------
13785
13786 procedure Record_Call_Or_Task_Activation
13787 (Call : Node_Id;
13788 Call_Lvl : Enclosing_Level_Kind)
13789 is
13790 begin
13791 -- Signal any enclosing local exception handlers that the call may
13792 -- raise Program_Error due to failed ABE check. Marking the exception
13793 -- handlers ensures proper expansion by both the front and back end
13794 -- restriction when No_Exception_Propagation is in effect.
13795
13796 Possible_Local_Raise (Call, Standard_Program_Error);
13797
13798 -- Perform early detection of guaranteed ABEs in order to suppress
13799 -- the instantiation of generic bodies because gigi cannot handle
13800 -- certain types of premature instantiations.
13801
13802 Process_Guaranteed_ABE
13803 (N => Call,
13804 In_State => Guaranteed_ABE_State);
13805
13806 -- Add the call or task activation to the appropriate set
13807
13808 if Call_Lvl = Declaration_Level then
13809 Add_Declaration_Scenario (Call);
13810
13811 elsif Call_Lvl = Library_Body_Level then
13812 Add_Library_Body_Scenario (Call);
13813
13814 elsif Call_Lvl = Library_Spec_Level
13815 or else Call_Lvl = Instantiation_Level
13816 then
13817 Add_Library_Spec_Scenario (Call);
13818 end if;
13819
13820 -- A call or a task activation requires a conditional ABE check when
13821 -- the dynamic model is in effect.
13822
13823 Add_Dynamic_ABE_Check_Scenario (Call);
13824 end Record_Call_Or_Task_Activation;
13825
13826 --------------------------
13827 -- Record_Instantiation --
13828 --------------------------
13829
13830 procedure Record_Instantiation
13831 (Inst : Node_Id;
13832 Inst_Lvl : Enclosing_Level_Kind)
13833 is
13834 begin
13835 -- Signal enclosing local exception handlers that instantiation may
13836 -- raise Program_Error due to failed ABE check. Marking the exception
13837 -- handlers ensures proper expansion by both the front and back end
13838 -- restriction when No_Exception_Propagation is in effect.
13839
13840 Possible_Local_Raise (Inst, Standard_Program_Error);
13841
13842 -- Perform early detection of guaranteed ABEs in order to suppress
13843 -- the instantiation of generic bodies because gigi cannot handle
13844 -- certain types of premature instantiations.
13845
13846 Process_Guaranteed_ABE
13847 (N => Inst,
13848 In_State => Guaranteed_ABE_State);
13849
13850 -- Add the instantiation to the appropriate set
13851
13852 if Inst_Lvl = Declaration_Level then
13853 Add_Declaration_Scenario (Inst);
13854
13855 elsif Inst_Lvl = Library_Body_Level then
13856 Add_Library_Body_Scenario (Inst);
13857
13858 elsif Inst_Lvl = Library_Spec_Level
13859 or else Inst_Lvl = Instantiation_Level
13860 then
13861 Add_Library_Spec_Scenario (Inst);
13862 end if;
13863
13864 -- Instantiations of generics subject to SPARK_Mode On require
13865 -- elaboration-related checks even though the instantiations may
13866 -- not appear within elaboration code.
13867
13868 if Is_Suitable_SPARK_Instantiation (Inst) then
13869 Add_SPARK_Scenario (Inst);
13870 end if;
13871
13872 -- An instantiation requires a conditional ABE check when the dynamic
13873 -- model is in effect.
13874
13875 Add_Dynamic_ABE_Check_Scenario (Inst);
13876 end Record_Instantiation;
13877
13878 --------------------------------
13879 -- Record_Variable_Assignment --
13880 --------------------------------
13881
13882 procedure Record_Variable_Assignment
13883 (Asmt : Node_Id;
13884 Asmt_Lvl : Enclosing_Level_Kind)
13885 is
13886 begin
13887 -- Add the variable assignment to the appropriate set
13888
13889 if Asmt_Lvl = Library_Body_Level then
13890 Add_Library_Body_Scenario (Asmt);
13891
13892 elsif Asmt_Lvl = Library_Spec_Level
13893 or else Asmt_Lvl = Instantiation_Level
13894 then
13895 Add_Library_Spec_Scenario (Asmt);
13896 end if;
13897 end Record_Variable_Assignment;
13898
13899 -------------------------------
13900 -- Record_Variable_Reference --
13901 -------------------------------
13902
13903 procedure Record_Variable_Reference
13904 (Ref : Node_Id;
13905 Ref_Lvl : Enclosing_Level_Kind)
13906 is
13907 begin
13908 -- Add the variable reference to the appropriate set
13909
13910 if Ref_Lvl = Library_Body_Level then
13911 Add_Library_Body_Scenario (Ref);
13912
13913 elsif Ref_Lvl = Library_Spec_Level
13914 or else Ref_Lvl = Instantiation_Level
13915 then
13916 Add_Library_Spec_Scenario (Ref);
13917 end if;
13918 end Record_Variable_Reference;
13919
13920 -- Local variables
13921
13922 Scen : constant Node_Id := Scenario (N);
13923 Scen_Lvl : Enclosing_Level_Kind;
13924
13925 -- Start of processing for Record_Elaboration_Scenario
13926
13927 begin
13928 -- Nothing to do when switch -gnatH (legacy elaboration checking mode
13929 -- enabled) is in effect because the legacy ABE mechanism does not need
13930 -- to carry out this action.
13931
13932 if Legacy_Elaboration_Checks then
13933 return;
13934
13935 -- Nothing to do for ASIS because ABE checks and diagnostics are not
13936 -- performed in this mode.
13937
13938 elsif ASIS_Mode then
13939 return;
13940
13941 -- Nothing to do when the scenario is being preanalyzed
13942
13943 elsif Preanalysis_Active then
13944 return;
13945
13946 -- Nothing to do when the elaboration phase of the compiler is not
13947 -- active.
13948
13949 elsif not Elaboration_Phase_Active then
13950 return;
13951 end if;
13952
13953 Scen_Lvl := Find_Enclosing_Level (Scen);
13954
13955 -- Ensure that a library-level call does not appear in a preelaborated
13956 -- unit. The check must come before ignoring scenarios within external
13957 -- units or inside generics because calls in those context must also be
13958 -- verified.
13959
13960 if Is_Suitable_Call (Scen) then
13961 Check_Preelaborated_Call (Scen, Scen_Lvl);
13962 end if;
13963
13964 -- Nothing to do when the scenario does not appear within the main unit
13965
13966 if not In_Main_Context (Scen) then
13967 return;
13968
13969 -- Nothing to do when the scenario appears within a generic
13970
13971 elsif Inside_A_Generic then
13972 return;
13973
13974 -- 'Access
13975
13976 elsif Is_Suitable_Access_Taken (Scen) then
13977 Record_Access_Taken
13978 (Attr => Scen,
13979 Attr_Lvl => Scen_Lvl);
13980
13981 -- Call or task activation
13982
13983 elsif Is_Suitable_Call (Scen) then
13984 Record_Call_Or_Task_Activation
13985 (Call => Scen,
13986 Call_Lvl => Scen_Lvl);
13987
13988 -- Derived type declaration
13989
13990 elsif Is_Suitable_SPARK_Derived_Type (Scen) then
13991 Add_SPARK_Scenario (Scen);
13992
13993 -- Instantiation
13994
13995 elsif Is_Suitable_Instantiation (Scen) then
13996 Record_Instantiation
13997 (Inst => Scen,
13998 Inst_Lvl => Scen_Lvl);
13999
14000 -- Refined_State pragma
14001
14002 elsif Is_Suitable_SPARK_Refined_State_Pragma (Scen) then
14003 Add_SPARK_Scenario (Scen);
14004
14005 -- Variable assignment
14006
14007 elsif Is_Suitable_Variable_Assignment (Scen) then
14008 Record_Variable_Assignment
14009 (Asmt => Scen,
14010 Asmt_Lvl => Scen_Lvl);
14011
14012 -- Variable reference
14013
14014 elsif Is_Suitable_Variable_Reference (Scen) then
14015 Record_Variable_Reference
14016 (Ref => Scen,
14017 Ref_Lvl => Scen_Lvl);
14018 end if;
14019 end Record_Elaboration_Scenario;
14020
14021 --------------
14022 -- Scenario --
14023 --------------
14024
14025 function Scenario (N : Node_Id) return Node_Id is
14026 Orig_N : constant Node_Id := Original_Node (N);
14027
14028 begin
14029 -- An expanded instantiation is rewritten into a spec-body pair where
14030 -- N denotes the spec. In this case the original instantiation is the
14031 -- proper elaboration scenario.
14032
14033 if Nkind (Orig_N) in N_Generic_Instantiation then
14034 return Orig_N;
14035
14036 -- Otherwise the scenario is already in its proper form
14037
14038 else
14039 return N;
14040 end if;
14041 end Scenario;
14042
14043 ----------------------
14044 -- Scenario_Storage --
14045 ----------------------
14046
14047 package body Scenario_Storage is
14048
14049 ---------------------
14050 -- Data structures --
14051 ---------------------
14052
14053 -- The following sets store all scenarios
14054
14055 Declaration_Scenarios : NE_Set.Membership_Set := NE_Set.Nil;
14056 Dynamic_ABE_Check_Scenarios : NE_Set.Membership_Set := NE_Set.Nil;
14057 Library_Body_Scenarios : NE_Set.Membership_Set := NE_Set.Nil;
14058 Library_Spec_Scenarios : NE_Set.Membership_Set := NE_Set.Nil;
14059 SPARK_Scenarios : NE_Set.Membership_Set := NE_Set.Nil;
14060
14061 -------------------------------
14062 -- Finalize_Scenario_Storage --
14063 -------------------------------
14064
14065 procedure Finalize_Scenario_Storage is
14066 begin
14067 NE_Set.Destroy (Declaration_Scenarios);
14068 NE_Set.Destroy (Dynamic_ABE_Check_Scenarios);
14069 NE_Set.Destroy (Library_Body_Scenarios);
14070 NE_Set.Destroy (Library_Spec_Scenarios);
14071 NE_Set.Destroy (SPARK_Scenarios);
14072 end Finalize_Scenario_Storage;
14073
14074 ---------------------------------
14075 -- Initialize_Scenario_Storage --
14076 ---------------------------------
14077
14078 procedure Initialize_Scenario_Storage is
14079 begin
14080 Declaration_Scenarios := NE_Set.Create (1000);
14081 Dynamic_ABE_Check_Scenarios := NE_Set.Create (500);
14082 Library_Body_Scenarios := NE_Set.Create (1000);
14083 Library_Spec_Scenarios := NE_Set.Create (1000);
14084 SPARK_Scenarios := NE_Set.Create (100);
14085 end Initialize_Scenario_Storage;
14086
14087 ------------------------------
14088 -- Add_Declaration_Scenario --
14089 ------------------------------
14090
14091 procedure Add_Declaration_Scenario (N : Node_Id) is
14092 pragma Assert (Present (N));
14093 begin
14094 NE_Set.Insert (Declaration_Scenarios, N);
14095 end Add_Declaration_Scenario;
14096
14097 ------------------------------------
14098 -- Add_Dynamic_ABE_Check_Scenario --
14099 ------------------------------------
14100
14101 procedure Add_Dynamic_ABE_Check_Scenario (N : Node_Id) is
14102 pragma Assert (Present (N));
14103
14104 begin
14105 if not Check_Or_Failure_Generation_OK then
14106 return;
14107
14108 -- Nothing to do if the dynamic model is not in effect
14109
14110 elsif not Dynamic_Elaboration_Checks then
14111 return;
14112 end if;
14113
14114 NE_Set.Insert (Dynamic_ABE_Check_Scenarios, N);
14115 end Add_Dynamic_ABE_Check_Scenario;
14116
14117 -------------------------------
14118 -- Add_Library_Body_Scenario --
14119 -------------------------------
14120
14121 procedure Add_Library_Body_Scenario (N : Node_Id) is
14122 pragma Assert (Present (N));
14123 begin
14124 NE_Set.Insert (Library_Body_Scenarios, N);
14125 end Add_Library_Body_Scenario;
14126
14127 -------------------------------
14128 -- Add_Library_Spec_Scenario --
14129 -------------------------------
14130
14131 procedure Add_Library_Spec_Scenario (N : Node_Id) is
14132 pragma Assert (Present (N));
14133 begin
14134 NE_Set.Insert (Library_Spec_Scenarios, N);
14135 end Add_Library_Spec_Scenario;
14136
14137 ------------------------
14138 -- Add_SPARK_Scenario --
14139 ------------------------
14140
14141 procedure Add_SPARK_Scenario (N : Node_Id) is
14142 pragma Assert (Present (N));
14143 begin
14144 NE_Set.Insert (SPARK_Scenarios, N);
14145 end Add_SPARK_Scenario;
14146
14147 ---------------------
14148 -- Delete_Scenario --
14149 ---------------------
14150
14151 procedure Delete_Scenario (N : Node_Id) is
14152 pragma Assert (Present (N));
14153
14154 begin
14155 -- Delete the scenario from whichever set it belongs to
14156
14157 NE_Set.Delete (Declaration_Scenarios, N);
14158 NE_Set.Delete (Dynamic_ABE_Check_Scenarios, N);
14159 NE_Set.Delete (Library_Body_Scenarios, N);
14160 NE_Set.Delete (Library_Spec_Scenarios, N);
14161 NE_Set.Delete (SPARK_Scenarios, N);
14162 end Delete_Scenario;
14163
14164 -----------------------------------
14165 -- Iterate_Declaration_Scenarios --
14166 -----------------------------------
14167
14168 function Iterate_Declaration_Scenarios return NE_Set.Iterator is
14169 begin
14170 return NE_Set.Iterate (Declaration_Scenarios);
14171 end Iterate_Declaration_Scenarios;
14172
14173 -----------------------------------------
14174 -- Iterate_Dynamic_ABE_Check_Scenarios --
14175 -----------------------------------------
14176
14177 function Iterate_Dynamic_ABE_Check_Scenarios return NE_Set.Iterator is
14178 begin
14179 return NE_Set.Iterate (Dynamic_ABE_Check_Scenarios);
14180 end Iterate_Dynamic_ABE_Check_Scenarios;
14181
14182 ------------------------------------
14183 -- Iterate_Library_Body_Scenarios --
14184 ------------------------------------
14185
14186 function Iterate_Library_Body_Scenarios return NE_Set.Iterator is
14187 begin
14188 return NE_Set.Iterate (Library_Body_Scenarios);
14189 end Iterate_Library_Body_Scenarios;
14190
14191 ------------------------------------
14192 -- Iterate_Library_Spec_Scenarios --
14193 ------------------------------------
14194
14195 function Iterate_Library_Spec_Scenarios return NE_Set.Iterator is
14196 begin
14197 return NE_Set.Iterate (Library_Spec_Scenarios);
14198 end Iterate_Library_Spec_Scenarios;
14199
14200 -----------------------------
14201 -- Iterate_SPARK_Scenarios --
14202 -----------------------------
14203
14204 function Iterate_SPARK_Scenarios return NE_Set.Iterator is
14205 begin
14206 return NE_Set.Iterate (SPARK_Scenarios);
14207 end Iterate_SPARK_Scenarios;
14208
14209 ----------------------
14210 -- Replace_Scenario --
14211 ----------------------
14212
14213 procedure Replace_Scenario (Old_N : Node_Id; New_N : Node_Id) is
14214 procedure Replace_Scenario_In (Scenarios : NE_Set.Membership_Set);
14215 -- Determine whether scenario Old_N is present in set Scenarios, and
14216 -- if this is the case it, replace it with New_N.
14217
14218 -------------------------
14219 -- Replace_Scenario_In --
14220 -------------------------
14221
14222 procedure Replace_Scenario_In (Scenarios : NE_Set.Membership_Set) is
14223 begin
14224 -- The set is intentionally checked for existance because node
14225 -- rewriting may occur after Sem_Elab has verified all scenarios
14226 -- and data structures have been destroyed.
14227
14228 if NE_Set.Present (Scenarios)
14229 and then NE_Set.Contains (Scenarios, Old_N)
14230 then
14231 NE_Set.Delete (Scenarios, Old_N);
14232 NE_Set.Insert (Scenarios, New_N);
14233 end if;
14234 end Replace_Scenario_In;
14235
14236 -- Start of processing for Replace_Scenario
14237
14238 begin
14239 Replace_Scenario_In (Declaration_Scenarios);
14240 Replace_Scenario_In (Dynamic_ABE_Check_Scenarios);
14241 Replace_Scenario_In (Library_Body_Scenarios);
14242 Replace_Scenario_In (Library_Spec_Scenarios);
14243 Replace_Scenario_In (SPARK_Scenarios);
14244 end Replace_Scenario;
14245 end Scenario_Storage;
14246
14247 ---------------
14248 -- Semantics --
14249 ---------------
14250
14251 package body Semantics is
14252
14253 --------------------------------
14254 -- Is_Accept_Alternative_Proc --
14255 --------------------------------
14256
14257 function Is_Accept_Alternative_Proc (Id : Entity_Id) return Boolean is
14258 begin
14259 -- To qualify, the entity must denote a procedure with a receiving
14260 -- entry.
14261
14262 return
14263 Ekind (Id) = E_Procedure and then Present (Receiving_Entry (Id));
14264 end Is_Accept_Alternative_Proc;
14265
14266 ------------------------
14267 -- Is_Activation_Proc --
14268 ------------------------
14269
14270 function Is_Activation_Proc (Id : Entity_Id) return Boolean is
14271 begin
14272 -- To qualify, the entity must denote one of the runtime procedures
14273 -- in charge of task activation.
14274
14275 if Ekind (Id) = E_Procedure then
14276 if Restricted_Profile then
14277 return Is_RTE (Id, RE_Activate_Restricted_Tasks);
14278 else
14279 return Is_RTE (Id, RE_Activate_Tasks);
14280 end if;
14281 end if;
14282
14283 return False;
14284 end Is_Activation_Proc;
14285
14286 ----------------------------
14287 -- Is_Ada_Semantic_Target --
14288 ----------------------------
14289
14290 function Is_Ada_Semantic_Target (Id : Entity_Id) return Boolean is
14291 begin
14292 return
14293 Is_Activation_Proc (Id)
14294 or else Is_Controlled_Proc (Id, Name_Adjust)
14295 or else Is_Controlled_Proc (Id, Name_Finalize)
14296 or else Is_Controlled_Proc (Id, Name_Initialize)
14297 or else Is_Init_Proc (Id)
14298 or else Is_Invariant_Proc (Id)
14299 or else Is_Protected_Entry (Id)
14300 or else Is_Protected_Subp (Id)
14301 or else Is_Protected_Body_Subp (Id)
14302 or else Is_Subprogram_Inst (Id)
14303 or else Is_Task_Entry (Id);
14304 end Is_Ada_Semantic_Target;
14305
14306 --------------------------------
14307 -- Is_Assertion_Pragma_Target --
14308 --------------------------------
14309
14310 function Is_Assertion_Pragma_Target (Id : Entity_Id) return Boolean is
14311 begin
14312 return
14313 Is_Default_Initial_Condition_Proc (Id)
14314 or else Is_Initial_Condition_Proc (Id)
14315 or else Is_Invariant_Proc (Id)
14316 or else Is_Partial_Invariant_Proc (Id)
14317 or else Is_Postconditions_Proc (Id);
14318 end Is_Assertion_Pragma_Target;
14319
14320 ----------------------------
14321 -- Is_Bodiless_Subprogram --
14322 ----------------------------
14323
14324 function Is_Bodiless_Subprogram (Subp_Id : Entity_Id) return Boolean is
14325 begin
14326 -- An abstract subprogram does not have a body
14327
14328 if Ekind_In (Subp_Id, E_Function,
14329 E_Operator,
14330 E_Procedure)
14331 and then Is_Abstract_Subprogram (Subp_Id)
14332 then
14333 return True;
14334
14335 -- A formal subprogram does not have a body
14336
14337 elsif Is_Formal_Subprogram (Subp_Id) then
14338 return True;
14339
14340 -- An imported subprogram may have a body, however it is not known at
14341 -- compile or bind time where the body resides and whether it will be
14342 -- elaborated on time.
14343
14344 elsif Is_Imported (Subp_Id) then
14345 return True;
14346 end if;
14347
14348 return False;
14349 end Is_Bodiless_Subprogram;
14350
14351 ----------------------
14352 -- Is_Bridge_Target --
14353 ----------------------
14354
14355 function Is_Bridge_Target (Id : Entity_Id) return Boolean is
14356 begin
14357 return
14358 Is_Accept_Alternative_Proc (Id)
14359 or else Is_Finalizer_Proc (Id)
14360 or else Is_Partial_Invariant_Proc (Id)
14361 or else Is_Postconditions_Proc (Id)
14362 or else Is_TSS (Id, TSS_Deep_Adjust)
14363 or else Is_TSS (Id, TSS_Deep_Finalize)
14364 or else Is_TSS (Id, TSS_Deep_Initialize);
14365 end Is_Bridge_Target;
14366
14367 ------------------------
14368 -- Is_Controlled_Proc --
14369 ------------------------
14370
14371 function Is_Controlled_Proc
14372 (Subp_Id : Entity_Id;
14373 Subp_Nam : Name_Id) return Boolean
14374 is
14375 Formal_Id : Entity_Id;
14376
14377 begin
14378 pragma Assert (Nam_In (Subp_Nam, Name_Adjust,
14379 Name_Finalize,
14380 Name_Initialize));
14381
14382 -- To qualify, the subprogram must denote a source procedure with
14383 -- name Adjust, Finalize, or Initialize where the sole formal is
14384 -- controlled.
14385
14386 if Comes_From_Source (Subp_Id)
14387 and then Ekind (Subp_Id) = E_Procedure
14388 and then Chars (Subp_Id) = Subp_Nam
14389 then
14390 Formal_Id := First_Formal (Subp_Id);
14391
14392 return
14393 Present (Formal_Id)
14394 and then Is_Controlled (Etype (Formal_Id))
14395 and then No (Next_Formal (Formal_Id));
14396 end if;
14397
14398 return False;
14399 end Is_Controlled_Proc;
14400
14401 ---------------------------------------
14402 -- Is_Default_Initial_Condition_Proc --
14403 ---------------------------------------
14404
14405 function Is_Default_Initial_Condition_Proc
14406 (Id : Entity_Id) return Boolean
14407 is
14408 begin
14409 -- To qualify, the entity must denote a Default_Initial_Condition
14410 -- procedure.
14411
14412 return Ekind (Id) = E_Procedure and then Is_DIC_Procedure (Id);
14413 end Is_Default_Initial_Condition_Proc;
14414
14415 -----------------------
14416 -- Is_Finalizer_Proc --
14417 -----------------------
14418
14419 function Is_Finalizer_Proc (Id : Entity_Id) return Boolean is
14420 begin
14421 -- To qualify, the entity must denote a _Finalizer procedure
14422
14423 return Ekind (Id) = E_Procedure and then Chars (Id) = Name_uFinalizer;
14424 end Is_Finalizer_Proc;
14425
14426 -------------------------------
14427 -- Is_Initial_Condition_Proc --
14428 -------------------------------
14429
14430 function Is_Initial_Condition_Proc (Id : Entity_Id) return Boolean is
14431 begin
14432 -- To qualify, the entity must denote an Initial_Condition procedure
14433
14434 return
14435 Ekind (Id) = E_Procedure
14436 and then Is_Initial_Condition_Procedure (Id);
14437 end Is_Initial_Condition_Proc;
14438
14439 --------------------
14440 -- Is_Initialized --
14441 --------------------
14442
14443 function Is_Initialized (Obj_Decl : Node_Id) return Boolean is
14444 begin
14445 -- To qualify, the object declaration must have an expression
14446
14447 return
14448 Present (Expression (Obj_Decl))
14449 or else Has_Init_Expression (Obj_Decl);
14450 end Is_Initialized;
14451
14452 -----------------------
14453 -- Is_Invariant_Proc --
14454 -----------------------
14455
14456 function Is_Invariant_Proc (Id : Entity_Id) return Boolean is
14457 begin
14458 -- To qualify, the entity must denote the "full" invariant procedure
14459
14460 return Ekind (Id) = E_Procedure and then Is_Invariant_Procedure (Id);
14461 end Is_Invariant_Proc;
14462
14463 ---------------------------------------
14464 -- Is_Non_Library_Level_Encapsulator --
14465 ---------------------------------------
14466
14467 function Is_Non_Library_Level_Encapsulator
14468 (N : Node_Id) return Boolean
14469 is
14470 begin
14471 case Nkind (N) is
14472 when N_Abstract_Subprogram_Declaration
14473 | N_Aspect_Specification
14474 | N_Component_Declaration
14475 | N_Entry_Body
14476 | N_Entry_Declaration
14477 | N_Expression_Function
14478 | N_Formal_Abstract_Subprogram_Declaration
14479 | N_Formal_Concrete_Subprogram_Declaration
14480 | N_Formal_Object_Declaration
14481 | N_Formal_Package_Declaration
14482 | N_Formal_Type_Declaration
14483 | N_Generic_Association
14484 | N_Implicit_Label_Declaration
14485 | N_Incomplete_Type_Declaration
14486 | N_Private_Extension_Declaration
14487 | N_Private_Type_Declaration
14488 | N_Protected_Body
14489 | N_Protected_Type_Declaration
14490 | N_Single_Protected_Declaration
14491 | N_Single_Task_Declaration
14492 | N_Subprogram_Body
14493 | N_Subprogram_Declaration
14494 | N_Task_Body
14495 | N_Task_Type_Declaration
14496 =>
14497 return True;
14498
14499 when others =>
14500 return Is_Generic_Declaration_Or_Body (N);
14501 end case;
14502 end Is_Non_Library_Level_Encapsulator;
14503
14504 -------------------------------
14505 -- Is_Partial_Invariant_Proc --
14506 -------------------------------
14507
14508 function Is_Partial_Invariant_Proc (Id : Entity_Id) return Boolean is
14509 begin
14510 -- To qualify, the entity must denote the "partial" invariant
14511 -- procedure.
14512
14513 return
14514 Ekind (Id) = E_Procedure
14515 and then Is_Partial_Invariant_Procedure (Id);
14516 end Is_Partial_Invariant_Proc;
14517
14518 ----------------------------
14519 -- Is_Postconditions_Proc --
14520 ----------------------------
14521
14522 function Is_Postconditions_Proc (Id : Entity_Id) return Boolean is
14523 begin
14524 -- To qualify, the entity must denote a _Postconditions procedure
14525
14526 return
14527 Ekind (Id) = E_Procedure and then Chars (Id) = Name_uPostconditions;
14528 end Is_Postconditions_Proc;
14529
14530 ---------------------------
14531 -- Is_Preelaborated_Unit --
14532 ---------------------------
14533
14534 function Is_Preelaborated_Unit (Id : Entity_Id) return Boolean is
14535 begin
14536 return
14537 Is_Preelaborated (Id)
14538 or else Is_Pure (Id)
14539 or else Is_Remote_Call_Interface (Id)
14540 or else Is_Remote_Types (Id)
14541 or else Is_Shared_Passive (Id);
14542 end Is_Preelaborated_Unit;
14543
14544 ------------------------
14545 -- Is_Protected_Entry --
14546 ------------------------
14547
14548 function Is_Protected_Entry (Id : Entity_Id) return Boolean is
14549 begin
14550 -- To qualify, the entity must denote an entry defined in a protected
14551 -- type.
14552
14553 return
14554 Is_Entry (Id)
14555 and then Is_Protected_Type (Non_Private_View (Scope (Id)));
14556 end Is_Protected_Entry;
14557
14558 -----------------------
14559 -- Is_Protected_Subp --
14560 -----------------------
14561
14562 function Is_Protected_Subp (Id : Entity_Id) return Boolean is
14563 begin
14564 -- To qualify, the entity must denote a subprogram defined within a
14565 -- protected type.
14566
14567 return
14568 Ekind_In (Id, E_Function, E_Procedure)
14569 and then Is_Protected_Type (Non_Private_View (Scope (Id)));
14570 end Is_Protected_Subp;
14571
14572 ----------------------------
14573 -- Is_Protected_Body_Subp --
14574 ----------------------------
14575
14576 function Is_Protected_Body_Subp (Id : Entity_Id) return Boolean is
14577 begin
14578 -- To qualify, the entity must denote a subprogram with attribute
14579 -- Protected_Subprogram set.
14580
14581 return
14582 Ekind_In (Id, E_Function, E_Procedure)
14583 and then Present (Protected_Subprogram (Id));
14584 end Is_Protected_Body_Subp;
14585
14586 -----------------
14587 -- Is_Scenario --
14588 -----------------
14589
14590 function Is_Scenario (N : Node_Id) return Boolean is
14591 begin
14592 case Nkind (N) is
14593 when N_Assignment_Statement
14594 | N_Attribute_Reference
14595 | N_Call_Marker
14596 | N_Entry_Call_Statement
14597 | N_Expanded_Name
14598 | N_Function_Call
14599 | N_Function_Instantiation
14600 | N_Identifier
14601 | N_Package_Instantiation
14602 | N_Procedure_Call_Statement
14603 | N_Procedure_Instantiation
14604 | N_Requeue_Statement
14605 =>
14606 return True;
14607
14608 when others =>
14609 return False;
14610 end case;
14611 end Is_Scenario;
14612
14613 ------------------------------
14614 -- Is_SPARK_Semantic_Target --
14615 ------------------------------
14616
14617 function Is_SPARK_Semantic_Target (Id : Entity_Id) return Boolean is
14618 begin
14619 return
14620 Is_Default_Initial_Condition_Proc (Id)
14621 or else Is_Initial_Condition_Proc (Id);
14622 end Is_SPARK_Semantic_Target;
14623
14624 ------------------------
14625 -- Is_Subprogram_Inst --
14626 ------------------------
14627
14628 function Is_Subprogram_Inst (Id : Entity_Id) return Boolean is
14629 begin
14630 -- To qualify, the entity must denote a function or a procedure which
14631 -- is hidden within an anonymous package, and is a generic instance.
14632
14633 return
14634 Ekind_In (Id, E_Function, E_Procedure)
14635 and then Is_Hidden (Id)
14636 and then Is_Generic_Instance (Id);
14637 end Is_Subprogram_Inst;
14638
14639 ------------------------------
14640 -- Is_Suitable_Access_Taken --
14641 ------------------------------
14642
14643 function Is_Suitable_Access_Taken (N : Node_Id) return Boolean is
14644 Nam : Name_Id;
14645 Pref : Node_Id;
14646 Subp_Id : Entity_Id;
14647
14648 begin
14649 -- Nothing to do when switch -gnatd.U (ignore 'Access) is in effect
14650
14651 if Debug_Flag_Dot_UU then
14652 return False;
14653
14654 -- Nothing to do when the scenario is not an attribute reference
14655
14656 elsif Nkind (N) /= N_Attribute_Reference then
14657 return False;
14658
14659 -- Nothing to do for internally-generated attributes because they are
14660 -- assumed to be ABE safe.
14661
14662 elsif not Comes_From_Source (N) then
14663 return False;
14664 end if;
14665
14666 Nam := Attribute_Name (N);
14667 Pref := Prefix (N);
14668
14669 -- Sanitize the prefix of the attribute
14670
14671 if not Is_Entity_Name (Pref) then
14672 return False;
14673
14674 elsif No (Entity (Pref)) then
14675 return False;
14676 end if;
14677
14678 Subp_Id := Entity (Pref);
14679
14680 if not Is_Subprogram_Or_Entry (Subp_Id) then
14681 return False;
14682 end if;
14683
14684 -- Traverse a possible chain of renamings to obtain the original
14685 -- entry or subprogram which the prefix may rename.
14686
14687 Subp_Id := Get_Renamed_Entity (Subp_Id);
14688
14689 -- To qualify, the attribute must meet the following prerequisites:
14690
14691 return
14692
14693 -- The prefix must denote a source entry, operator, or subprogram
14694 -- which is not imported.
14695
14696 Comes_From_Source (Subp_Id)
14697 and then Is_Subprogram_Or_Entry (Subp_Id)
14698 and then not Is_Bodiless_Subprogram (Subp_Id)
14699
14700 -- The attribute name must be one of the 'Access forms. Note that
14701 -- 'Unchecked_Access cannot apply to a subprogram.
14702
14703 and then Nam_In (Nam, Name_Access, Name_Unrestricted_Access);
14704 end Is_Suitable_Access_Taken;
14705
14706 ----------------------
14707 -- Is_Suitable_Call --
14708 ----------------------
14709
14710 function Is_Suitable_Call (N : Node_Id) return Boolean is
14711 begin
14712 -- Entry and subprogram calls are intentionally ignored because they
14713 -- may undergo expansion depending on the compilation mode, previous
14714 -- errors, generic context, etc. Call markers play the role of calls
14715 -- and provide a uniform foundation for ABE processing.
14716
14717 return Nkind (N) = N_Call_Marker;
14718 end Is_Suitable_Call;
14719
14720 -------------------------------
14721 -- Is_Suitable_Instantiation --
14722 -------------------------------
14723
14724 function Is_Suitable_Instantiation (N : Node_Id) return Boolean is
14725 Inst : constant Node_Id := Scenario (N);
14726
14727 begin
14728 -- To qualify, the instantiation must come from source
14729
14730 return
14731 Comes_From_Source (Inst)
14732 and then Nkind (Inst) in N_Generic_Instantiation;
14733 end Is_Suitable_Instantiation;
14734
14735 ------------------------------------
14736 -- Is_Suitable_SPARK_Derived_Type --
14737 ------------------------------------
14738
14739 function Is_Suitable_SPARK_Derived_Type (N : Node_Id) return Boolean is
14740 Prag : Node_Id;
14741 Typ : Entity_Id;
14742
14743 begin
14744 -- To qualify, the type declaration must denote a derived tagged type
14745 -- with primitive operations, subject to pragma SPARK_Mode On.
14746
14747 if Nkind (N) = N_Full_Type_Declaration
14748 and then Nkind (Type_Definition (N)) = N_Derived_Type_Definition
14749 then
14750 Typ := Defining_Entity (N);
14751 Prag := SPARK_Pragma (Typ);
14752
14753 return
14754 Is_Tagged_Type (Typ)
14755 and then Has_Primitive_Operations (Typ)
14756 and then Present (Prag)
14757 and then Get_SPARK_Mode_From_Annotation (Prag) = On;
14758 end if;
14759
14760 return False;
14761 end Is_Suitable_SPARK_Derived_Type;
14762
14763 -------------------------------------
14764 -- Is_Suitable_SPARK_Instantiation --
14765 -------------------------------------
14766
14767 function Is_Suitable_SPARK_Instantiation (N : Node_Id) return Boolean is
14768 Inst : constant Node_Id := Scenario (N);
14769
14770 Gen_Id : Entity_Id;
14771 Prag : Node_Id;
14772
14773 begin
14774 -- To qualify, both the instantiation and the generic must be subject
14775 -- to SPARK_Mode On.
14776
14777 if Is_Suitable_Instantiation (N) then
14778 Gen_Id := Instantiated_Generic (Inst);
14779 Prag := SPARK_Pragma (Gen_Id);
14780
14781 return
14782 Is_SPARK_Mode_On_Node (Inst)
14783 and then Present (Prag)
14784 and then Get_SPARK_Mode_From_Annotation (Prag) = On;
14785 end if;
14786
14787 return False;
14788 end Is_Suitable_SPARK_Instantiation;
14789
14790 --------------------------------------------
14791 -- Is_Suitable_SPARK_Refined_State_Pragma --
14792 --------------------------------------------
14793
14794 function Is_Suitable_SPARK_Refined_State_Pragma
14795 (N : Node_Id) return Boolean
14796 is
14797 begin
14798 -- To qualfy, the pragma must denote Refined_State
14799
14800 return
14801 Nkind (N) = N_Pragma
14802 and then Pragma_Name (N) = Name_Refined_State;
14803 end Is_Suitable_SPARK_Refined_State_Pragma;
14804
14805 -------------------------------------
14806 -- Is_Suitable_Variable_Assignment --
14807 -------------------------------------
14808
14809 function Is_Suitable_Variable_Assignment (N : Node_Id) return Boolean is
14810 N_Unit : Node_Id;
14811 N_Unit_Id : Entity_Id;
14812 Nam : Node_Id;
14813 Var_Decl : Node_Id;
14814 Var_Id : Entity_Id;
14815 Var_Unit : Node_Id;
14816 Var_Unit_Id : Entity_Id;
14817
14818 begin
14819 -- Nothing to do when the scenario is not an assignment
14820
14821 if Nkind (N) /= N_Assignment_Statement then
14822 return False;
14823
14824 -- Nothing to do for internally-generated assignments because they
14825 -- are assumed to be ABE safe.
14826
14827 elsif not Comes_From_Source (N) then
14828 return False;
14829
14830 -- Assignments are ignored in GNAT mode on the assumption that
14831 -- they are ABE-safe. This behaviour parallels that of the old
14832 -- ABE mechanism.
14833
14834 elsif GNAT_Mode then
14835 return False;
14836 end if;
14837
14838 Nam := Assignment_Target (N);
14839
14840 -- Sanitize the left hand side of the assignment
14841
14842 if not Is_Entity_Name (Nam) then
14843 return False;
14844
14845 elsif No (Entity (Nam)) then
14846 return False;
14847 end if;
14848
14849 Var_Id := Entity (Nam);
14850
14851 -- Sanitize the variable
14852
14853 if Var_Id = Any_Id then
14854 return False;
14855
14856 elsif Ekind (Var_Id) /= E_Variable then
14857 return False;
14858 end if;
14859
14860 Var_Decl := Declaration_Node (Var_Id);
14861
14862 if Nkind (Var_Decl) /= N_Object_Declaration then
14863 return False;
14864 end if;
14865
14866 N_Unit_Id := Find_Top_Unit (N);
14867 N_Unit := Unit_Declaration_Node (N_Unit_Id);
14868
14869 Var_Unit_Id := Find_Top_Unit (Var_Decl);
14870 Var_Unit := Unit_Declaration_Node (Var_Unit_Id);
14871
14872 -- To qualify, the assignment must meet the following prerequisites:
14873
14874 return
14875 Comes_From_Source (Var_Id)
14876
14877 -- The variable must be declared in the spec of compilation unit
14878 -- U.
14879
14880 and then Nkind (Var_Unit) = N_Package_Declaration
14881 and then Find_Enclosing_Level (Var_Decl) = Library_Spec_Level
14882
14883 -- The assignment must occur in the body of compilation unit U
14884
14885 and then Nkind (N_Unit) = N_Package_Body
14886 and then Present (Corresponding_Body (Var_Unit))
14887 and then Corresponding_Body (Var_Unit) = N_Unit_Id;
14888 end Is_Suitable_Variable_Assignment;
14889
14890 ------------------------------------
14891 -- Is_Suitable_Variable_Reference --
14892 ------------------------------------
14893
14894 function Is_Suitable_Variable_Reference (N : Node_Id) return Boolean is
14895 begin
14896 -- Expanded names and identifiers are intentionally ignored because
14897 -- they be folded, optimized away, etc. Variable references markers
14898 -- play the role of variable references and provide a uniform
14899 -- foundation for ABE processing.
14900
14901 return Nkind (N) = N_Variable_Reference_Marker;
14902 end Is_Suitable_Variable_Reference;
14903
14904 -------------------
14905 -- Is_Task_Entry --
14906 -------------------
14907
14908 function Is_Task_Entry (Id : Entity_Id) return Boolean is
14909 begin
14910 -- To qualify, the entity must denote an entry defined in a task type
14911
14912 return
14913 Is_Entry (Id) and then Is_Task_Type (Non_Private_View (Scope (Id)));
14914 end Is_Task_Entry;
14915
14916 ------------------------
14917 -- Is_Up_Level_Target --
14918 ------------------------
14919
14920 function Is_Up_Level_Target
14921 (Targ_Decl : Node_Id;
14922 In_State : Processing_In_State) return Boolean
14923 is
14924 Root : constant Node_Id := Root_Scenario;
14925 Root_Rep : constant Scenario_Rep_Id :=
14926 Scenario_Representation_Of (Root, In_State);
14927
14928 begin
14929 -- The root appears within the declaratons of a block statement,
14930 -- entry body, subprogram body, or task body ignoring enclosing
14931 -- packages. The root is always within the main unit.
14932
14933 if not In_State.Suppress_Up_Level_Targets
14934 and then Level (Root_Rep) = Declaration_Level
14935 then
14936 -- The target is within the main unit. It acts as an up-level
14937 -- target when it appears within a context which encloses the
14938 -- root.
14939 --
14940 -- package body Main_Unit is
14941 -- function Func ...; -- target
14942 --
14943 -- procedure Proc is
14944 -- X : ... := Func; -- root scenario
14945
14946 if In_Extended_Main_Code_Unit (Targ_Decl) then
14947 return not In_Same_Context (Root, Targ_Decl, Nested_OK => True);
14948
14949 -- Otherwise the target is external to the main unit which makes
14950 -- it an up-level target.
14951
14952 else
14953 return True;
14954 end if;
14955 end if;
14956
14957 return False;
14958 end Is_Up_Level_Target;
14959 end Semantics;
14960
14961 ---------------------------
14962 -- Set_Elaboration_Phase --
14963 ---------------------------
14964
14965 procedure Set_Elaboration_Phase (Status : Elaboration_Phase_Status) is
14966 begin
14967 Elaboration_Phase := Status;
14968 end Set_Elaboration_Phase;
14969
14970 ---------------------
14971 -- SPARK_Processor --
14972 ---------------------
14973
14974 package body SPARK_Processor is
14975
14976 -----------------------
14977 -- Local subprograms --
14978 -----------------------
14979
14980 procedure Process_SPARK_Derived_Type
14981 (Typ_Decl : Node_Id;
14982 Typ_Rep : Scenario_Rep_Id;
14983 In_State : Processing_In_State);
14984 pragma Inline (Process_SPARK_Derived_Type);
14985 -- Verify that the freeze node of a derived type denoted by declaration
14986 -- Typ_Decl is within the early call region of each overriding primitive
14987 -- body that belongs to the derived type (SPARK RM 7.7(8)). Typ_Rep is
14988 -- the representation of the type. In_State denotes the current state of
14989 -- the Processing phase.
14990
14991 procedure Process_SPARK_Instantiation
14992 (Inst : Node_Id;
14993 Inst_Rep : Scenario_Rep_Id;
14994 In_State : Processing_In_State);
14995 pragma Inline (Process_SPARK_Instantiation);
14996 -- Verify that instanciation Inst does not precede the generic body it
14997 -- instantiates (SPARK RM 7.7(6)). Inst_Rep is the representation of the
14998 -- instantiation. In_State is the current state of the Processing phase.
14999
15000 procedure Process_SPARK_Refined_State_Pragma
15001 (Prag : Node_Id;
15002 Prag_Rep : Scenario_Rep_Id;
15003 In_State : Processing_In_State);
15004 pragma Inline (Process_SPARK_Refined_State_Pragma);
15005 -- Verify that each constituent of Refined_State pragma Prag which
15006 -- belongs to abstract state mentioned in pragma Initializes has prior
15007 -- elaboration with respect to the main unit (SPARK RM 7.7.1(7)).
15008 -- Prag_Rep is the representation of the pragma. In_State denotes the
15009 -- current state of the Processing phase.
15010
15011 procedure Process_SPARK_Scenario
15012 (N : Node_Id;
15013 In_State : Processing_In_State);
15014 pragma Inline (Process_SPARK_Scenario);
15015 -- Top-level dispatcher for verifying SPARK scenarios which are not
15016 -- always executable during elaboration but still need elaboration-
15017 -- related checks. In_State is the current state of the Processing
15018 -- phase.
15019
15020 ---------------------------------
15021 -- Check_SPARK_Model_In_Effect --
15022 ---------------------------------
15023
15024 SPARK_Model_Warning_Posted : Boolean := False;
15025 -- This flag prevents the same SPARK model-related warning from being
15026 -- emitted multiple times.
15027
15028 procedure Check_SPARK_Model_In_Effect is
15029 Spec_Id : constant Entity_Id :=
15030 Unique_Entity (Cunit_Entity (Main_Unit));
15031
15032 begin
15033 -- Do not emit the warning multiple times as this creates useless
15034 -- noise.
15035
15036 if SPARK_Model_Warning_Posted then
15037 null;
15038
15039 -- SPARK rule verification requires the "strict" static model
15040
15041 elsif Static_Elaboration_Checks
15042 and not Relaxed_Elaboration_Checks
15043 then
15044 null;
15045
15046 -- Any other combination of models does not guarantee the absence of
15047 -- ABE problems for SPARK rule verification purposes. Note that there
15048 -- is no need to check for the presence of the legacy ABE mechanism
15049 -- because the legacy code has its own dedicated processing for SPARK
15050 -- rules.
15051
15052 else
15053 SPARK_Model_Warning_Posted := True;
15054
15055 Error_Msg_N
15056 ("??SPARK elaboration checks require static elaboration model",
15057 Spec_Id);
15058
15059 if Dynamic_Elaboration_Checks then
15060 Error_Msg_N
15061 ("\dynamic elaboration model is in effect", Spec_Id);
15062
15063 else
15064 pragma Assert (Relaxed_Elaboration_Checks);
15065 Error_Msg_N
15066 ("\relaxed elaboration model is in effect", Spec_Id);
15067 end if;
15068 end if;
15069 end Check_SPARK_Model_In_Effect;
15070
15071 ---------------------------
15072 -- Check_SPARK_Scenarios --
15073 ---------------------------
15074
15075 procedure Check_SPARK_Scenarios is
15076 Iter : NE_Set.Iterator;
15077 N : Node_Id;
15078
15079 begin
15080 Iter := Iterate_SPARK_Scenarios;
15081 while NE_Set.Has_Next (Iter) loop
15082 NE_Set.Next (Iter, N);
15083
15084 Process_SPARK_Scenario
15085 (N => N,
15086 In_State => SPARK_State);
15087 end loop;
15088 end Check_SPARK_Scenarios;
15089
15090 --------------------------------
15091 -- Process_SPARK_Derived_Type --
15092 --------------------------------
15093
15094 procedure Process_SPARK_Derived_Type
15095 (Typ_Decl : Node_Id;
15096 Typ_Rep : Scenario_Rep_Id;
15097 In_State : Processing_In_State)
15098 is
15099 pragma Unreferenced (In_State);
15100
15101 Typ : constant Entity_Id := Target (Typ_Rep);
15102
15103 Stop_Check : exception;
15104 -- This exception is raised when the freeze node violates the
15105 -- placement rules.
15106
15107 procedure Check_Overriding_Primitive
15108 (Prim : Entity_Id;
15109 FNode : Node_Id);
15110 pragma Inline (Check_Overriding_Primitive);
15111 -- Verify that freeze node FNode is within the early call region of
15112 -- overriding primitive Prim's body.
15113
15114 function Freeze_Node_Location (FNode : Node_Id) return Source_Ptr;
15115 pragma Inline (Freeze_Node_Location);
15116 -- Return a more accurate source location associated with freeze node
15117 -- FNode.
15118
15119 function Precedes_Source_Construct (N : Node_Id) return Boolean;
15120 pragma Inline (Precedes_Source_Construct);
15121 -- Determine whether arbitrary node N appears prior to some source
15122 -- construct.
15123
15124 procedure Suggest_Elaborate_Body
15125 (N : Node_Id;
15126 Body_Decl : Node_Id;
15127 Error_Nod : Node_Id);
15128 pragma Inline (Suggest_Elaborate_Body);
15129 -- Suggest the use of pragma Elaborate_Body when the pragma will
15130 -- allow for node N to appear within the early call region of
15131 -- subprogram body Body_Decl. The suggestion is attached to
15132 -- Error_Nod as a continuation error.
15133
15134 --------------------------------
15135 -- Check_Overriding_Primitive --
15136 --------------------------------
15137
15138 procedure Check_Overriding_Primitive
15139 (Prim : Entity_Id;
15140 FNode : Node_Id)
15141 is
15142 Prim_Decl : constant Node_Id := Unit_Declaration_Node (Prim);
15143 Body_Decl : Node_Id;
15144 Body_Id : Entity_Id;
15145 Region : Node_Id;
15146
15147 begin
15148 -- Nothing to do for predefined primitives because they are
15149 -- artifacts of tagged type expansion and cannot override source
15150 -- primitives.
15151
15152 if Is_Predefined_Dispatching_Operation (Prim) then
15153 return;
15154 end if;
15155
15156 Body_Id := Corresponding_Body (Prim_Decl);
15157
15158 -- Nothing to do when the primitive does not have a corresponding
15159 -- body. This can happen when the unit with the bodies is not the
15160 -- main unit subjected to ABE checks.
15161
15162 if No (Body_Id) then
15163 return;
15164
15165 -- The primitive overrides a parent or progenitor primitive
15166
15167 elsif Present (Overridden_Operation (Prim)) then
15168
15169 -- Nothing to do when overriding an interface primitive happens
15170 -- by inheriting a non-interface primitive as the check would
15171 -- be done on the parent primitive.
15172
15173 if Present (Alias (Prim)) then
15174 return;
15175 end if;
15176
15177 -- Nothing to do when the primitive is not overriding. The body of
15178 -- such a primitive cannot be targeted by a dispatching call which
15179 -- is executable during elaboration, and cannot cause an ABE.
15180
15181 else
15182 return;
15183 end if;
15184
15185 Body_Decl := Unit_Declaration_Node (Body_Id);
15186 Region := Find_Early_Call_Region (Body_Decl);
15187
15188 -- The freeze node appears prior to the early call region of the
15189 -- primitive body.
15190
15191 -- IMPORTANT: This check must always be performed even when
15192 -- -gnatd.v (enforce SPARK elaboration rules in SPARK code) is not
15193 -- specified because the static model cannot guarantee the absence
15194 -- of ABEs in the presence of dispatching calls.
15195
15196 if Earlier_In_Extended_Unit (FNode, Region) then
15197 Error_Msg_Node_2 := Prim;
15198 Error_Msg_NE
15199 ("first freezing point of type & must appear within early "
15200 & "call region of primitive body & (SPARK RM 7.7(8))",
15201 Typ_Decl, Typ);
15202
15203 Error_Msg_Sloc := Sloc (Region);
15204 Error_Msg_N ("\region starts #", Typ_Decl);
15205
15206 Error_Msg_Sloc := Sloc (Body_Decl);
15207 Error_Msg_N ("\region ends #", Typ_Decl);
15208
15209 Error_Msg_Sloc := Freeze_Node_Location (FNode);
15210 Error_Msg_N ("\first freezing point #", Typ_Decl);
15211
15212 -- If applicable, suggest the use of pragma Elaborate_Body in
15213 -- the associated package spec.
15214
15215 Suggest_Elaborate_Body
15216 (N => FNode,
15217 Body_Decl => Body_Decl,
15218 Error_Nod => Typ_Decl);
15219
15220 raise Stop_Check;
15221 end if;
15222 end Check_Overriding_Primitive;
15223
15224 --------------------------
15225 -- Freeze_Node_Location --
15226 --------------------------
15227
15228 function Freeze_Node_Location (FNode : Node_Id) return Source_Ptr is
15229 Context : constant Node_Id := Parent (FNode);
15230 Loc : constant Source_Ptr := Sloc (FNode);
15231
15232 Prv_Decls : List_Id;
15233 Vis_Decls : List_Id;
15234
15235 begin
15236 -- In general, the source location of the freeze node is as close
15237 -- as possible to the real freeze point, except when the freeze
15238 -- node is at the "bottom" of a package spec.
15239
15240 if Nkind (Context) = N_Package_Specification then
15241 Prv_Decls := Private_Declarations (Context);
15242 Vis_Decls := Visible_Declarations (Context);
15243
15244 -- The freeze node appears in the private declarations of the
15245 -- package.
15246
15247 if Present (Prv_Decls)
15248 and then List_Containing (FNode) = Prv_Decls
15249 then
15250 null;
15251
15252 -- The freeze node appears in the visible declarations of the
15253 -- package and there are no private declarations.
15254
15255 elsif Present (Vis_Decls)
15256 and then List_Containing (FNode) = Vis_Decls
15257 and then (No (Prv_Decls) or else Is_Empty_List (Prv_Decls))
15258 then
15259 null;
15260
15261 -- Otherwise the freeze node is not in the "last" declarative
15262 -- list of the package. Use the existing source location of the
15263 -- freeze node.
15264
15265 else
15266 return Loc;
15267 end if;
15268
15269 -- The freeze node appears at the "bottom" of the package when
15270 -- it is in the "last" declarative list and is either the last
15271 -- in the list or is followed by internal constructs only. In
15272 -- that case the more appropriate source location is that of
15273 -- the package end label.
15274
15275 if not Precedes_Source_Construct (FNode) then
15276 return Sloc (End_Label (Context));
15277 end if;
15278 end if;
15279
15280 return Loc;
15281 end Freeze_Node_Location;
15282
15283 -------------------------------
15284 -- Precedes_Source_Construct --
15285 -------------------------------
15286
15287 function Precedes_Source_Construct (N : Node_Id) return Boolean is
15288 Decl : Node_Id;
15289
15290 begin
15291 Decl := Next (N);
15292 while Present (Decl) loop
15293 if Comes_From_Source (Decl) then
15294 return True;
15295
15296 -- A generated body for a source expression function is treated
15297 -- as a source construct.
15298
15299 elsif Nkind (Decl) = N_Subprogram_Body
15300 and then Was_Expression_Function (Decl)
15301 and then Comes_From_Source (Original_Node (Decl))
15302 then
15303 return True;
15304 end if;
15305
15306 Next (Decl);
15307 end loop;
15308
15309 return False;
15310 end Precedes_Source_Construct;
15311
15312 ----------------------------
15313 -- Suggest_Elaborate_Body --
15314 ----------------------------
15315
15316 procedure Suggest_Elaborate_Body
15317 (N : Node_Id;
15318 Body_Decl : Node_Id;
15319 Error_Nod : Node_Id)
15320 is
15321 Unit_Id : constant Node_Id := Unit (Cunit (Main_Unit));
15322 Region : Node_Id;
15323
15324 begin
15325 -- The suggestion applies only when the subprogram body resides in
15326 -- a compilation package body, and a pragma Elaborate_Body would
15327 -- allow for the node to appear in the early call region of the
15328 -- subprogram body. This implies that all code from the subprogram
15329 -- body up to the node is preelaborable.
15330
15331 if Nkind (Unit_Id) = N_Package_Body then
15332
15333 -- Find the start of the early call region again assuming that
15334 -- the package spec has pragma Elaborate_Body. Note that the
15335 -- internal data structures are intentionally not updated
15336 -- because this is a speculative search.
15337
15338 Region :=
15339 Find_Early_Call_Region
15340 (Body_Decl => Body_Decl,
15341 Assume_Elab_Body => True,
15342 Skip_Memoization => True);
15343
15344 -- If the node appears within the early call region, assuming
15345 -- that the package spec carries pragma Elaborate_Body, then it
15346 -- is safe to suggest the pragma.
15347
15348 if Earlier_In_Extended_Unit (Region, N) then
15349 Error_Msg_Name_1 := Name_Elaborate_Body;
15350 Error_Msg_NE
15351 ("\consider adding pragma % in spec of unit &",
15352 Error_Nod, Defining_Entity (Unit_Id));
15353 end if;
15354 end if;
15355 end Suggest_Elaborate_Body;
15356
15357 -- Local variables
15358
15359 FNode : constant Node_Id := Freeze_Node (Typ);
15360 Prims : constant Elist_Id := Direct_Primitive_Operations (Typ);
15361
15362 Prim_Elmt : Elmt_Id;
15363
15364 -- Start of processing for Process_SPARK_Derived_Type
15365
15366 begin
15367 -- A type should have its freeze node set by the time SPARK scenarios
15368 -- are being verified.
15369
15370 pragma Assert (Present (FNode));
15371
15372 -- Verify that the freeze node of the derived type is within the
15373 -- early call region of each overriding primitive body
15374 -- (SPARK RM 7.7(8)).
15375
15376 if Present (Prims) then
15377 Prim_Elmt := First_Elmt (Prims);
15378 while Present (Prim_Elmt) loop
15379 Check_Overriding_Primitive
15380 (Prim => Node (Prim_Elmt),
15381 FNode => FNode);
15382
15383 Next_Elmt (Prim_Elmt);
15384 end loop;
15385 end if;
15386
15387 exception
15388 when Stop_Check =>
15389 null;
15390 end Process_SPARK_Derived_Type;
15391
15392 ---------------------------------
15393 -- Process_SPARK_Instantiation --
15394 ---------------------------------
15395
15396 procedure Process_SPARK_Instantiation
15397 (Inst : Node_Id;
15398 Inst_Rep : Scenario_Rep_Id;
15399 In_State : Processing_In_State)
15400 is
15401 Gen_Id : constant Entity_Id := Target (Inst_Rep);
15402 Gen_Rep : constant Target_Rep_Id :=
15403 Target_Representation_Of (Gen_Id, In_State);
15404 Body_Decl : constant Node_Id := Body_Declaration (Gen_Rep);
15405
15406 begin
15407 -- The instantiation and the generic body are both in the main unit
15408
15409 if Present (Body_Decl)
15410 and then In_Extended_Main_Code_Unit (Body_Decl)
15411
15412 -- If the instantiation appears prior to the generic body, then the
15413 -- instantiation is illegal (SPARK RM 7.7(6)).
15414
15415 -- IMPORTANT: This check must always be performed even when
15416 -- -gnatd.v (enforce SPARK elaboration rules in SPARK code) is not
15417 -- specified because the rule prevents use-before-declaration of
15418 -- objects that may precede the generic body.
15419
15420 and then Earlier_In_Extended_Unit (Inst, Body_Decl)
15421 then
15422 Error_Msg_NE
15423 ("cannot instantiate & before body seen", Inst, Gen_Id);
15424 end if;
15425 end Process_SPARK_Instantiation;
15426
15427 ----------------------------
15428 -- Process_SPARK_Scenario --
15429 ----------------------------
15430
15431 procedure Process_SPARK_Scenario
15432 (N : Node_Id;
15433 In_State : Processing_In_State)
15434 is
15435 Scen : constant Node_Id := Scenario (N);
15436
15437 begin
15438 -- Ensure that a suitable elaboration model is in effect for SPARK
15439 -- rule verification.
15440
15441 Check_SPARK_Model_In_Effect;
15442
15443 -- Add the current scenario to the stack of active scenarios
15444
15445 Push_Active_Scenario (Scen);
15446
15447 -- Derived type
15448
15449 if Is_Suitable_SPARK_Derived_Type (Scen) then
15450 Process_SPARK_Derived_Type
15451 (Typ_Decl => Scen,
15452 Typ_Rep => Scenario_Representation_Of (Scen, In_State),
15453 In_State => In_State);
15454
15455 -- Instantiation
15456
15457 elsif Is_Suitable_SPARK_Instantiation (Scen) then
15458 Process_SPARK_Instantiation
15459 (Inst => Scen,
15460 Inst_Rep => Scenario_Representation_Of (Scen, In_State),
15461 In_State => In_State);
15462
15463 -- Refined_State pragma
15464
15465 elsif Is_Suitable_SPARK_Refined_State_Pragma (Scen) then
15466 Process_SPARK_Refined_State_Pragma
15467 (Prag => Scen,
15468 Prag_Rep => Scenario_Representation_Of (Scen, In_State),
15469 In_State => In_State);
15470 end if;
15471
15472 -- Remove the current scenario from the stack of active scenarios
15473 -- once all ABE diagnostics and checks have been performed.
15474
15475 Pop_Active_Scenario (Scen);
15476 end Process_SPARK_Scenario;
15477
15478 ----------------------------------------
15479 -- Process_SPARK_Refined_State_Pragma --
15480 ----------------------------------------
15481
15482 procedure Process_SPARK_Refined_State_Pragma
15483 (Prag : Node_Id;
15484 Prag_Rep : Scenario_Rep_Id;
15485 In_State : Processing_In_State)
15486 is
15487 pragma Unreferenced (Prag_Rep);
15488
15489 procedure Check_SPARK_Constituent (Constit_Id : Entity_Id);
15490 pragma Inline (Check_SPARK_Constituent);
15491 -- Ensure that a single constituent Constit_Id is elaborated prior to
15492 -- the main unit.
15493
15494 procedure Check_SPARK_Constituents (Constits : Elist_Id);
15495 pragma Inline (Check_SPARK_Constituents);
15496 -- Ensure that all constituents found in list Constits are elaborated
15497 -- prior to the main unit.
15498
15499 procedure Check_SPARK_Initialized_State (State : Node_Id);
15500 pragma Inline (Check_SPARK_Initialized_State);
15501 -- Ensure that the constituents of single abstract state State are
15502 -- elaborated prior to the main unit.
15503
15504 procedure Check_SPARK_Initialized_States (Pack_Id : Entity_Id);
15505 pragma Inline (Check_SPARK_Initialized_States);
15506 -- Ensure that the constituents of all abstract states which appear
15507 -- in the Initializes pragma of package Pack_Id are elaborated prior
15508 -- to the main unit.
15509
15510 -----------------------------
15511 -- Check_SPARK_Constituent --
15512 -----------------------------
15513
15514 procedure Check_SPARK_Constituent (Constit_Id : Entity_Id) is
15515 SM_Prag : Node_Id;
15516
15517 begin
15518 -- Nothing to do for "null" constituents
15519
15520 if Nkind (Constit_Id) = N_Null then
15521 return;
15522
15523 -- Nothing to do for illegal constituents
15524
15525 elsif Error_Posted (Constit_Id) then
15526 return;
15527 end if;
15528
15529 SM_Prag := SPARK_Pragma (Constit_Id);
15530
15531 -- The check applies only when the constituent is subject to
15532 -- pragma SPARK_Mode On.
15533
15534 if Present (SM_Prag)
15535 and then Get_SPARK_Mode_From_Annotation (SM_Prag) = On
15536 then
15537 -- An external constituent of an abstract state which appears
15538 -- in the Initializes pragma of a package spec imposes an
15539 -- Elaborate requirement on the context of the main unit.
15540 -- Determine whether the context has a pragma strong enough to
15541 -- meet the requirement.
15542
15543 -- IMPORTANT: This check is performed only when -gnatd.v
15544 -- (enforce SPARK elaboration rules in SPARK code) is in effect
15545 -- because the static model can ensure the prior elaboration of
15546 -- the unit which contains a constituent by installing implicit
15547 -- Elaborate pragma.
15548
15549 if Debug_Flag_Dot_V then
15550 Meet_Elaboration_Requirement
15551 (N => Prag,
15552 Targ_Id => Constit_Id,
15553 Req_Nam => Name_Elaborate,
15554 In_State => In_State);
15555
15556 -- Otherwise ensure that the unit with the external constituent
15557 -- is elaborated prior to the main unit.
15558
15559 else
15560 Ensure_Prior_Elaboration
15561 (N => Prag,
15562 Unit_Id => Find_Top_Unit (Constit_Id),
15563 Prag_Nam => Name_Elaborate,
15564 In_State => In_State);
15565 end if;
15566 end if;
15567 end Check_SPARK_Constituent;
15568
15569 ------------------------------
15570 -- Check_SPARK_Constituents --
15571 ------------------------------
15572
15573 procedure Check_SPARK_Constituents (Constits : Elist_Id) is
15574 Constit_Elmt : Elmt_Id;
15575
15576 begin
15577 if Present (Constits) then
15578 Constit_Elmt := First_Elmt (Constits);
15579 while Present (Constit_Elmt) loop
15580 Check_SPARK_Constituent (Node (Constit_Elmt));
15581 Next_Elmt (Constit_Elmt);
15582 end loop;
15583 end if;
15584 end Check_SPARK_Constituents;
15585
15586 -----------------------------------
15587 -- Check_SPARK_Initialized_State --
15588 -----------------------------------
15589
15590 procedure Check_SPARK_Initialized_State (State : Node_Id) is
15591 SM_Prag : Node_Id;
15592 State_Id : Entity_Id;
15593
15594 begin
15595 -- Nothing to do for "null" initialization items
15596
15597 if Nkind (State) = N_Null then
15598 return;
15599
15600 -- Nothing to do for illegal states
15601
15602 elsif Error_Posted (State) then
15603 return;
15604 end if;
15605
15606 State_Id := Entity_Of (State);
15607
15608 -- Sanitize the state
15609
15610 if No (State_Id) then
15611 return;
15612
15613 elsif Error_Posted (State_Id) then
15614 return;
15615
15616 elsif Ekind (State_Id) /= E_Abstract_State then
15617 return;
15618 end if;
15619
15620 -- The check is performed only when the abstract state is subject
15621 -- to SPARK_Mode On.
15622
15623 SM_Prag := SPARK_Pragma (State_Id);
15624
15625 if Present (SM_Prag)
15626 and then Get_SPARK_Mode_From_Annotation (SM_Prag) = On
15627 then
15628 Check_SPARK_Constituents (Refinement_Constituents (State_Id));
15629 end if;
15630 end Check_SPARK_Initialized_State;
15631
15632 ------------------------------------
15633 -- Check_SPARK_Initialized_States --
15634 ------------------------------------
15635
15636 procedure Check_SPARK_Initialized_States (Pack_Id : Entity_Id) is
15637 Init_Prag : constant Node_Id :=
15638 Get_Pragma (Pack_Id, Pragma_Initializes);
15639
15640 Init : Node_Id;
15641 Inits : Node_Id;
15642
15643 begin
15644 if Present (Init_Prag) then
15645 Inits := Expression (Get_Argument (Init_Prag, Pack_Id));
15646
15647 -- Avoid processing a "null" initialization list. The only
15648 -- other alternative is an aggregate.
15649
15650 if Nkind (Inits) = N_Aggregate then
15651
15652 -- The initialization items appear in list form:
15653 --
15654 -- (state1, state2)
15655
15656 if Present (Expressions (Inits)) then
15657 Init := First (Expressions (Inits));
15658 while Present (Init) loop
15659 Check_SPARK_Initialized_State (Init);
15660 Next (Init);
15661 end loop;
15662 end if;
15663
15664 -- The initialization items appear in associated form:
15665 --
15666 -- (state1 => item1,
15667 -- state2 => (item2, item3))
15668
15669 if Present (Component_Associations (Inits)) then
15670 Init := First (Component_Associations (Inits));
15671 while Present (Init) loop
15672 Check_SPARK_Initialized_State (Init);
15673 Next (Init);
15674 end loop;
15675 end if;
15676 end if;
15677 end if;
15678 end Check_SPARK_Initialized_States;
15679
15680 -- Local variables
15681
15682 Pack_Body : constant Node_Id := Find_Related_Package_Or_Body (Prag);
15683
15684 -- Start of processing for Process_SPARK_Refined_State_Pragma
15685
15686 begin
15687 -- Pragma Refined_State must be associated with a package body
15688
15689 pragma Assert
15690 (Present (Pack_Body) and then Nkind (Pack_Body) = N_Package_Body);
15691
15692 -- Verify that each external contitunent of an abstract state
15693 -- mentioned in pragma Initializes is properly elaborated.
15694
15695 Check_SPARK_Initialized_States (Unique_Defining_Entity (Pack_Body));
15696 end Process_SPARK_Refined_State_Pragma;
15697 end SPARK_Processor;
15698
15699 -------------------------------
15700 -- Spec_And_Body_From_Entity --
15701 -------------------------------
15702
15703 procedure Spec_And_Body_From_Entity
15704 (Id : Node_Id;
15705 Spec_Decl : out Node_Id;
15706 Body_Decl : out Node_Id)
15707 is
15708 begin
15709 Spec_And_Body_From_Node
15710 (N => Unit_Declaration_Node (Id),
15711 Spec_Decl => Spec_Decl,
15712 Body_Decl => Body_Decl);
15713 end Spec_And_Body_From_Entity;
15714
15715 -----------------------------
15716 -- Spec_And_Body_From_Node --
15717 -----------------------------
15718
15719 procedure Spec_And_Body_From_Node
15720 (N : Node_Id;
15721 Spec_Decl : out Node_Id;
15722 Body_Decl : out Node_Id)
15723 is
15724 Body_Id : Entity_Id;
15725 Spec_Id : Entity_Id;
15726
15727 begin
15728 -- Assume that the construct lacks spec and body
15729
15730 Body_Decl := Empty;
15731 Spec_Decl := Empty;
15732
15733 -- Bodies
15734
15735 if Nkind_In (N, N_Package_Body,
15736 N_Protected_Body,
15737 N_Subprogram_Body,
15738 N_Task_Body)
15739 then
15740 Spec_Id := Corresponding_Spec (N);
15741
15742 -- The body completes a previous declaration
15743
15744 if Present (Spec_Id) then
15745 Spec_Decl := Unit_Declaration_Node (Spec_Id);
15746
15747 -- Otherwise the body acts as the initial declaration, and is both a
15748 -- spec and body. There is no need to look for an optional body.
15749
15750 else
15751 Body_Decl := N;
15752 Spec_Decl := N;
15753 return;
15754 end if;
15755
15756 -- Declarations
15757
15758 elsif Nkind_In (N, N_Entry_Declaration,
15759 N_Generic_Package_Declaration,
15760 N_Generic_Subprogram_Declaration,
15761 N_Package_Declaration,
15762 N_Protected_Type_Declaration,
15763 N_Subprogram_Declaration,
15764 N_Task_Type_Declaration)
15765 then
15766 Spec_Decl := N;
15767
15768 -- Expression function
15769
15770 elsif Nkind (N) = N_Expression_Function then
15771 Spec_Id := Corresponding_Spec (N);
15772 pragma Assert (Present (Spec_Id));
15773
15774 Spec_Decl := Unit_Declaration_Node (Spec_Id);
15775
15776 -- Instantiations
15777
15778 elsif Nkind (N) in N_Generic_Instantiation then
15779 Spec_Decl := Instance_Spec (N);
15780 pragma Assert (Present (Spec_Decl));
15781
15782 -- Stubs
15783
15784 elsif Nkind (N) in N_Body_Stub then
15785 Spec_Id := Corresponding_Spec_Of_Stub (N);
15786
15787 -- The stub completes a previous declaration
15788
15789 if Present (Spec_Id) then
15790 Spec_Decl := Unit_Declaration_Node (Spec_Id);
15791
15792 -- Otherwise the stub acts as a spec
15793
15794 else
15795 Spec_Decl := N;
15796 end if;
15797 end if;
15798
15799 -- Obtain an optional or mandatory body
15800
15801 if Present (Spec_Decl) then
15802 Body_Id := Corresponding_Body (Spec_Decl);
15803
15804 if Present (Body_Id) then
15805 Body_Decl := Unit_Declaration_Node (Body_Id);
15806 end if;
15807 end if;
15808 end Spec_And_Body_From_Node;
15809
15810 -------------------------------
15811 -- Static_Elaboration_Checks --
15812 -------------------------------
15813
15814 function Static_Elaboration_Checks return Boolean is
15815 begin
15816 return not Dynamic_Elaboration_Checks;
15817 end Static_Elaboration_Checks;
15818
15819 -----------------
15820 -- Unit_Entity --
15821 -----------------
15822
15823 function Unit_Entity (Unit_Id : Entity_Id) return Entity_Id is
15824 function Is_Subunit (Id : Entity_Id) return Boolean;
15825 pragma Inline (Is_Subunit);
15826 -- Determine whether the entity of an initial declaration denotes a
15827 -- subunit.
15828
15829 ----------------
15830 -- Is_Subunit --
15831 ----------------
15832
15833 function Is_Subunit (Id : Entity_Id) return Boolean is
15834 Decl : constant Node_Id := Unit_Declaration_Node (Id);
15835
15836 begin
15837 return
15838 Nkind_In (Decl, N_Generic_Package_Declaration,
15839 N_Generic_Subprogram_Declaration,
15840 N_Package_Declaration,
15841 N_Protected_Type_Declaration,
15842 N_Subprogram_Declaration,
15843 N_Task_Type_Declaration)
15844 and then Present (Corresponding_Body (Decl))
15845 and then Nkind (Parent (Unit_Declaration_Node
15846 (Corresponding_Body (Decl)))) = N_Subunit;
15847 end Is_Subunit;
15848
15849 -- Local variables
15850
15851 Id : Entity_Id;
15852
15853 -- Start of processing for Unit_Entity
15854
15855 begin
15856 Id := Unique_Entity (Unit_Id);
15857
15858 -- Skip all subunits found in the scope chain which ends at the input
15859 -- unit.
15860
15861 while Is_Subunit (Id) loop
15862 Id := Scope (Id);
15863 end loop;
15864
15865 return Id;
15866 end Unit_Entity;
15867
15868 ---------------------------------
15869 -- Update_Elaboration_Scenario --
15870 ---------------------------------
15871
15872 procedure Update_Elaboration_Scenario (New_N : Node_Id; Old_N : Node_Id) is
15873 begin
15874 -- Nothing to do when the elaboration phase of the compiler is not
15875 -- active.
15876
15877 if not Elaboration_Phase_Active then
15878 return;
15879
15880 -- Nothing to do when the old and new scenarios are one and the same
15881
15882 elsif Old_N = New_N then
15883 return;
15884 end if;
15885
15886 -- A scenario is being transformed by Atree.Rewrite. Update all relevant
15887 -- internal data structures to reflect this change. This ensures that a
15888 -- potential run-time conditional ABE check or a guaranteed ABE failure
15889 -- is inserted at the proper place in the tree.
15890
15891 if Is_Scenario (Old_N) then
15892 Replace_Scenario (Old_N, New_N);
15893 end if;
15894 end Update_Elaboration_Scenario;
15895
15896 ---------------------------------------------------------------------------
15897 -- --
15898 -- L E G A C Y A C C E S S B E F O R E E L A B O R A T I O N --
15899 -- --
15900 -- M E C H A N I S M --
15901 -- --
15902 ---------------------------------------------------------------------------
15903
15904 -- This section contains the implementation of the pre-18.x legacy ABE
15905 -- mechanism. The mechanism can be activated using switch -gnatH (legacy
15906 -- elaboration checking mode enabled).
15907
15908 -----------------------------
15909 -- Description of Approach --
15910 -----------------------------
15911
15912 -- Every non-static call that is encountered by Sem_Res results in a call
15913 -- to Check_Elab_Call, with N being the call node, and Outer set to its
15914 -- default value of True. In addition X'Access is treated like a call
15915 -- for the access-to-procedure case, and in SPARK mode only we also
15916 -- check variable references.
15917
15918 -- The goal of Check_Elab_Call is to determine whether or not the reference
15919 -- in question can generate an access before elaboration error (raising
15920 -- Program_Error) either by directly calling a subprogram whose body
15921 -- has not yet been elaborated, or indirectly, by calling a subprogram
15922 -- whose body has been elaborated, but which contains a call to such a
15923 -- subprogram.
15924
15925 -- In addition, in SPARK mode, we are checking for a variable reference in
15926 -- another package, which requires an explicit Elaborate_All pragma.
15927
15928 -- The only references that we need to look at the outer level are
15929 -- references that occur in elaboration code. There are two cases. The
15930 -- reference can be at the outer level of elaboration code, or it can
15931 -- be within another unit, e.g. the elaboration code of a subprogram.
15932
15933 -- In the case of an elaboration call at the outer level, we must trace
15934 -- all calls to outer level routines either within the current unit or to
15935 -- other units that are with'ed. For calls within the current unit, we can
15936 -- determine if the body has been elaborated or not, and if it has not,
15937 -- then a warning is generated.
15938
15939 -- Note that there are two subcases. If the original call directly calls a
15940 -- subprogram whose body has not been elaborated, then we know that an ABE
15941 -- will take place, and we replace the call by a raise of Program_Error.
15942 -- If the call is indirect, then we don't know that the PE will be raised,
15943 -- since the call might be guarded by a conditional. In this case we set
15944 -- Do_Elab_Check on the call so that a dynamic check is generated, and
15945 -- output a warning.
15946
15947 -- For calls to a subprogram in a with'ed unit or a 'Access or variable
15948 -- reference (SPARK mode case), we require that a pragma Elaborate_All
15949 -- or pragma Elaborate be present, or that the referenced unit have a
15950 -- pragma Preelaborate, pragma Pure, or pragma Elaborate_Body. If none
15951 -- of these conditions is met, then a warning is generated that a pragma
15952 -- Elaborate_All may be needed (error in the SPARK case), or an implicit
15953 -- pragma is generated.
15954
15955 -- For the case of an elaboration call at some inner level, we are
15956 -- interested in tracing only calls to subprograms at the same level, i.e.
15957 -- those that can be called during elaboration. Any calls to outer level
15958 -- routines cannot cause ABE's as a result of the original call (there
15959 -- might be an outer level call to the subprogram from outside that causes
15960 -- the ABE, but that gets analyzed separately).
15961
15962 -- Note that we never trace calls to inner level subprograms, since these
15963 -- cannot result in ABE's unless there is an elaboration problem at a lower
15964 -- level, which will be separately detected.
15965
15966 -- Note on pragma Elaborate. The checking here assumes that a pragma
15967 -- Elaborate on a with'ed unit guarantees that subprograms within the unit
15968 -- can be called without causing an ABE. This is not in fact the case since
15969 -- pragma Elaborate does not guarantee the transitive coverage guaranteed
15970 -- by Elaborate_All. However, we decide to trust the user in this case.
15971
15972 --------------------------------------
15973 -- Instantiation Elaboration Errors --
15974 --------------------------------------
15975
15976 -- A special case arises when an instantiation appears in a context that is
15977 -- known to be before the body is elaborated, e.g.
15978
15979 -- generic package x is ...
15980 -- ...
15981 -- package xx is new x;
15982 -- ...
15983 -- package body x is ...
15984
15985 -- In this situation it is certain that an elaboration error will occur,
15986 -- and an unconditional raise Program_Error statement is inserted before
15987 -- the instantiation, and a warning generated.
15988
15989 -- The problem is that in this case we have no place to put the body of
15990 -- the instantiation. We can't put it in the normal place, because it is
15991 -- too early, and will cause errors to occur as a result of referencing
15992 -- entities before they are declared.
15993
15994 -- Our approach in this case is simply to avoid creating the body of the
15995 -- instantiation in such a case. The instantiation spec is modified to
15996 -- include dummy bodies for all subprograms, so that the resulting code
15997 -- does not contain subprogram specs with no corresponding bodies.
15998
15999 -- The following table records the recursive call chain for output in the
16000 -- Output routine. Each entry records the call node and the entity of the
16001 -- called routine. The number of entries in the table (i.e. the value of
16002 -- Elab_Call.Last) indicates the current depth of recursion and is used to
16003 -- identify the outer level.
16004
16005 type Elab_Call_Element is record
16006 Cloc : Source_Ptr;
16007 Ent : Entity_Id;
16008 end record;
16009
16010 package Elab_Call is new Table.Table
16011 (Table_Component_Type => Elab_Call_Element,
16012 Table_Index_Type => Int,
16013 Table_Low_Bound => 1,
16014 Table_Initial => 50,
16015 Table_Increment => 100,
16016 Table_Name => "Elab_Call");
16017
16018 -- The following table records all calls that have been processed starting
16019 -- from an outer level call. The table prevents both infinite recursion and
16020 -- useless reanalysis of calls within the same context. The use of context
16021 -- is important because it allows for proper checks in more complex code:
16022
16023 -- if ... then
16024 -- Call; -- requires a check
16025 -- Call; -- does not need a check thanks to the table
16026 -- elsif ... then
16027 -- Call; -- requires a check, different context
16028 -- end if;
16029
16030 -- Call; -- requires a check, different context
16031
16032 type Visited_Element is record
16033 Subp_Id : Entity_Id;
16034 -- The entity of the subprogram being called
16035
16036 Context : Node_Id;
16037 -- The context where the call to the subprogram occurs
16038 end record;
16039
16040 package Elab_Visited is new Table.Table
16041 (Table_Component_Type => Visited_Element,
16042 Table_Index_Type => Int,
16043 Table_Low_Bound => 1,
16044 Table_Initial => 200,
16045 Table_Increment => 100,
16046 Table_Name => "Elab_Visited");
16047
16048 -- The following table records delayed calls which must be examined after
16049 -- all generic bodies have been instantiated.
16050
16051 type Delay_Element is record
16052 N : Node_Id;
16053 -- The parameter N from the call to Check_Internal_Call. Note that this
16054 -- node may get rewritten over the delay period by expansion in the call
16055 -- case (but not in the instantiation case).
16056
16057 E : Entity_Id;
16058 -- The parameter E from the call to Check_Internal_Call
16059
16060 Orig_Ent : Entity_Id;
16061 -- The parameter Orig_Ent from the call to Check_Internal_Call
16062
16063 Curscop : Entity_Id;
16064 -- The current scope of the call. This is restored when we complete the
16065 -- delayed call, so that we do this in the right scope.
16066
16067 Outer_Scope : Entity_Id;
16068 -- Save scope of outer level call
16069
16070 From_Elab_Code : Boolean;
16071 -- Save indication of whether this call is from elaboration code
16072
16073 In_Task_Activation : Boolean;
16074 -- Save indication of whether this call is from a task body. Tasks are
16075 -- activated at the "begin", which is after all local procedure bodies,
16076 -- so calls to those procedures can't fail, even if they occur after the
16077 -- task body.
16078
16079 From_SPARK_Code : Boolean;
16080 -- Save indication of whether this call is under SPARK_Mode => On
16081 end record;
16082
16083 package Delay_Check is new Table.Table
16084 (Table_Component_Type => Delay_Element,
16085 Table_Index_Type => Int,
16086 Table_Low_Bound => 1,
16087 Table_Initial => 1000,
16088 Table_Increment => 100,
16089 Table_Name => "Delay_Check");
16090
16091 C_Scope : Entity_Id;
16092 -- Top-level scope of current scope. Compute this only once at the outer
16093 -- level, i.e. for a call to Check_Elab_Call from outside this unit.
16094
16095 Outer_Level_Sloc : Source_Ptr;
16096 -- Save Sloc value for outer level call node for comparisons of source
16097 -- locations. A body is too late if it appears after the *outer* level
16098 -- call, not the particular call that is being analyzed.
16099
16100 From_Elab_Code : Boolean;
16101 -- This flag shows whether the outer level call currently being examined
16102 -- is or is not in elaboration code. We are only interested in calls to
16103 -- routines in other units if this flag is True.
16104
16105 In_Task_Activation : Boolean := False;
16106 -- This flag indicates whether we are performing elaboration checks on task
16107 -- bodies, at the point of activation. If true, we do not raise
16108 -- Program_Error for calls to local procedures, because all local bodies
16109 -- are known to be elaborated. However, we still need to trace such calls,
16110 -- because a local procedure could call a procedure in another package,
16111 -- so we might need an implicit Elaborate_All.
16112
16113 Delaying_Elab_Checks : Boolean := True;
16114 -- This is set True till the compilation is complete, including the
16115 -- insertion of all instance bodies. Then when Check_Elab_Calls is called,
16116 -- the delay table is used to make the delayed calls and this flag is reset
16117 -- to False, so that the calls are processed.
16118
16119 -----------------------
16120 -- Local Subprograms --
16121 -----------------------
16122
16123 -- Note: Outer_Scope in all following specs represents the scope of
16124 -- interest of the outer level call. If it is set to Standard_Standard,
16125 -- then it means the outer level call was at elaboration level, and that
16126 -- thus all calls are of interest. If it was set to some other scope,
16127 -- then the original call was an inner call, and we are not interested
16128 -- in calls that go outside this scope.
16129
16130 procedure Activate_Elaborate_All_Desirable (N : Node_Id; U : Entity_Id);
16131 -- Analysis of construct N shows that we should set Elaborate_All_Desirable
16132 -- for the WITH clause for unit U (which will always be present). A special
16133 -- case is when N is a function or procedure instantiation, in which case
16134 -- it is sufficient to set Elaborate_Desirable, since in this case there is
16135 -- no possibility of transitive elaboration issues.
16136
16137 procedure Check_A_Call
16138 (N : Node_Id;
16139 E : Entity_Id;
16140 Outer_Scope : Entity_Id;
16141 Inter_Unit_Only : Boolean;
16142 Generate_Warnings : Boolean := True;
16143 In_Init_Proc : Boolean := False);
16144 -- This is the internal recursive routine that is called to check for
16145 -- possible elaboration error. The argument N is a subprogram call or
16146 -- generic instantiation, or 'Access attribute reference to be checked, and
16147 -- E is the entity of the called subprogram, or instantiated generic unit,
16148 -- or subprogram referenced by 'Access.
16149 --
16150 -- In SPARK mode, N can also be a variable reference, since in SPARK this
16151 -- also triggers a requirement for Elaborate_All, and in this case E is the
16152 -- entity being referenced.
16153 --
16154 -- Outer_Scope is the outer level scope for the original reference.
16155 -- Inter_Unit_Only is set if the call is only to be checked in the
16156 -- case where it is to another unit (and skipped if within a unit).
16157 -- Generate_Warnings is set to False to suppress warning messages about
16158 -- missing pragma Elaborate_All's. These messages are not wanted for
16159 -- inner calls in the dynamic model. Note that an instance of the Access
16160 -- attribute applied to a subprogram also generates a call to this
16161 -- procedure (since the referenced subprogram may be called later
16162 -- indirectly). Flag In_Init_Proc should be set whenever the current
16163 -- context is a type init proc.
16164 --
16165 -- Note: this might better be called Check_A_Reference to recognize the
16166 -- variable case for SPARK, but we prefer to retain the historical name
16167 -- since in practice this is mostly about checking calls for the possible
16168 -- occurrence of an access-before-elaboration exception.
16169
16170 procedure Check_Bad_Instantiation (N : Node_Id);
16171 -- N is a node for an instantiation (if called with any other node kind,
16172 -- Check_Bad_Instantiation ignores the call). This subprogram checks for
16173 -- the special case of a generic instantiation of a generic spec in the
16174 -- same declarative part as the instantiation where a body is present and
16175 -- has not yet been seen. This is an obvious error, but needs to be checked
16176 -- specially at the time of the instantiation, since it is a case where we
16177 -- cannot insert the body anywhere. If this case is detected, warnings are
16178 -- generated, and a raise of Program_Error is inserted. In addition any
16179 -- subprograms in the generic spec are stubbed, and the Bad_Instantiation
16180 -- flag is set on the instantiation node. The caller in Sem_Ch12 uses this
16181 -- flag as an indication that no attempt should be made to insert an
16182 -- instance body.
16183
16184 procedure Check_Internal_Call
16185 (N : Node_Id;
16186 E : Entity_Id;
16187 Outer_Scope : Entity_Id;
16188 Orig_Ent : Entity_Id);
16189 -- N is a function call or procedure statement call node and E is the
16190 -- entity of the called function, which is within the current compilation
16191 -- unit (where subunits count as part of the parent). This call checks if
16192 -- this call, or any call within any accessed body could cause an ABE, and
16193 -- if so, outputs a warning. Orig_Ent differs from E only in the case of
16194 -- renamings, and points to the original name of the entity. This is used
16195 -- for error messages. Outer_Scope is the outer level scope for the
16196 -- original call.
16197
16198 procedure Check_Internal_Call_Continue
16199 (N : Node_Id;
16200 E : Entity_Id;
16201 Outer_Scope : Entity_Id;
16202 Orig_Ent : Entity_Id);
16203 -- The processing for Check_Internal_Call is divided up into two phases,
16204 -- and this represents the second phase. The second phase is delayed if
16205 -- Delaying_Elab_Checks is set to True. In this delayed case, the first
16206 -- phase makes an entry in the Delay_Check table, which is processed when
16207 -- Check_Elab_Calls is called. N, E and Orig_Ent are as for the call to
16208 -- Check_Internal_Call. Outer_Scope is the outer level scope for the
16209 -- original call.
16210
16211 function Get_Referenced_Ent (N : Node_Id) return Entity_Id;
16212 -- N is either a function or procedure call or an access attribute that
16213 -- references a subprogram. This call retrieves the relevant entity. If
16214 -- this is a call to a protected subprogram, the entity is a selected
16215 -- component. The callable entity may be absent, in which case Empty is
16216 -- returned. This happens with non-analyzed calls in nested generics.
16217 --
16218 -- If SPARK_Mode is On, then N can also be a reference to an E_Variable
16219 -- entity, in which case, the value returned is simply this entity.
16220
16221 function Has_Generic_Body (N : Node_Id) return Boolean;
16222 -- N is a generic package instantiation node, and this routine determines
16223 -- if this package spec does in fact have a generic body. If so, then
16224 -- True is returned, otherwise False. Note that this is not at all the
16225 -- same as checking if the unit requires a body, since it deals with
16226 -- the case of optional bodies accurately (i.e. if a body is optional,
16227 -- then it looks to see if a body is actually present). Note: this
16228 -- function can only do a fully correct job if in generating code mode
16229 -- where all bodies have to be present. If we are operating in semantics
16230 -- check only mode, then in some cases of optional bodies, a result of
16231 -- False may incorrectly be given. In practice this simply means that
16232 -- some cases of warnings for incorrect order of elaboration will only
16233 -- be given when generating code, which is not a big problem (and is
16234 -- inevitable, given the optional body semantics of Ada).
16235
16236 procedure Insert_Elab_Check (N : Node_Id; C : Node_Id := Empty);
16237 -- Given code for an elaboration check (or unconditional raise if the check
16238 -- is not needed), inserts the code in the appropriate place. N is the call
16239 -- or instantiation node for which the check code is required. C is the
16240 -- test whose failure triggers the raise.
16241
16242 function Is_Call_Of_Generic_Formal (N : Node_Id) return Boolean;
16243 -- Returns True if node N is a call to a generic formal subprogram
16244
16245 function Is_Finalization_Procedure (Id : Entity_Id) return Boolean;
16246 -- Determine whether entity Id denotes a [Deep_]Finalize procedure
16247
16248 procedure Output_Calls
16249 (N : Node_Id;
16250 Check_Elab_Flag : Boolean);
16251 -- Outputs chain of calls stored in the Elab_Call table. The caller has
16252 -- already generated the main warning message, so the warnings generated
16253 -- are all continuation messages. The argument is the call node at which
16254 -- the messages are to be placed. When Check_Elab_Flag is set, calls are
16255 -- enumerated only when flag Elab_Warning is set for the dynamic case or
16256 -- when flag Elab_Info_Messages is set for the static case.
16257
16258 function Same_Elaboration_Scope (Scop1, Scop2 : Entity_Id) return Boolean;
16259 -- Given two scopes, determine whether they are the same scope from an
16260 -- elaboration point of view, i.e. packages and blocks are ignored.
16261
16262 procedure Set_C_Scope;
16263 -- On entry C_Scope is set to some scope. On return, C_Scope is reset
16264 -- to be the enclosing compilation unit of this scope.
16265
16266 procedure Set_Elaboration_Constraint
16267 (Call : Node_Id;
16268 Subp : Entity_Id;
16269 Scop : Entity_Id);
16270 -- The current unit U may depend semantically on some unit P that is not
16271 -- in the current context. If there is an elaboration call that reaches P,
16272 -- we need to indicate that P requires an Elaborate_All, but this is not
16273 -- effective in U's ali file, if there is no with_clause for P. In this
16274 -- case we add the Elaborate_All on the unit Q that directly or indirectly
16275 -- makes P available. This can happen in two cases:
16276 --
16277 -- a) Q declares a subtype of a type declared in P, and the call is an
16278 -- initialization call for an object of that subtype.
16279 --
16280 -- b) Q declares an object of some tagged type whose root type is
16281 -- declared in P, and the initialization call uses object notation on
16282 -- that object to reach a primitive operation or a classwide operation
16283 -- declared in P.
16284 --
16285 -- If P appears in the context of U, the current processing is correct.
16286 -- Otherwise we must identify these two cases to retrieve Q and place the
16287 -- Elaborate_All_Desirable on it.
16288
16289 function Spec_Entity (E : Entity_Id) return Entity_Id;
16290 -- Given a compilation unit entity, if it is a spec entity, it is returned
16291 -- unchanged. If it is a body entity, then the spec for the corresponding
16292 -- spec is returned
16293
16294 function Within (E1, E2 : Entity_Id) return Boolean;
16295 -- Given two scopes E1 and E2, returns True if E1 is equal to E2, or is one
16296 -- of its contained scopes, False otherwise.
16297
16298 function Within_Elaborate_All
16299 (Unit : Unit_Number_Type;
16300 E : Entity_Id) return Boolean;
16301 -- Return True if we are within the scope of an Elaborate_All for E, or if
16302 -- we are within the scope of an Elaborate_All for some other unit U, and U
16303 -- with's E. This prevents spurious warnings when the called entity is
16304 -- renamed within U, or in case of generic instances.
16305
16306 --------------------------------------
16307 -- Activate_Elaborate_All_Desirable --
16308 --------------------------------------
16309
16310 procedure Activate_Elaborate_All_Desirable (N : Node_Id; U : Entity_Id) is
16311 UN : constant Unit_Number_Type := Get_Code_Unit (N);
16312 CU : constant Node_Id := Cunit (UN);
16313 UE : constant Entity_Id := Cunit_Entity (UN);
16314 Unm : constant Unit_Name_Type := Unit_Name (UN);
16315 CI : constant List_Id := Context_Items (CU);
16316 Itm : Node_Id;
16317 Ent : Entity_Id;
16318
16319 procedure Add_To_Context_And_Mark (Itm : Node_Id);
16320 -- This procedure is called when the elaborate indication must be
16321 -- applied to a unit not in the context of the referencing unit. The
16322 -- unit gets added to the context as an implicit with.
16323
16324 function In_Withs_Of (UEs : Entity_Id) return Boolean;
16325 -- UEs is the spec entity of a unit. If the unit to be marked is
16326 -- in the context item list of this unit spec, then the call returns
16327 -- True and Itm is left set to point to the relevant N_With_Clause node.
16328
16329 procedure Set_Elab_Flag (Itm : Node_Id);
16330 -- Sets Elaborate_[All_]Desirable as appropriate on Itm
16331
16332 -----------------------------
16333 -- Add_To_Context_And_Mark --
16334 -----------------------------
16335
16336 procedure Add_To_Context_And_Mark (Itm : Node_Id) is
16337 CW : constant Node_Id :=
16338 Make_With_Clause (Sloc (Itm),
16339 Name => Name (Itm));
16340
16341 begin
16342 Set_Library_Unit (CW, Library_Unit (Itm));
16343 Set_Implicit_With (CW);
16344
16345 -- Set elaborate all desirable on copy and then append the copy to
16346 -- the list of body with's and we are done.
16347
16348 Set_Elab_Flag (CW);
16349 Append_To (CI, CW);
16350 end Add_To_Context_And_Mark;
16351
16352 -----------------
16353 -- In_Withs_Of --
16354 -----------------
16355
16356 function In_Withs_Of (UEs : Entity_Id) return Boolean is
16357 UNs : constant Unit_Number_Type := Get_Source_Unit (UEs);
16358 CUs : constant Node_Id := Cunit (UNs);
16359 CIs : constant List_Id := Context_Items (CUs);
16360
16361 begin
16362 Itm := First (CIs);
16363 while Present (Itm) loop
16364 if Nkind (Itm) = N_With_Clause then
16365 Ent :=
16366 Cunit_Entity (Get_Cunit_Unit_Number (Library_Unit (Itm)));
16367
16368 if U = Ent then
16369 return True;
16370 end if;
16371 end if;
16372
16373 Next (Itm);
16374 end loop;
16375
16376 return False;
16377 end In_Withs_Of;
16378
16379 -------------------
16380 -- Set_Elab_Flag --
16381 -------------------
16382
16383 procedure Set_Elab_Flag (Itm : Node_Id) is
16384 begin
16385 if Nkind (N) in N_Subprogram_Instantiation then
16386 Set_Elaborate_Desirable (Itm);
16387 else
16388 Set_Elaborate_All_Desirable (Itm);
16389 end if;
16390 end Set_Elab_Flag;
16391
16392 -- Start of processing for Activate_Elaborate_All_Desirable
16393
16394 begin
16395 -- Do not set binder indication if expansion is disabled, as when
16396 -- compiling a generic unit.
16397
16398 if not Expander_Active then
16399 return;
16400 end if;
16401
16402 -- If an instance of a generic package contains a controlled object (so
16403 -- we're calling Initialize at elaboration time), and the instance is in
16404 -- a package body P that says "with P;", then we need to return without
16405 -- adding "pragma Elaborate_All (P);" to P.
16406
16407 if U = Main_Unit_Entity then
16408 return;
16409 end if;
16410
16411 Itm := First (CI);
16412 while Present (Itm) loop
16413 if Nkind (Itm) = N_With_Clause then
16414 Ent := Cunit_Entity (Get_Cunit_Unit_Number (Library_Unit (Itm)));
16415
16416 -- If we find it, then mark elaborate all desirable and return
16417
16418 if U = Ent then
16419 Set_Elab_Flag (Itm);
16420 return;
16421 end if;
16422 end if;
16423
16424 Next (Itm);
16425 end loop;
16426
16427 -- If we fall through then the with clause is not present in the
16428 -- current unit. One legitimate possibility is that the with clause
16429 -- is present in the spec when we are a body.
16430
16431 if Is_Body_Name (Unm)
16432 and then In_Withs_Of (Spec_Entity (UE))
16433 then
16434 Add_To_Context_And_Mark (Itm);
16435 return;
16436 end if;
16437
16438 -- Similarly, we may be in the spec or body of a child unit, where
16439 -- the unit in question is with'ed by some ancestor of the child unit.
16440
16441 if Is_Child_Name (Unm) then
16442 declare
16443 Pkg : Entity_Id;
16444
16445 begin
16446 Pkg := UE;
16447 loop
16448 Pkg := Scope (Pkg);
16449 exit when Pkg = Standard_Standard;
16450
16451 if In_Withs_Of (Pkg) then
16452 Add_To_Context_And_Mark (Itm);
16453 return;
16454 end if;
16455 end loop;
16456 end;
16457 end if;
16458
16459 -- Here if we do not find with clause on spec or body. We just ignore
16460 -- this case; it means that the elaboration involves some other unit
16461 -- than the unit being compiled, and will be caught elsewhere.
16462 end Activate_Elaborate_All_Desirable;
16463
16464 ------------------
16465 -- Check_A_Call --
16466 ------------------
16467
16468 procedure Check_A_Call
16469 (N : Node_Id;
16470 E : Entity_Id;
16471 Outer_Scope : Entity_Id;
16472 Inter_Unit_Only : Boolean;
16473 Generate_Warnings : Boolean := True;
16474 In_Init_Proc : Boolean := False)
16475 is
16476 Access_Case : constant Boolean := Nkind (N) = N_Attribute_Reference;
16477 -- Indicates if we have Access attribute case
16478
16479 function Call_To_Instance_From_Outside (Id : Entity_Id) return Boolean;
16480 -- True if we're calling an instance of a generic subprogram, or a
16481 -- subprogram in an instance of a generic package, and the call is
16482 -- outside that instance.
16483
16484 procedure Elab_Warning
16485 (Msg_D : String;
16486 Msg_S : String;
16487 Ent : Node_Or_Entity_Id);
16488 -- Generate a call to Error_Msg_NE with parameters Msg_D or Msg_S (for
16489 -- dynamic or static elaboration model), N and Ent. Msg_D is a real
16490 -- warning (output if Msg_D is non-null and Elab_Warnings is set),
16491 -- Msg_S is an info message (output if Elab_Info_Messages is set).
16492
16493 function Find_W_Scope return Entity_Id;
16494 -- Find top-level scope for called entity (not following renamings
16495 -- or derivations). This is where the Elaborate_All will go if it is
16496 -- needed. We start with the called entity, except in the case of an
16497 -- initialization procedure outside the current package, where the init
16498 -- proc is in the root package, and we start from the entity of the name
16499 -- in the call.
16500
16501 -----------------------------------
16502 -- Call_To_Instance_From_Outside --
16503 -----------------------------------
16504
16505 function Call_To_Instance_From_Outside (Id : Entity_Id) return Boolean is
16506 Scop : Entity_Id := Id;
16507
16508 begin
16509 loop
16510 if Scop = Standard_Standard then
16511 return False;
16512 end if;
16513
16514 if Is_Generic_Instance (Scop) then
16515 return not In_Open_Scopes (Scop);
16516 end if;
16517
16518 Scop := Scope (Scop);
16519 end loop;
16520 end Call_To_Instance_From_Outside;
16521
16522 ------------------
16523 -- Elab_Warning --
16524 ------------------
16525
16526 procedure Elab_Warning
16527 (Msg_D : String;
16528 Msg_S : String;
16529 Ent : Node_Or_Entity_Id)
16530 is
16531 begin
16532 -- Dynamic elaboration checks, real warning
16533
16534 if Dynamic_Elaboration_Checks then
16535 if not Access_Case then
16536 if Msg_D /= "" and then Elab_Warnings then
16537 Error_Msg_NE (Msg_D, N, Ent);
16538 end if;
16539
16540 -- In the access case emit first warning message as well,
16541 -- otherwise list of calls will appear as errors.
16542
16543 elsif Elab_Warnings then
16544 Error_Msg_NE (Msg_S, N, Ent);
16545 end if;
16546
16547 -- Static elaboration checks, info message
16548
16549 else
16550 if Elab_Info_Messages then
16551 Error_Msg_NE (Msg_S, N, Ent);
16552 end if;
16553 end if;
16554 end Elab_Warning;
16555
16556 ------------------
16557 -- Find_W_Scope --
16558 ------------------
16559
16560 function Find_W_Scope return Entity_Id is
16561 Refed_Ent : constant Entity_Id := Get_Referenced_Ent (N);
16562 W_Scope : Entity_Id;
16563
16564 begin
16565 if Is_Init_Proc (Refed_Ent)
16566 and then not In_Same_Extended_Unit (N, Refed_Ent)
16567 then
16568 W_Scope := Scope (Refed_Ent);
16569 else
16570 W_Scope := E;
16571 end if;
16572
16573 -- Now loop through scopes to get to the enclosing compilation unit
16574
16575 while not Is_Compilation_Unit (W_Scope) loop
16576 W_Scope := Scope (W_Scope);
16577 end loop;
16578
16579 return W_Scope;
16580 end Find_W_Scope;
16581
16582 -- Local variables
16583
16584 Inst_Case : constant Boolean := Nkind (N) in N_Generic_Instantiation;
16585 -- Indicates if we have instantiation case
16586
16587 Loc : constant Source_Ptr := Sloc (N);
16588
16589 Variable_Case : constant Boolean :=
16590 Nkind (N) in N_Has_Entity
16591 and then Present (Entity (N))
16592 and then Ekind (Entity (N)) = E_Variable;
16593 -- Indicates if we have variable reference case
16594
16595 W_Scope : constant Entity_Id := Find_W_Scope;
16596 -- Top-level scope of directly called entity for subprogram. This
16597 -- differs from E_Scope in the case where renamings or derivations
16598 -- are involved, since it does not follow these links. W_Scope is
16599 -- generally in a visible unit, and it is this scope that may require
16600 -- an Elaborate_All. However, there are some cases (initialization
16601 -- calls and calls involving object notation) where W_Scope might not
16602 -- be in the context of the current unit, and there is an intermediate
16603 -- package that is, in which case the Elaborate_All has to be placed
16604 -- on this intermediate package. These special cases are handled in
16605 -- Set_Elaboration_Constraint.
16606
16607 Ent : Entity_Id;
16608 Callee_Unit_Internal : Boolean;
16609 Caller_Unit_Internal : Boolean;
16610 Decl : Node_Id;
16611 Inst_Callee : Source_Ptr;
16612 Inst_Caller : Source_Ptr;
16613 Unit_Callee : Unit_Number_Type;
16614 Unit_Caller : Unit_Number_Type;
16615
16616 Body_Acts_As_Spec : Boolean;
16617 -- Set to true if call is to body acting as spec (no separate spec)
16618
16619 Cunit_SC : Boolean := False;
16620 -- Set to suppress dynamic elaboration checks where one of the
16621 -- enclosing scopes has Elaboration_Checks_Suppressed set, or else
16622 -- if a pragma Elaborate[_All] applies to that scope, in which case
16623 -- warnings on the scope are also suppressed. For the internal case,
16624 -- we ignore this flag.
16625
16626 E_Scope : Entity_Id;
16627 -- Top-level scope of entity for called subprogram. This value includes
16628 -- following renamings and derivations, so this scope can be in a
16629 -- non-visible unit. This is the scope that is to be investigated to
16630 -- see whether an elaboration check is required.
16631
16632 Is_DIC : Boolean;
16633 -- Flag set when the subprogram being invoked is the procedure generated
16634 -- for pragma Default_Initial_Condition.
16635
16636 SPARK_Elab_Errors : Boolean;
16637 -- Flag set when an entity is called or a variable is read during SPARK
16638 -- dynamic elaboration.
16639
16640 -- Start of processing for Check_A_Call
16641
16642 begin
16643 -- If the call is known to be within a local Suppress Elaboration
16644 -- pragma, nothing to check. This can happen in task bodies. But
16645 -- we ignore this for a call to a generic formal.
16646
16647 if Nkind (N) in N_Subprogram_Call
16648 and then No_Elaboration_Check (N)
16649 and then not Is_Call_Of_Generic_Formal (N)
16650 then
16651 return;
16652
16653 -- If this is a rewrite of a Valid_Scalars attribute, then nothing to
16654 -- check, we don't mind in this case if the call occurs before the body
16655 -- since this is all generated code.
16656
16657 elsif Nkind (Original_Node (N)) = N_Attribute_Reference
16658 and then Attribute_Name (Original_Node (N)) = Name_Valid_Scalars
16659 then
16660 return;
16661
16662 -- Intrinsics such as instances of Unchecked_Deallocation do not have
16663 -- any body, so elaboration checking is not needed, and would be wrong.
16664
16665 elsif Is_Intrinsic_Subprogram (E) then
16666 return;
16667
16668 -- Do not consider references to internal variables for SPARK semantics
16669
16670 elsif Variable_Case and then not Comes_From_Source (E) then
16671 return;
16672 end if;
16673
16674 -- Proceed with check
16675
16676 Ent := E;
16677
16678 -- For a variable reference, just set Body_Acts_As_Spec to False
16679
16680 if Variable_Case then
16681 Body_Acts_As_Spec := False;
16682
16683 -- Additional checks for all other cases
16684
16685 else
16686 -- Go to parent for derived subprogram, or to original subprogram in
16687 -- the case of a renaming (Alias covers both these cases).
16688
16689 loop
16690 if (Suppress_Elaboration_Warnings (Ent)
16691 or else Elaboration_Checks_Suppressed (Ent))
16692 and then (Inst_Case or else No (Alias (Ent)))
16693 then
16694 return;
16695 end if;
16696
16697 -- Nothing to do for imported entities
16698
16699 if Is_Imported (Ent) then
16700 return;
16701 end if;
16702
16703 exit when Inst_Case or else No (Alias (Ent));
16704 Ent := Alias (Ent);
16705 end loop;
16706
16707 Decl := Unit_Declaration_Node (Ent);
16708
16709 if Nkind (Decl) = N_Subprogram_Body then
16710 Body_Acts_As_Spec := True;
16711
16712 elsif Nkind_In (Decl, N_Subprogram_Declaration,
16713 N_Subprogram_Body_Stub)
16714 or else Inst_Case
16715 then
16716 Body_Acts_As_Spec := False;
16717
16718 -- If we have none of an instantiation, subprogram body or subprogram
16719 -- declaration, or in the SPARK case, a variable reference, then
16720 -- it is not a case that we want to check. (One case is a call to a
16721 -- generic formal subprogram, where we do not want the check in the
16722 -- template).
16723
16724 else
16725 return;
16726 end if;
16727 end if;
16728
16729 E_Scope := Ent;
16730 loop
16731 if Elaboration_Checks_Suppressed (E_Scope)
16732 or else Suppress_Elaboration_Warnings (E_Scope)
16733 then
16734 Cunit_SC := True;
16735 end if;
16736
16737 -- Exit when we get to compilation unit, not counting subunits
16738
16739 exit when Is_Compilation_Unit (E_Scope)
16740 and then (Is_Child_Unit (E_Scope)
16741 or else Scope (E_Scope) = Standard_Standard);
16742
16743 pragma Assert (E_Scope /= Standard_Standard);
16744
16745 -- Move up a scope looking for compilation unit
16746
16747 E_Scope := Scope (E_Scope);
16748 end loop;
16749
16750 -- No checks needed for pure or preelaborated compilation units
16751
16752 if Is_Pure (E_Scope) or else Is_Preelaborated (E_Scope) then
16753 return;
16754 end if;
16755
16756 -- If the generic entity is within a deeper instance than we are, then
16757 -- either the instantiation to which we refer itself caused an ABE, in
16758 -- which case that will be handled separately, or else we know that the
16759 -- body we need appears as needed at the point of the instantiation.
16760 -- However, this assumption is only valid if we are in static mode.
16761
16762 if not Dynamic_Elaboration_Checks
16763 and then
16764 Instantiation_Depth (Sloc (Ent)) > Instantiation_Depth (Sloc (N))
16765 then
16766 return;
16767 end if;
16768
16769 -- Do not give a warning for a package with no body
16770
16771 if Ekind (Ent) = E_Generic_Package and then not Has_Generic_Body (N) then
16772 return;
16773 end if;
16774
16775 -- Case of entity is in same unit as call or instantiation. In the
16776 -- instantiation case, W_Scope may be different from E_Scope; we want
16777 -- the unit in which the instantiation occurs, since we're analyzing
16778 -- based on the expansion.
16779
16780 if W_Scope = C_Scope then
16781 if not Inter_Unit_Only then
16782 Check_Internal_Call (N, Ent, Outer_Scope, E);
16783 end if;
16784
16785 return;
16786 end if;
16787
16788 -- Case of entity is not in current unit (i.e. with'ed unit case)
16789
16790 -- We are only interested in such calls if the outer call was from
16791 -- elaboration code, or if we are in Dynamic_Elaboration_Checks mode.
16792
16793 if not From_Elab_Code and then not Dynamic_Elaboration_Checks then
16794 return;
16795 end if;
16796
16797 -- Nothing to do if some scope said that no checks were required
16798
16799 if Cunit_SC then
16800 return;
16801 end if;
16802
16803 -- Nothing to do for a generic instance, because a call to an instance
16804 -- cannot fail the elaboration check, because the body of the instance
16805 -- is always elaborated immediately after the spec.
16806
16807 if Call_To_Instance_From_Outside (Ent) then
16808 return;
16809 end if;
16810
16811 -- Nothing to do if subprogram with no separate spec. However, a call
16812 -- to Deep_Initialize may result in a call to a user-defined Initialize
16813 -- procedure, which imposes a body dependency. This happens only if the
16814 -- type is controlled and the Initialize procedure is not inherited.
16815
16816 if Body_Acts_As_Spec then
16817 if Is_TSS (Ent, TSS_Deep_Initialize) then
16818 declare
16819 Typ : constant Entity_Id := Etype (First_Formal (Ent));
16820 Init : Entity_Id;
16821
16822 begin
16823 if not Is_Controlled (Typ) then
16824 return;
16825 else
16826 Init := Find_Prim_Op (Typ, Name_Initialize);
16827
16828 if Comes_From_Source (Init) then
16829 Ent := Init;
16830 else
16831 return;
16832 end if;
16833 end if;
16834 end;
16835
16836 else
16837 return;
16838 end if;
16839 end if;
16840
16841 -- Check cases of internal units
16842
16843 Callee_Unit_Internal := In_Internal_Unit (E_Scope);
16844
16845 -- Do not give a warning if the with'ed unit is internal and this is
16846 -- the generic instantiation case (this saves a lot of hassle dealing
16847 -- with the Text_IO special child units)
16848
16849 if Callee_Unit_Internal and Inst_Case then
16850 return;
16851 end if;
16852
16853 if C_Scope = Standard_Standard then
16854 Caller_Unit_Internal := False;
16855 else
16856 Caller_Unit_Internal := In_Internal_Unit (C_Scope);
16857 end if;
16858
16859 -- Do not give a warning if the with'ed unit is internal and the caller
16860 -- is not internal (since the binder always elaborates internal units
16861 -- first).
16862
16863 if Callee_Unit_Internal and not Caller_Unit_Internal then
16864 return;
16865 end if;
16866
16867 -- For now, if debug flag -gnatdE is not set, do no checking for one
16868 -- internal unit withing another. This fixes the problem with the sgi
16869 -- build and storage errors. To be resolved later ???
16870
16871 if (Callee_Unit_Internal and Caller_Unit_Internal)
16872 and not Debug_Flag_EE
16873 then
16874 return;
16875 end if;
16876
16877 if Is_TSS (E, TSS_Deep_Initialize) then
16878 Ent := E;
16879 end if;
16880
16881 -- If the call is in an instance, and the called entity is not
16882 -- defined in the same instance, then the elaboration issue focuses
16883 -- around the unit containing the template, it is this unit that
16884 -- requires an Elaborate_All.
16885
16886 -- However, if we are doing dynamic elaboration, we need to chase the
16887 -- call in the usual manner.
16888
16889 -- We also need to chase the call in the usual manner if it is a call
16890 -- to a generic formal parameter, since that case was not handled as
16891 -- part of the processing of the template.
16892
16893 Inst_Caller := Instantiation (Get_Source_File_Index (Sloc (N)));
16894 Inst_Callee := Instantiation (Get_Source_File_Index (Sloc (Ent)));
16895
16896 if Inst_Caller = No_Location then
16897 Unit_Caller := No_Unit;
16898 else
16899 Unit_Caller := Get_Source_Unit (N);
16900 end if;
16901
16902 if Inst_Callee = No_Location then
16903 Unit_Callee := No_Unit;
16904 else
16905 Unit_Callee := Get_Source_Unit (Ent);
16906 end if;
16907
16908 if Unit_Caller /= No_Unit
16909 and then Unit_Callee /= Unit_Caller
16910 and then not Dynamic_Elaboration_Checks
16911 and then not Is_Call_Of_Generic_Formal (N)
16912 then
16913 E_Scope := Spec_Entity (Cunit_Entity (Unit_Caller));
16914
16915 -- If we don't get a spec entity, just ignore call. Not quite
16916 -- clear why this check is necessary. ???
16917
16918 if No (E_Scope) then
16919 return;
16920 end if;
16921
16922 -- Otherwise step to enclosing compilation unit
16923
16924 while not Is_Compilation_Unit (E_Scope) loop
16925 E_Scope := Scope (E_Scope);
16926 end loop;
16927
16928 -- For the case where N is not an instance, and is not a call within
16929 -- instance to other than a generic formal, we recompute E_Scope
16930 -- for the error message, since we do NOT want to go to the unit
16931 -- that has the ultimate declaration in the case of renaming and
16932 -- derivation and we also want to go to the generic unit in the
16933 -- case of an instance, and no further.
16934
16935 else
16936 -- Loop to carefully follow renamings and derivations one step
16937 -- outside the current unit, but not further.
16938
16939 if not (Inst_Case or Variable_Case)
16940 and then Present (Alias (Ent))
16941 then
16942 E_Scope := Alias (Ent);
16943 else
16944 E_Scope := Ent;
16945 end if;
16946
16947 loop
16948 while not Is_Compilation_Unit (E_Scope) loop
16949 E_Scope := Scope (E_Scope);
16950 end loop;
16951
16952 -- If E_Scope is the same as C_Scope, it means that there
16953 -- definitely was a local renaming or derivation, and we
16954 -- are not yet out of the current unit.
16955
16956 exit when E_Scope /= C_Scope;
16957 Ent := Alias (Ent);
16958 E_Scope := Ent;
16959
16960 -- If no alias, there could be a previous error, but not if we've
16961 -- already reached the outermost level (Standard).
16962
16963 if No (Ent) then
16964 return;
16965 end if;
16966 end loop;
16967 end if;
16968
16969 if Within_Elaborate_All (Current_Sem_Unit, E_Scope) then
16970 return;
16971 end if;
16972
16973 -- Determine whether the Default_Initial_Condition procedure of some
16974 -- type is being invoked.
16975
16976 Is_DIC := Ekind (Ent) = E_Procedure and then Is_DIC_Procedure (Ent);
16977
16978 -- Checks related to Default_Initial_Condition fall under the SPARK
16979 -- umbrella because this is a SPARK-specific annotation.
16980
16981 SPARK_Elab_Errors :=
16982 SPARK_Mode = On and (Is_DIC or Dynamic_Elaboration_Checks);
16983
16984 -- Now check if an Elaborate_All (or dynamic check) is needed
16985
16986 if (Elab_Info_Messages or Elab_Warnings or SPARK_Elab_Errors)
16987 and then Generate_Warnings
16988 and then not Suppress_Elaboration_Warnings (Ent)
16989 and then not Elaboration_Checks_Suppressed (Ent)
16990 and then not Suppress_Elaboration_Warnings (E_Scope)
16991 and then not Elaboration_Checks_Suppressed (E_Scope)
16992 then
16993 -- Instantiation case
16994
16995 if Inst_Case then
16996 if Comes_From_Source (Ent) and then SPARK_Elab_Errors then
16997 Error_Msg_NE
16998 ("instantiation of & during elaboration in SPARK", N, Ent);
16999 else
17000 Elab_Warning
17001 ("instantiation of & may raise Program_Error?l?",
17002 "info: instantiation of & during elaboration?$?", Ent);
17003 end if;
17004
17005 -- Indirect call case, info message only in static elaboration
17006 -- case, because the attribute reference itself cannot raise an
17007 -- exception. Note that SPARK does not permit indirect calls.
17008
17009 elsif Access_Case then
17010 Elab_Warning ("", "info: access to & during elaboration?$?", Ent);
17011
17012 -- Variable reference in SPARK mode
17013
17014 elsif Variable_Case then
17015 if Comes_From_Source (Ent) and then SPARK_Elab_Errors then
17016 Error_Msg_NE
17017 ("reference to & during elaboration in SPARK", N, Ent);
17018 end if;
17019
17020 -- Subprogram call case
17021
17022 else
17023 if Nkind (Name (N)) in N_Has_Entity
17024 and then Is_Init_Proc (Entity (Name (N)))
17025 and then Comes_From_Source (Ent)
17026 then
17027 Elab_Warning
17028 ("implicit call to & may raise Program_Error?l?",
17029 "info: implicit call to & during elaboration?$?",
17030 Ent);
17031
17032 elsif SPARK_Elab_Errors then
17033
17034 -- Emit a specialized error message when the elaboration of an
17035 -- object of a private type evaluates the expression of pragma
17036 -- Default_Initial_Condition. This prevents the internal name
17037 -- of the procedure from appearing in the error message.
17038
17039 if Is_DIC then
17040 Error_Msg_N
17041 ("call to Default_Initial_Condition during elaboration in "
17042 & "SPARK", N);
17043 else
17044 Error_Msg_NE
17045 ("call to & during elaboration in SPARK", N, Ent);
17046 end if;
17047
17048 else
17049 Elab_Warning
17050 ("call to & may raise Program_Error?l?",
17051 "info: call to & during elaboration?$?",
17052 Ent);
17053 end if;
17054 end if;
17055
17056 Error_Msg_Qual_Level := Nat'Last;
17057
17058 -- Case of Elaborate_All not present and required, for SPARK this
17059 -- is an error, so give an error message.
17060
17061 if SPARK_Elab_Errors then
17062 Error_Msg_NE -- CODEFIX
17063 ("\Elaborate_All pragma required for&", N, W_Scope);
17064
17065 -- Otherwise we generate an implicit pragma. For a subprogram
17066 -- instantiation, Elaborate is good enough, since no transitive
17067 -- call is possible at elaboration time in this case.
17068
17069 elsif Nkind (N) in N_Subprogram_Instantiation then
17070 Elab_Warning
17071 ("\missing pragma Elaborate for&?l?",
17072 "\implicit pragma Elaborate for& generated?$?",
17073 W_Scope);
17074
17075 -- For all other cases, we need an implicit Elaborate_All
17076
17077 else
17078 Elab_Warning
17079 ("\missing pragma Elaborate_All for&?l?",
17080 "\implicit pragma Elaborate_All for & generated?$?",
17081 W_Scope);
17082 end if;
17083
17084 Error_Msg_Qual_Level := 0;
17085
17086 -- Take into account the flags related to elaboration warning
17087 -- messages when enumerating the various calls involved. This
17088 -- ensures the proper pairing of the main warning and the
17089 -- clarification messages generated by Output_Calls.
17090
17091 Output_Calls (N, Check_Elab_Flag => True);
17092
17093 -- Set flag to prevent further warnings for same unit unless in
17094 -- All_Errors_Mode.
17095
17096 if not All_Errors_Mode and not Dynamic_Elaboration_Checks then
17097 Set_Suppress_Elaboration_Warnings (W_Scope);
17098 end if;
17099 end if;
17100
17101 -- Check for runtime elaboration check required
17102
17103 if Dynamic_Elaboration_Checks then
17104 if not Elaboration_Checks_Suppressed (Ent)
17105 and then not Elaboration_Checks_Suppressed (W_Scope)
17106 and then not Elaboration_Checks_Suppressed (E_Scope)
17107 and then not Cunit_SC
17108 then
17109 -- Runtime elaboration check required. Generate check of the
17110 -- elaboration Boolean for the unit containing the entity.
17111
17112 -- Note that for this case, we do check the real unit (the one
17113 -- from following renamings, since that is the issue).
17114
17115 -- Could this possibly miss a useless but required PE???
17116
17117 Insert_Elab_Check (N,
17118 Make_Attribute_Reference (Loc,
17119 Attribute_Name => Name_Elaborated,
17120 Prefix =>
17121 New_Occurrence_Of (Spec_Entity (E_Scope), Loc)));
17122
17123 -- Prevent duplicate elaboration checks on the same call, which
17124 -- can happen if the body enclosing the call appears itself in a
17125 -- call whose elaboration check is delayed.
17126
17127 if Nkind (N) in N_Subprogram_Call then
17128 Set_No_Elaboration_Check (N);
17129 end if;
17130 end if;
17131
17132 -- Case of static elaboration model
17133
17134 else
17135 -- Do not do anything if elaboration checks suppressed. Note that
17136 -- we check Ent here, not E, since we want the real entity for the
17137 -- body to see if checks are suppressed for it, not the dummy
17138 -- entry for renamings or derivations.
17139
17140 if Elaboration_Checks_Suppressed (Ent)
17141 or else Elaboration_Checks_Suppressed (E_Scope)
17142 or else Elaboration_Checks_Suppressed (W_Scope)
17143 then
17144 null;
17145
17146 -- Do not generate an Elaborate_All for finalization routines
17147 -- that perform partial clean up as part of initialization.
17148
17149 elsif In_Init_Proc and then Is_Finalization_Procedure (Ent) then
17150 null;
17151
17152 -- Here we need to generate an implicit elaborate all
17153
17154 else
17155 -- Generate Elaborate_All warning unless suppressed
17156
17157 if (Elab_Info_Messages and Generate_Warnings and not Inst_Case)
17158 and then not Suppress_Elaboration_Warnings (Ent)
17159 and then not Suppress_Elaboration_Warnings (E_Scope)
17160 and then not Suppress_Elaboration_Warnings (W_Scope)
17161 then
17162 Error_Msg_Node_2 := W_Scope;
17163 Error_Msg_NE
17164 ("info: call to& in elaboration code requires pragma "
17165 & "Elaborate_All on&?$?", N, E);
17166 end if;
17167
17168 -- Set indication for binder to generate Elaborate_All
17169
17170 Set_Elaboration_Constraint (N, E, W_Scope);
17171 end if;
17172 end if;
17173 end Check_A_Call;
17174
17175 -----------------------------
17176 -- Check_Bad_Instantiation --
17177 -----------------------------
17178
17179 procedure Check_Bad_Instantiation (N : Node_Id) is
17180 Ent : Entity_Id;
17181
17182 begin
17183 -- Nothing to do if we do not have an instantiation (happens in some
17184 -- error cases, and also in the formal package declaration case)
17185
17186 if Nkind (N) not in N_Generic_Instantiation then
17187 return;
17188
17189 -- Nothing to do if serious errors detected (avoid cascaded errors)
17190
17191 elsif Serious_Errors_Detected /= 0 then
17192 return;
17193
17194 -- Nothing to do if not in full analysis mode
17195
17196 elsif not Full_Analysis then
17197 return;
17198
17199 -- Nothing to do if inside a generic template
17200
17201 elsif Inside_A_Generic then
17202 return;
17203
17204 -- Nothing to do if a library level instantiation
17205
17206 elsif Nkind (Parent (N)) = N_Compilation_Unit then
17207 return;
17208
17209 -- Nothing to do if we are compiling a proper body for semantic
17210 -- purposes only. The generic body may be in another proper body.
17211
17212 elsif
17213 Nkind (Parent (Unit_Declaration_Node (Main_Unit_Entity))) = N_Subunit
17214 then
17215 return;
17216 end if;
17217
17218 Ent := Get_Generic_Entity (N);
17219
17220 -- The case we are interested in is when the generic spec is in the
17221 -- current declarative part
17222
17223 if not Same_Elaboration_Scope (Current_Scope, Scope (Ent))
17224 or else not In_Same_Extended_Unit (N, Ent)
17225 then
17226 return;
17227 end if;
17228
17229 -- If the generic entity is within a deeper instance than we are, then
17230 -- either the instantiation to which we refer itself caused an ABE, in
17231 -- which case that will be handled separately. Otherwise, we know that
17232 -- the body we need appears as needed at the point of the instantiation.
17233 -- If they are both at the same level but not within the same instance
17234 -- then the body of the generic will be in the earlier instance.
17235
17236 declare
17237 D1 : constant Nat := Instantiation_Depth (Sloc (Ent));
17238 D2 : constant Nat := Instantiation_Depth (Sloc (N));
17239
17240 begin
17241 if D1 > D2 then
17242 return;
17243
17244 elsif D1 = D2
17245 and then Is_Generic_Instance (Scope (Ent))
17246 and then not In_Open_Scopes (Scope (Ent))
17247 then
17248 return;
17249 end if;
17250 end;
17251
17252 -- Now we can proceed, if the entity being called has a completion,
17253 -- then we are definitely OK, since we have already seen the body.
17254
17255 if Has_Completion (Ent) then
17256 return;
17257 end if;
17258
17259 -- If there is no body, then nothing to do
17260
17261 if not Has_Generic_Body (N) then
17262 return;
17263 end if;
17264
17265 -- Here we definitely have a bad instantiation
17266
17267 Error_Msg_Warn := SPARK_Mode /= On;
17268 Error_Msg_NE ("cannot instantiate& before body seen<<", N, Ent);
17269 Error_Msg_N ("\Program_Error [<<", N);
17270
17271 Insert_Elab_Check (N);
17272 Set_Is_Known_Guaranteed_ABE (N);
17273 end Check_Bad_Instantiation;
17274
17275 ---------------------
17276 -- Check_Elab_Call --
17277 ---------------------
17278
17279 procedure Check_Elab_Call
17280 (N : Node_Id;
17281 Outer_Scope : Entity_Id := Empty;
17282 In_Init_Proc : Boolean := False)
17283 is
17284 Ent : Entity_Id;
17285 P : Node_Id;
17286
17287 begin
17288 pragma Assert (Legacy_Elaboration_Checks);
17289
17290 -- If the reference is not in the main unit, there is nothing to check.
17291 -- Elaboration call from units in the context of the main unit will lead
17292 -- to semantic dependencies when those units are compiled.
17293
17294 if not In_Extended_Main_Code_Unit (N) then
17295 return;
17296 end if;
17297
17298 -- For an entry call, check relevant restriction
17299
17300 if Nkind (N) = N_Entry_Call_Statement
17301 and then not In_Subprogram_Or_Concurrent_Unit
17302 then
17303 Check_Restriction (No_Entry_Calls_In_Elaboration_Code, N);
17304
17305 -- Nothing to do if this is not an expected type of reference (happens
17306 -- in some error conditions, and in some cases where rewriting occurs).
17307
17308 elsif Nkind (N) not in N_Subprogram_Call
17309 and then Nkind (N) /= N_Attribute_Reference
17310 and then (SPARK_Mode /= On
17311 or else Nkind (N) not in N_Has_Entity
17312 or else No (Entity (N))
17313 or else Ekind (Entity (N)) /= E_Variable)
17314 then
17315 return;
17316
17317 -- Nothing to do if this is a call already rewritten for elab checking.
17318 -- Such calls appear as the targets of If_Expressions.
17319
17320 -- This check MUST be wrong, it catches far too much
17321
17322 elsif Nkind (Parent (N)) = N_If_Expression then
17323 return;
17324
17325 -- Nothing to do if inside a generic template
17326
17327 elsif Inside_A_Generic
17328 and then No (Enclosing_Generic_Body (N))
17329 then
17330 return;
17331
17332 -- Nothing to do if call is being preanalyzed, as when within a
17333 -- pre/postcondition, a predicate, or an invariant.
17334
17335 elsif In_Spec_Expression then
17336 return;
17337 end if;
17338
17339 -- Nothing to do if this is a call to a postcondition, which is always
17340 -- within a subprogram body, even though the current scope may be the
17341 -- enclosing scope of the subprogram.
17342
17343 if Nkind (N) = N_Procedure_Call_Statement
17344 and then Is_Entity_Name (Name (N))
17345 and then Chars (Entity (Name (N))) = Name_uPostconditions
17346 then
17347 return;
17348 end if;
17349
17350 -- Here we have a reference at elaboration time that must be checked
17351
17352 if Debug_Flag_Underscore_LL then
17353 Write_Str (" Check_Elab_Ref: ");
17354
17355 if Nkind (N) = N_Attribute_Reference then
17356 if not Is_Entity_Name (Prefix (N)) then
17357 Write_Str ("<<not entity name>>");
17358 else
17359 Write_Name (Chars (Entity (Prefix (N))));
17360 end if;
17361
17362 Write_Str ("'Access");
17363
17364 elsif No (Name (N)) or else not Is_Entity_Name (Name (N)) then
17365 Write_Str ("<<not entity name>> ");
17366
17367 else
17368 Write_Name (Chars (Entity (Name (N))));
17369 end if;
17370
17371 Write_Str (" reference at ");
17372 Write_Location (Sloc (N));
17373 Write_Eol;
17374 end if;
17375
17376 -- Climb up the tree to make sure we are not inside default expression
17377 -- of a parameter specification or a record component, since in both
17378 -- these cases, we will be doing the actual reference later, not now,
17379 -- and it is at the time of the actual reference (statically speaking)
17380 -- that we must do our static check, not at the time of its initial
17381 -- analysis).
17382
17383 -- However, we have to check references within component definitions
17384 -- (e.g. a function call that determines an array component bound),
17385 -- so we terminate the loop in that case.
17386
17387 P := Parent (N);
17388 while Present (P) loop
17389 if Nkind_In (P, N_Parameter_Specification,
17390 N_Component_Declaration)
17391 then
17392 return;
17393
17394 -- The reference occurs within the constraint of a component,
17395 -- so it must be checked.
17396
17397 elsif Nkind (P) = N_Component_Definition then
17398 exit;
17399
17400 else
17401 P := Parent (P);
17402 end if;
17403 end loop;
17404
17405 -- Stuff that happens only at the outer level
17406
17407 if No (Outer_Scope) then
17408 Elab_Visited.Set_Last (0);
17409
17410 -- Nothing to do if current scope is Standard (this is a bit odd, but
17411 -- it happens in the case of generic instantiations).
17412
17413 C_Scope := Current_Scope;
17414
17415 if C_Scope = Standard_Standard then
17416 return;
17417 end if;
17418
17419 -- First case, we are in elaboration code
17420
17421 From_Elab_Code := not In_Subprogram_Or_Concurrent_Unit;
17422
17423 if From_Elab_Code then
17424
17425 -- Complain if ref that comes from source in preelaborated unit
17426 -- and we are not inside a subprogram (i.e. we are in elab code).
17427
17428 if Comes_From_Source (N)
17429 and then In_Preelaborated_Unit
17430 and then not In_Inlined_Body
17431 and then Nkind (N) /= N_Attribute_Reference
17432 then
17433 -- This is a warning in GNAT mode allowing such calls to be
17434 -- used in the predefined library with appropriate care.
17435
17436 Error_Msg_Warn := GNAT_Mode;
17437 Error_Msg_N
17438 ("<<non-static call not allowed in preelaborated unit", N);
17439 return;
17440 end if;
17441
17442 -- Second case, we are inside a subprogram or concurrent unit, which
17443 -- means we are not in elaboration code.
17444
17445 else
17446 -- In this case, the issue is whether we are inside the
17447 -- declarative part of the unit in which we live, or inside its
17448 -- statements. In the latter case, there is no issue of ABE calls
17449 -- at this level (a call from outside to the unit in which we live
17450 -- might cause an ABE, but that will be detected when we analyze
17451 -- that outer level call, as it recurses into the called unit).
17452
17453 -- Climb up the tree, doing this test, and also testing for being
17454 -- inside a default expression, which, as discussed above, is not
17455 -- checked at this stage.
17456
17457 declare
17458 P : Node_Id;
17459 L : List_Id;
17460
17461 begin
17462 P := N;
17463 loop
17464 -- If we find a parentless subtree, it seems safe to assume
17465 -- that we are not in a declarative part and that no
17466 -- checking is required.
17467
17468 if No (P) then
17469 return;
17470 end if;
17471
17472 if Is_List_Member (P) then
17473 L := List_Containing (P);
17474 P := Parent (L);
17475 else
17476 L := No_List;
17477 P := Parent (P);
17478 end if;
17479
17480 exit when Nkind (P) = N_Subunit;
17481
17482 -- Filter out case of default expressions, where we do not
17483 -- do the check at this stage.
17484
17485 if Nkind_In (P, N_Parameter_Specification,
17486 N_Component_Declaration)
17487 then
17488 return;
17489 end if;
17490
17491 -- A protected body has no elaboration code and contains
17492 -- only other bodies.
17493
17494 if Nkind (P) = N_Protected_Body then
17495 return;
17496
17497 elsif Nkind_In (P, N_Subprogram_Body,
17498 N_Task_Body,
17499 N_Block_Statement,
17500 N_Entry_Body)
17501 then
17502 if L = Declarations (P) then
17503 exit;
17504
17505 -- We are not in elaboration code, but we are doing
17506 -- dynamic elaboration checks, in this case, we still
17507 -- need to do the reference, since the subprogram we are
17508 -- in could be called from another unit, also in dynamic
17509 -- elaboration check mode, at elaboration time.
17510
17511 elsif Dynamic_Elaboration_Checks then
17512
17513 -- We provide a debug flag to disable this check. That
17514 -- way we have an easy work around for regressions
17515 -- that are caused by this new check. This debug flag
17516 -- can be removed later.
17517
17518 if Debug_Flag_DD then
17519 return;
17520 end if;
17521
17522 -- Do the check in this case
17523
17524 exit;
17525
17526 elsif Nkind (P) = N_Task_Body then
17527
17528 -- The check is deferred until Check_Task_Activation
17529 -- but we need to capture local suppress pragmas
17530 -- that may inhibit checks on this call.
17531
17532 Ent := Get_Referenced_Ent (N);
17533
17534 if No (Ent) then
17535 return;
17536
17537 elsif Elaboration_Checks_Suppressed (Current_Scope)
17538 or else Elaboration_Checks_Suppressed (Ent)
17539 or else Elaboration_Checks_Suppressed (Scope (Ent))
17540 then
17541 if Nkind (N) in N_Subprogram_Call then
17542 Set_No_Elaboration_Check (N);
17543 end if;
17544 end if;
17545
17546 return;
17547
17548 -- Static model, call is not in elaboration code, we
17549 -- never need to worry, because in the static model the
17550 -- top-level caller always takes care of things.
17551
17552 else
17553 return;
17554 end if;
17555 end if;
17556 end loop;
17557 end;
17558 end if;
17559 end if;
17560
17561 Ent := Get_Referenced_Ent (N);
17562
17563 if No (Ent) then
17564 return;
17565 end if;
17566
17567 -- Determine whether a prior call to the same subprogram was already
17568 -- examined within the same context. If this is the case, then there is
17569 -- no need to proceed with the various warnings and checks because the
17570 -- work was already done for the previous call.
17571
17572 declare
17573 Self : constant Visited_Element :=
17574 (Subp_Id => Ent, Context => Parent (N));
17575
17576 begin
17577 for Index in 1 .. Elab_Visited.Last loop
17578 if Self = Elab_Visited.Table (Index) then
17579 return;
17580 end if;
17581 end loop;
17582 end;
17583
17584 -- See if we need to analyze this reference. We analyze it if either of
17585 -- the following conditions is met:
17586
17587 -- It is an inner level call (since in this case it was triggered
17588 -- by an outer level call from elaboration code), but only if the
17589 -- call is within the scope of the original outer level call.
17590
17591 -- It is an outer level reference from elaboration code, or a call to
17592 -- an entity is in the same elaboration scope.
17593
17594 -- And in these cases, we will check both inter-unit calls and
17595 -- intra-unit (within a single unit) calls.
17596
17597 C_Scope := Current_Scope;
17598
17599 -- If not outer level reference, then we follow it if it is within the
17600 -- original scope of the outer reference.
17601
17602 if Present (Outer_Scope)
17603 and then Within (Scope (Ent), Outer_Scope)
17604 then
17605 Set_C_Scope;
17606 Check_A_Call
17607 (N => N,
17608 E => Ent,
17609 Outer_Scope => Outer_Scope,
17610 Inter_Unit_Only => False,
17611 In_Init_Proc => In_Init_Proc);
17612
17613 -- Nothing to do if elaboration checks suppressed for this scope.
17614 -- However, an interesting exception, the fact that elaboration checks
17615 -- are suppressed within an instance (because we can trace the body when
17616 -- we process the template) does not extend to calls to generic formal
17617 -- subprograms.
17618
17619 elsif Elaboration_Checks_Suppressed (Current_Scope)
17620 and then not Is_Call_Of_Generic_Formal (N)
17621 then
17622 null;
17623
17624 elsif From_Elab_Code then
17625 Set_C_Scope;
17626 Check_A_Call (N, Ent, Standard_Standard, Inter_Unit_Only => False);
17627
17628 elsif Same_Elaboration_Scope (C_Scope, Scope (Ent)) then
17629 Set_C_Scope;
17630 Check_A_Call (N, Ent, Scope (Ent), Inter_Unit_Only => False);
17631
17632 -- If none of those cases holds, but Dynamic_Elaboration_Checks mode
17633 -- is set, then we will do the check, but only in the inter-unit case
17634 -- (this is to accommodate unguarded elaboration calls from other units
17635 -- in which this same mode is set). We don't want warnings in this case,
17636 -- it would generate warnings having nothing to do with elaboration.
17637
17638 elsif Dynamic_Elaboration_Checks then
17639 Set_C_Scope;
17640 Check_A_Call
17641 (N,
17642 Ent,
17643 Standard_Standard,
17644 Inter_Unit_Only => True,
17645 Generate_Warnings => False);
17646
17647 -- Otherwise nothing to do
17648
17649 else
17650 return;
17651 end if;
17652
17653 -- A call to an Init_Proc in elaboration code may bring additional
17654 -- dependencies, if some of the record components thereof have
17655 -- initializations that are function calls that come from source. We
17656 -- treat the current node as a call to each of these functions, to check
17657 -- their elaboration impact.
17658
17659 if Is_Init_Proc (Ent) and then From_Elab_Code then
17660 Process_Init_Proc : declare
17661 Unit_Decl : constant Node_Id := Unit_Declaration_Node (Ent);
17662
17663 function Check_Init_Call (Nod : Node_Id) return Traverse_Result;
17664 -- Find subprogram calls within body of Init_Proc for Traverse
17665 -- instantiation below.
17666
17667 procedure Traverse_Body is new Traverse_Proc (Check_Init_Call);
17668 -- Traversal procedure to find all calls with body of Init_Proc
17669
17670 ---------------------
17671 -- Check_Init_Call --
17672 ---------------------
17673
17674 function Check_Init_Call (Nod : Node_Id) return Traverse_Result is
17675 Func : Entity_Id;
17676
17677 begin
17678 if Nkind (Nod) in N_Subprogram_Call
17679 and then Is_Entity_Name (Name (Nod))
17680 then
17681 Func := Entity (Name (Nod));
17682
17683 if Comes_From_Source (Func) then
17684 Check_A_Call
17685 (N, Func, Standard_Standard, Inter_Unit_Only => True);
17686 end if;
17687
17688 return OK;
17689
17690 else
17691 return OK;
17692 end if;
17693 end Check_Init_Call;
17694
17695 -- Start of processing for Process_Init_Proc
17696
17697 begin
17698 if Nkind (Unit_Decl) = N_Subprogram_Body then
17699 Traverse_Body (Handled_Statement_Sequence (Unit_Decl));
17700 end if;
17701 end Process_Init_Proc;
17702 end if;
17703 end Check_Elab_Call;
17704
17705 -----------------------
17706 -- Check_Elab_Assign --
17707 -----------------------
17708
17709 procedure Check_Elab_Assign (N : Node_Id) is
17710 Ent : Entity_Id;
17711 Scop : Entity_Id;
17712
17713 Pkg_Spec : Entity_Id;
17714 Pkg_Body : Entity_Id;
17715
17716 begin
17717 pragma Assert (Legacy_Elaboration_Checks);
17718
17719 -- For record or array component, check prefix. If it is an access type,
17720 -- then there is nothing to do (we do not know what is being assigned),
17721 -- but otherwise this is an assignment to the prefix.
17722
17723 if Nkind_In (N, N_Indexed_Component,
17724 N_Selected_Component,
17725 N_Slice)
17726 then
17727 if not Is_Access_Type (Etype (Prefix (N))) then
17728 Check_Elab_Assign (Prefix (N));
17729 end if;
17730
17731 return;
17732 end if;
17733
17734 -- For type conversion, check expression
17735
17736 if Nkind (N) = N_Type_Conversion then
17737 Check_Elab_Assign (Expression (N));
17738 return;
17739 end if;
17740
17741 -- Nothing to do if this is not an entity reference otherwise get entity
17742
17743 if Is_Entity_Name (N) then
17744 Ent := Entity (N);
17745 else
17746 return;
17747 end if;
17748
17749 -- What we are looking for is a reference in the body of a package that
17750 -- modifies a variable declared in the visible part of the package spec.
17751
17752 if Present (Ent)
17753 and then Comes_From_Source (N)
17754 and then not Suppress_Elaboration_Warnings (Ent)
17755 and then Ekind (Ent) = E_Variable
17756 and then not In_Private_Part (Ent)
17757 and then Is_Library_Level_Entity (Ent)
17758 then
17759 Scop := Current_Scope;
17760 loop
17761 if No (Scop) or else Scop = Standard_Standard then
17762 return;
17763 elsif Ekind (Scop) = E_Package
17764 and then Is_Compilation_Unit (Scop)
17765 then
17766 exit;
17767 else
17768 Scop := Scope (Scop);
17769 end if;
17770 end loop;
17771
17772 -- Here Scop points to the containing library package
17773
17774 Pkg_Spec := Scop;
17775 Pkg_Body := Body_Entity (Pkg_Spec);
17776
17777 -- All OK if the package has an Elaborate_Body pragma
17778
17779 if Has_Pragma_Elaborate_Body (Scop) then
17780 return;
17781 end if;
17782
17783 -- OK if entity being modified is not in containing package spec
17784
17785 if not In_Same_Source_Unit (Scop, Ent) then
17786 return;
17787 end if;
17788
17789 -- All OK if entity appears in generic package or generic instance.
17790 -- We just get too messed up trying to give proper warnings in the
17791 -- presence of generics. Better no message than a junk one.
17792
17793 Scop := Scope (Ent);
17794 while Present (Scop) and then Scop /= Pkg_Spec loop
17795 if Ekind (Scop) = E_Generic_Package then
17796 return;
17797 elsif Ekind (Scop) = E_Package
17798 and then Is_Generic_Instance (Scop)
17799 then
17800 return;
17801 end if;
17802
17803 Scop := Scope (Scop);
17804 end loop;
17805
17806 -- All OK if in task, don't issue warnings there
17807
17808 if In_Task_Activation then
17809 return;
17810 end if;
17811
17812 -- OK if no package body
17813
17814 if No (Pkg_Body) then
17815 return;
17816 end if;
17817
17818 -- OK if reference is not in package body
17819
17820 if not In_Same_Source_Unit (Pkg_Body, N) then
17821 return;
17822 end if;
17823
17824 -- OK if package body has no handled statement sequence
17825
17826 declare
17827 HSS : constant Node_Id :=
17828 Handled_Statement_Sequence (Declaration_Node (Pkg_Body));
17829 begin
17830 if No (HSS) or else not Comes_From_Source (HSS) then
17831 return;
17832 end if;
17833 end;
17834
17835 -- We definitely have a case of a modification of an entity in
17836 -- the package spec from the elaboration code of the package body.
17837 -- We may not give the warning (because there are some additional
17838 -- checks to avoid too many false positives), but it would be a good
17839 -- idea for the binder to try to keep the body elaboration close to
17840 -- the spec elaboration.
17841
17842 Set_Elaborate_Body_Desirable (Pkg_Spec);
17843
17844 -- All OK in gnat mode (we know what we are doing)
17845
17846 if GNAT_Mode then
17847 return;
17848 end if;
17849
17850 -- All OK if all warnings suppressed
17851
17852 if Warning_Mode = Suppress then
17853 return;
17854 end if;
17855
17856 -- All OK if elaboration checks suppressed for entity
17857
17858 if Checks_May_Be_Suppressed (Ent)
17859 and then Is_Check_Suppressed (Ent, Elaboration_Check)
17860 then
17861 return;
17862 end if;
17863
17864 -- OK if the entity is initialized. Note that the No_Initialization
17865 -- flag usually means that the initialization has been rewritten into
17866 -- assignments, but that still counts for us.
17867
17868 declare
17869 Decl : constant Node_Id := Declaration_Node (Ent);
17870 begin
17871 if Nkind (Decl) = N_Object_Declaration
17872 and then (Present (Expression (Decl))
17873 or else No_Initialization (Decl))
17874 then
17875 return;
17876 end if;
17877 end;
17878
17879 -- Here is where we give the warning
17880
17881 -- All OK if warnings suppressed on the entity
17882
17883 if not Has_Warnings_Off (Ent) then
17884 Error_Msg_Sloc := Sloc (Ent);
17885
17886 Error_Msg_NE
17887 ("??& can be accessed by clients before this initialization",
17888 N, Ent);
17889 Error_Msg_NE
17890 ("\??add Elaborate_Body to spec to ensure & is initialized",
17891 N, Ent);
17892 end if;
17893
17894 if not All_Errors_Mode then
17895 Set_Suppress_Elaboration_Warnings (Ent);
17896 end if;
17897 end if;
17898 end Check_Elab_Assign;
17899
17900 ----------------------
17901 -- Check_Elab_Calls --
17902 ----------------------
17903
17904 -- WARNING: This routine manages SPARK regions
17905
17906 procedure Check_Elab_Calls is
17907 Saved_SM : SPARK_Mode_Type;
17908 Saved_SMP : Node_Id;
17909
17910 begin
17911 pragma Assert (Legacy_Elaboration_Checks);
17912
17913 -- If expansion is disabled, do not generate any checks, unless we
17914 -- are in GNATprove mode, so that errors are issued in GNATprove for
17915 -- violations of static elaboration rules in SPARK code. Also skip
17916 -- checks if any subunits are missing because in either case we lack the
17917 -- full information that we need, and no object file will be created in
17918 -- any case.
17919
17920 if (not Expander_Active and not GNATprove_Mode)
17921 or else Is_Generic_Unit (Cunit_Entity (Main_Unit))
17922 or else Subunits_Missing
17923 then
17924 return;
17925 end if;
17926
17927 -- Skip delayed calls if we had any errors
17928
17929 if Serious_Errors_Detected = 0 then
17930 Delaying_Elab_Checks := False;
17931 Expander_Mode_Save_And_Set (True);
17932
17933 for J in Delay_Check.First .. Delay_Check.Last loop
17934 Push_Scope (Delay_Check.Table (J).Curscop);
17935 From_Elab_Code := Delay_Check.Table (J).From_Elab_Code;
17936 In_Task_Activation := Delay_Check.Table (J).In_Task_Activation;
17937
17938 Saved_SM := SPARK_Mode;
17939 Saved_SMP := SPARK_Mode_Pragma;
17940
17941 -- Set appropriate value of SPARK_Mode
17942
17943 if Delay_Check.Table (J).From_SPARK_Code then
17944 SPARK_Mode := On;
17945 end if;
17946
17947 Check_Internal_Call_Continue
17948 (N => Delay_Check.Table (J).N,
17949 E => Delay_Check.Table (J).E,
17950 Outer_Scope => Delay_Check.Table (J).Outer_Scope,
17951 Orig_Ent => Delay_Check.Table (J).Orig_Ent);
17952
17953 Restore_SPARK_Mode (Saved_SM, Saved_SMP);
17954 Pop_Scope;
17955 end loop;
17956
17957 -- Set Delaying_Elab_Checks back on for next main compilation
17958
17959 Expander_Mode_Restore;
17960 Delaying_Elab_Checks := True;
17961 end if;
17962 end Check_Elab_Calls;
17963
17964 ------------------------------
17965 -- Check_Elab_Instantiation --
17966 ------------------------------
17967
17968 procedure Check_Elab_Instantiation
17969 (N : Node_Id;
17970 Outer_Scope : Entity_Id := Empty)
17971 is
17972 Ent : Entity_Id;
17973
17974 begin
17975 pragma Assert (Legacy_Elaboration_Checks);
17976
17977 -- Check for and deal with bad instantiation case. There is some
17978 -- duplicated code here, but we will worry about this later ???
17979
17980 Check_Bad_Instantiation (N);
17981
17982 if Is_Known_Guaranteed_ABE (N) then
17983 return;
17984 end if;
17985
17986 -- Nothing to do if we do not have an instantiation (happens in some
17987 -- error cases, and also in the formal package declaration case)
17988
17989 if Nkind (N) not in N_Generic_Instantiation then
17990 return;
17991 end if;
17992
17993 -- Nothing to do if inside a generic template
17994
17995 if Inside_A_Generic then
17996 return;
17997 end if;
17998
17999 -- Nothing to do if the instantiation is not in the main unit
18000
18001 if not In_Extended_Main_Code_Unit (N) then
18002 return;
18003 end if;
18004
18005 Ent := Get_Generic_Entity (N);
18006 From_Elab_Code := not In_Subprogram_Or_Concurrent_Unit;
18007
18008 -- See if we need to analyze this instantiation. We analyze it if
18009 -- either of the following conditions is met:
18010
18011 -- It is an inner level instantiation (since in this case it was
18012 -- triggered by an outer level call from elaboration code), but
18013 -- only if the instantiation is within the scope of the original
18014 -- outer level call.
18015
18016 -- It is an outer level instantiation from elaboration code, or the
18017 -- instantiated entity is in the same elaboration scope.
18018
18019 -- And in these cases, we will check both the inter-unit case and
18020 -- the intra-unit (within a single unit) case.
18021
18022 C_Scope := Current_Scope;
18023
18024 if Present (Outer_Scope) and then Within (Scope (Ent), Outer_Scope) then
18025 Set_C_Scope;
18026 Check_A_Call (N, Ent, Outer_Scope, Inter_Unit_Only => False);
18027
18028 elsif From_Elab_Code then
18029 Set_C_Scope;
18030 Check_A_Call (N, Ent, Standard_Standard, Inter_Unit_Only => False);
18031
18032 elsif Same_Elaboration_Scope (C_Scope, Scope (Ent)) then
18033 Set_C_Scope;
18034 Check_A_Call (N, Ent, Scope (Ent), Inter_Unit_Only => False);
18035
18036 -- If none of those cases holds, but Dynamic_Elaboration_Checks mode is
18037 -- set, then we will do the check, but only in the inter-unit case (this
18038 -- is to accommodate unguarded elaboration calls from other units in
18039 -- which this same mode is set). We inhibit warnings in this case, since
18040 -- this instantiation is not occurring in elaboration code.
18041
18042 elsif Dynamic_Elaboration_Checks then
18043 Set_C_Scope;
18044 Check_A_Call
18045 (N,
18046 Ent,
18047 Standard_Standard,
18048 Inter_Unit_Only => True,
18049 Generate_Warnings => False);
18050
18051 else
18052 return;
18053 end if;
18054 end Check_Elab_Instantiation;
18055
18056 -------------------------
18057 -- Check_Internal_Call --
18058 -------------------------
18059
18060 procedure Check_Internal_Call
18061 (N : Node_Id;
18062 E : Entity_Id;
18063 Outer_Scope : Entity_Id;
18064 Orig_Ent : Entity_Id)
18065 is
18066 function Within_Initial_Condition (Call : Node_Id) return Boolean;
18067 -- Determine whether call Call occurs within pragma Initial_Condition or
18068 -- pragma Check with check_kind set to Initial_Condition.
18069
18070 ------------------------------
18071 -- Within_Initial_Condition --
18072 ------------------------------
18073
18074 function Within_Initial_Condition (Call : Node_Id) return Boolean is
18075 Args : List_Id;
18076 Nam : Name_Id;
18077 Par : Node_Id;
18078
18079 begin
18080 -- Traverse the parent chain looking for an enclosing pragma
18081
18082 Par := Call;
18083 while Present (Par) loop
18084 if Nkind (Par) = N_Pragma then
18085 Nam := Pragma_Name (Par);
18086
18087 -- Pragma Initial_Condition appears in its alternative from as
18088 -- Check (Initial_Condition, ...).
18089
18090 if Nam = Name_Check then
18091 Args := Pragma_Argument_Associations (Par);
18092
18093 -- Pragma Check should have at least two arguments
18094
18095 pragma Assert (Present (Args));
18096
18097 return
18098 Chars (Expression (First (Args))) = Name_Initial_Condition;
18099
18100 -- Direct match
18101
18102 elsif Nam = Name_Initial_Condition then
18103 return True;
18104
18105 -- Since pragmas are never nested within other pragmas, stop
18106 -- the traversal.
18107
18108 else
18109 return False;
18110 end if;
18111
18112 -- Prevent the search from going too far
18113
18114 elsif Is_Body_Or_Package_Declaration (Par) then
18115 exit;
18116 end if;
18117
18118 Par := Parent (Par);
18119
18120 -- If assertions are not enabled, the check pragma is rewritten
18121 -- as an if_statement in sem_prag, to generate various warnings
18122 -- on boolean expressions. Retrieve the original pragma.
18123
18124 if Nkind (Original_Node (Par)) = N_Pragma then
18125 Par := Original_Node (Par);
18126 end if;
18127 end loop;
18128
18129 return False;
18130 end Within_Initial_Condition;
18131
18132 -- Local variables
18133
18134 Inst_Case : constant Boolean := Nkind (N) in N_Generic_Instantiation;
18135
18136 -- Start of processing for Check_Internal_Call
18137
18138 begin
18139 -- For P'Access, we want to warn if the -gnatw.f switch is set, and the
18140 -- node comes from source.
18141
18142 if Nkind (N) = N_Attribute_Reference
18143 and then ((not Warn_On_Elab_Access and then not Debug_Flag_Dot_O)
18144 or else not Comes_From_Source (N))
18145 then
18146 return;
18147
18148 -- If not function or procedure call, instantiation, or 'Access, then
18149 -- ignore call (this happens in some error cases and rewriting cases).
18150
18151 elsif not Nkind_In (N, N_Attribute_Reference,
18152 N_Function_Call,
18153 N_Procedure_Call_Statement)
18154 and then not Inst_Case
18155 then
18156 return;
18157
18158 -- Nothing to do if this is a call or instantiation that has already
18159 -- been found to be a sure ABE.
18160
18161 elsif Nkind (N) /= N_Attribute_Reference
18162 and then Is_Known_Guaranteed_ABE (N)
18163 then
18164 return;
18165
18166 -- Nothing to do if errors already detected (avoid cascaded errors)
18167
18168 elsif Serious_Errors_Detected /= 0 then
18169 return;
18170
18171 -- Nothing to do if not in full analysis mode
18172
18173 elsif not Full_Analysis then
18174 return;
18175
18176 -- Nothing to do if analyzing in special spec-expression mode, since the
18177 -- call is not actually being made at this time.
18178
18179 elsif In_Spec_Expression then
18180 return;
18181
18182 -- Nothing to do for call to intrinsic subprogram
18183
18184 elsif Is_Intrinsic_Subprogram (E) then
18185 return;
18186
18187 -- Nothing to do if call is within a generic unit
18188
18189 elsif Inside_A_Generic then
18190 return;
18191
18192 -- Nothing to do when the call appears within pragma Initial_Condition.
18193 -- The pragma is part of the elaboration statements of a package body
18194 -- and may only call external subprograms or subprograms whose body is
18195 -- already available.
18196
18197 elsif Within_Initial_Condition (N) then
18198 return;
18199 end if;
18200
18201 -- Delay this call if we are still delaying calls
18202
18203 if Delaying_Elab_Checks then
18204 Delay_Check.Append
18205 ((N => N,
18206 E => E,
18207 Orig_Ent => Orig_Ent,
18208 Curscop => Current_Scope,
18209 Outer_Scope => Outer_Scope,
18210 From_Elab_Code => From_Elab_Code,
18211 In_Task_Activation => In_Task_Activation,
18212 From_SPARK_Code => SPARK_Mode = On));
18213 return;
18214
18215 -- Otherwise, call phase 2 continuation right now
18216
18217 else
18218 Check_Internal_Call_Continue (N, E, Outer_Scope, Orig_Ent);
18219 end if;
18220 end Check_Internal_Call;
18221
18222 ----------------------------------
18223 -- Check_Internal_Call_Continue --
18224 ----------------------------------
18225
18226 procedure Check_Internal_Call_Continue
18227 (N : Node_Id;
18228 E : Entity_Id;
18229 Outer_Scope : Entity_Id;
18230 Orig_Ent : Entity_Id)
18231 is
18232 function Find_Elab_Reference (N : Node_Id) return Traverse_Result;
18233 -- Function applied to each node as we traverse the body. Checks for
18234 -- call or entity reference that needs checking, and if so checks it.
18235 -- Always returns OK, so entire tree is traversed, except that as
18236 -- described below subprogram bodies are skipped for now.
18237
18238 procedure Traverse is new Atree.Traverse_Proc (Find_Elab_Reference);
18239 -- Traverse procedure using above Find_Elab_Reference function
18240
18241 -------------------------
18242 -- Find_Elab_Reference --
18243 -------------------------
18244
18245 function Find_Elab_Reference (N : Node_Id) return Traverse_Result is
18246 Actual : Node_Id;
18247
18248 begin
18249 -- If user has specified that there are no entry calls in elaboration
18250 -- code, do not trace past an accept statement, because the rendez-
18251 -- vous will happen after elaboration.
18252
18253 if Nkind_In (Original_Node (N), N_Accept_Statement,
18254 N_Selective_Accept)
18255 and then Restriction_Active (No_Entry_Calls_In_Elaboration_Code)
18256 then
18257 return Abandon;
18258
18259 -- If we have a function call, check it
18260
18261 elsif Nkind (N) = N_Function_Call then
18262 Check_Elab_Call (N, Outer_Scope);
18263 return OK;
18264
18265 -- If we have a procedure call, check the call, and also check
18266 -- arguments that are assignments (OUT or IN OUT mode formals).
18267
18268 elsif Nkind (N) = N_Procedure_Call_Statement then
18269 Check_Elab_Call (N, Outer_Scope, In_Init_Proc => Is_Init_Proc (E));
18270
18271 Actual := First_Actual (N);
18272 while Present (Actual) loop
18273 if Known_To_Be_Assigned (Actual) then
18274 Check_Elab_Assign (Actual);
18275 end if;
18276
18277 Next_Actual (Actual);
18278 end loop;
18279
18280 return OK;
18281
18282 -- If we have an access attribute for a subprogram, check it.
18283 -- Suppress this behavior under debug flag.
18284
18285 elsif not Debug_Flag_Dot_UU
18286 and then Nkind (N) = N_Attribute_Reference
18287 and then Nam_In (Attribute_Name (N), Name_Access,
18288 Name_Unrestricted_Access)
18289 and then Is_Entity_Name (Prefix (N))
18290 and then Is_Subprogram (Entity (Prefix (N)))
18291 then
18292 Check_Elab_Call (N, Outer_Scope);
18293 return OK;
18294
18295 -- In SPARK mode, if we have an entity reference to a variable, then
18296 -- check it. For now we consider any reference.
18297
18298 elsif SPARK_Mode = On
18299 and then Nkind (N) in N_Has_Entity
18300 and then Present (Entity (N))
18301 and then Ekind (Entity (N)) = E_Variable
18302 then
18303 Check_Elab_Call (N, Outer_Scope);
18304 return OK;
18305
18306 -- If we have a generic instantiation, check it
18307
18308 elsif Nkind (N) in N_Generic_Instantiation then
18309 Check_Elab_Instantiation (N, Outer_Scope);
18310 return OK;
18311
18312 -- Skip subprogram bodies that come from source (wait for call to
18313 -- analyze these). The reason for the come from source test is to
18314 -- avoid catching task bodies.
18315
18316 -- For task bodies, we should really avoid these too, waiting for the
18317 -- task activation, but that's too much trouble to catch for now, so
18318 -- we go in unconditionally. This is not so terrible, it means the
18319 -- error backtrace is not quite complete, and we are too eager to
18320 -- scan bodies of tasks that are unused, but this is hardly very
18321 -- significant.
18322
18323 elsif Nkind (N) = N_Subprogram_Body
18324 and then Comes_From_Source (N)
18325 then
18326 return Skip;
18327
18328 elsif Nkind (N) = N_Assignment_Statement
18329 and then Comes_From_Source (N)
18330 then
18331 Check_Elab_Assign (Name (N));
18332 return OK;
18333
18334 else
18335 return OK;
18336 end if;
18337 end Find_Elab_Reference;
18338
18339 Inst_Case : constant Boolean := Is_Generic_Unit (E);
18340 Loc : constant Source_Ptr := Sloc (N);
18341
18342 Ebody : Entity_Id;
18343 Sbody : Node_Id;
18344
18345 -- Start of processing for Check_Internal_Call_Continue
18346
18347 begin
18348 -- Save outer level call if at outer level
18349
18350 if Elab_Call.Last = 0 then
18351 Outer_Level_Sloc := Loc;
18352 end if;
18353
18354 -- If the call is to a function that renames a literal, no check needed
18355
18356 if Ekind (E) = E_Enumeration_Literal then
18357 return;
18358 end if;
18359
18360 -- Register the subprogram as examined within this particular context.
18361 -- This ensures that calls to the same subprogram but in different
18362 -- contexts receive warnings and checks of their own since the calls
18363 -- may be reached through different flow paths.
18364
18365 Elab_Visited.Append ((Subp_Id => E, Context => Parent (N)));
18366
18367 Sbody := Unit_Declaration_Node (E);
18368
18369 if not Nkind_In (Sbody, N_Subprogram_Body, N_Package_Body) then
18370 Ebody := Corresponding_Body (Sbody);
18371
18372 if No (Ebody) then
18373 return;
18374 else
18375 Sbody := Unit_Declaration_Node (Ebody);
18376 end if;
18377 end if;
18378
18379 -- If the body appears after the outer level call or instantiation then
18380 -- we have an error case handled below.
18381
18382 if Earlier_In_Extended_Unit (Outer_Level_Sloc, Sloc (Sbody))
18383 and then not In_Task_Activation
18384 then
18385 null;
18386
18387 -- If we have the instantiation case we are done, since we now know that
18388 -- the body of the generic appeared earlier.
18389
18390 elsif Inst_Case then
18391 return;
18392
18393 -- Otherwise we have a call, so we trace through the called body to see
18394 -- if it has any problems.
18395
18396 else
18397 pragma Assert (Nkind (Sbody) = N_Subprogram_Body);
18398
18399 Elab_Call.Append ((Cloc => Loc, Ent => E));
18400
18401 if Debug_Flag_Underscore_LL then
18402 Write_Str ("Elab_Call.Last = ");
18403 Write_Int (Int (Elab_Call.Last));
18404 Write_Str (" Ent = ");
18405 Write_Name (Chars (E));
18406 Write_Str (" at ");
18407 Write_Location (Sloc (N));
18408 Write_Eol;
18409 end if;
18410
18411 -- Now traverse declarations and statements of subprogram body. Note
18412 -- that we cannot simply Traverse (Sbody), since traverse does not
18413 -- normally visit subprogram bodies.
18414
18415 declare
18416 Decl : Node_Id;
18417 begin
18418 Decl := First (Declarations (Sbody));
18419 while Present (Decl) loop
18420 Traverse (Decl);
18421 Next (Decl);
18422 end loop;
18423 end;
18424
18425 Traverse (Handled_Statement_Sequence (Sbody));
18426
18427 Elab_Call.Decrement_Last;
18428 return;
18429 end if;
18430
18431 -- Here is the case of calling a subprogram where the body has not yet
18432 -- been encountered. A warning message is needed, except if this is the
18433 -- case of appearing within an aspect specification that results in
18434 -- a check call, we do not really have such a situation, so no warning
18435 -- is needed (e.g. the case of a precondition, where the call appears
18436 -- textually before the body, but in actual fact is moved to the
18437 -- appropriate subprogram body and so does not need a check).
18438
18439 declare
18440 P : Node_Id;
18441 O : Node_Id;
18442
18443 begin
18444 P := Parent (N);
18445 loop
18446 -- Keep looking at parents if we are still in the subexpression
18447
18448 if Nkind (P) in N_Subexpr then
18449 P := Parent (P);
18450
18451 -- Here P is the parent of the expression, check for special case
18452
18453 else
18454 O := Original_Node (P);
18455
18456 -- Definitely not the special case if orig node is not a pragma
18457
18458 exit when Nkind (O) /= N_Pragma;
18459
18460 -- Check we have an If statement or a null statement (happens
18461 -- when the If has been expanded to be True).
18462
18463 exit when not Nkind_In (P, N_If_Statement, N_Null_Statement);
18464
18465 -- Our special case will be indicated either by the pragma
18466 -- coming from an aspect ...
18467
18468 if Present (Corresponding_Aspect (O)) then
18469 return;
18470
18471 -- Or, in the case of an initial condition, specifically by a
18472 -- Check pragma specifying an Initial_Condition check.
18473
18474 elsif Pragma_Name (O) = Name_Check
18475 and then
18476 Chars
18477 (Expression (First (Pragma_Argument_Associations (O)))) =
18478 Name_Initial_Condition
18479 then
18480 return;
18481
18482 -- For anything else, we have an error
18483
18484 else
18485 exit;
18486 end if;
18487 end if;
18488 end loop;
18489 end;
18490
18491 -- Not that special case, warning and dynamic check is required
18492
18493 -- If we have nothing in the call stack, then this is at the outer
18494 -- level, and the ABE is bound to occur, unless it's a 'Access, or
18495 -- it's a renaming.
18496
18497 if Elab_Call.Last = 0 then
18498 Error_Msg_Warn := SPARK_Mode /= On;
18499
18500 declare
18501 Insert_Check : Boolean := True;
18502 -- This flag is set to True if an elaboration check should be
18503 -- inserted.
18504
18505 begin
18506 if In_Task_Activation then
18507 Insert_Check := False;
18508
18509 elsif Inst_Case then
18510 Error_Msg_NE
18511 ("cannot instantiate& before body seen<<", N, Orig_Ent);
18512
18513 elsif Nkind (N) = N_Attribute_Reference then
18514 Error_Msg_NE
18515 ("Access attribute of & before body seen<<", N, Orig_Ent);
18516 Error_Msg_N ("\possible Program_Error on later references<", N);
18517 Insert_Check := False;
18518
18519 elsif Nkind (Unit_Declaration_Node (Orig_Ent)) /=
18520 N_Subprogram_Renaming_Declaration
18521 then
18522 Error_Msg_NE
18523 ("cannot call& before body seen<<", N, Orig_Ent);
18524
18525 elsif not Is_Generic_Actual_Subprogram (Orig_Ent) then
18526 Insert_Check := False;
18527 end if;
18528
18529 if Insert_Check then
18530 Error_Msg_N ("\Program_Error [<<", N);
18531 Insert_Elab_Check (N);
18532 end if;
18533 end;
18534
18535 -- Call is not at outer level
18536
18537 else
18538 -- Do not generate elaboration checks in GNATprove mode because the
18539 -- elaboration counter and the check are both forms of expansion.
18540
18541 if GNATprove_Mode then
18542 null;
18543
18544 -- Generate an elaboration check
18545
18546 elsif not Elaboration_Checks_Suppressed (E) then
18547 Set_Elaboration_Entity_Required (E);
18548
18549 -- Create a declaration of the elaboration entity, and insert it
18550 -- prior to the subprogram or the generic unit, within the same
18551 -- scope. Since the subprogram may be overloaded, create a unique
18552 -- entity.
18553
18554 if No (Elaboration_Entity (E)) then
18555 declare
18556 Loce : constant Source_Ptr := Sloc (E);
18557 Ent : constant Entity_Id :=
18558 Make_Defining_Identifier (Loc,
18559 New_External_Name (Chars (E), 'E', -1));
18560
18561 begin
18562 Set_Elaboration_Entity (E, Ent);
18563 Push_Scope (Scope (E));
18564
18565 Insert_Action (Declaration_Node (E),
18566 Make_Object_Declaration (Loce,
18567 Defining_Identifier => Ent,
18568 Object_Definition =>
18569 New_Occurrence_Of (Standard_Short_Integer, Loce),
18570 Expression =>
18571 Make_Integer_Literal (Loc, Uint_0)));
18572
18573 -- Set elaboration flag at the point of the body
18574
18575 Set_Elaboration_Flag (Sbody, E);
18576
18577 -- Kill current value indication. This is necessary because
18578 -- the tests of this flag are inserted out of sequence and
18579 -- must not pick up bogus indications of the wrong constant
18580 -- value. Also, this is never a true constant, since one way
18581 -- or another, it gets reset.
18582
18583 Set_Current_Value (Ent, Empty);
18584 Set_Last_Assignment (Ent, Empty);
18585 Set_Is_True_Constant (Ent, False);
18586 Pop_Scope;
18587 end;
18588 end if;
18589
18590 -- Generate:
18591 -- if Enn = 0 then
18592 -- raise Program_Error with "access before elaboration";
18593 -- end if;
18594
18595 Insert_Elab_Check (N,
18596 Make_Attribute_Reference (Loc,
18597 Attribute_Name => Name_Elaborated,
18598 Prefix => New_Occurrence_Of (E, Loc)));
18599 end if;
18600
18601 -- Generate the warning
18602
18603 if not Suppress_Elaboration_Warnings (E)
18604 and then not Elaboration_Checks_Suppressed (E)
18605
18606 -- Suppress this warning if we have a function call that occurred
18607 -- within an assertion expression, since we can get false warnings
18608 -- in this case, due to the out of order handling in this case.
18609
18610 and then
18611 (Nkind (Original_Node (N)) /= N_Function_Call
18612 or else not In_Assertion_Expression_Pragma (Original_Node (N)))
18613 then
18614 Error_Msg_Warn := SPARK_Mode /= On;
18615
18616 if Inst_Case then
18617 Error_Msg_NE
18618 ("instantiation of& may occur before body is seen<l<",
18619 N, Orig_Ent);
18620 else
18621 -- A rather specific check. For Finalize/Adjust/Initialize, if
18622 -- the type has Warnings_Off set, suppress the warning.
18623
18624 if Nam_In (Chars (E), Name_Adjust,
18625 Name_Finalize,
18626 Name_Initialize)
18627 and then Present (First_Formal (E))
18628 then
18629 declare
18630 T : constant Entity_Id := Etype (First_Formal (E));
18631 begin
18632 if Is_Controlled (T) then
18633 if Warnings_Off (T)
18634 or else (Ekind (T) = E_Private_Type
18635 and then Warnings_Off (Full_View (T)))
18636 then
18637 goto Output;
18638 end if;
18639 end if;
18640 end;
18641 end if;
18642
18643 -- Go ahead and give warning if not this special case
18644
18645 Error_Msg_NE
18646 ("call to& may occur before body is seen<l<", N, Orig_Ent);
18647 end if;
18648
18649 Error_Msg_N ("\Program_Error ]<l<", N);
18650
18651 -- There is no need to query the elaboration warning message flags
18652 -- because the main message is an error, not a warning, therefore
18653 -- all the clarification messages produces by Output_Calls must be
18654 -- emitted unconditionally.
18655
18656 <<Output>>
18657
18658 Output_Calls (N, Check_Elab_Flag => False);
18659 end if;
18660 end if;
18661 end Check_Internal_Call_Continue;
18662
18663 ---------------------------
18664 -- Check_Task_Activation --
18665 ---------------------------
18666
18667 procedure Check_Task_Activation (N : Node_Id) is
18668 Loc : constant Source_Ptr := Sloc (N);
18669 Inter_Procs : constant Elist_Id := New_Elmt_List;
18670 Intra_Procs : constant Elist_Id := New_Elmt_List;
18671 Ent : Entity_Id;
18672 P : Entity_Id;
18673 Task_Scope : Entity_Id;
18674 Cunit_SC : Boolean := False;
18675 Decl : Node_Id;
18676 Elmt : Elmt_Id;
18677 Enclosing : Entity_Id;
18678
18679 procedure Add_Task_Proc (Typ : Entity_Id);
18680 -- Add to Task_Procs the task body procedure(s) of task types in Typ.
18681 -- For record types, this procedure recurses over component types.
18682
18683 procedure Collect_Tasks (Decls : List_Id);
18684 -- Collect the types of the tasks that are to be activated in the given
18685 -- list of declarations, in order to perform elaboration checks on the
18686 -- corresponding task procedures that are called implicitly here.
18687
18688 function Outer_Unit (E : Entity_Id) return Entity_Id;
18689 -- find enclosing compilation unit of Entity, ignoring subunits, or
18690 -- else enclosing subprogram. If E is not a package, there is no need
18691 -- for inter-unit elaboration checks.
18692
18693 -------------------
18694 -- Add_Task_Proc --
18695 -------------------
18696
18697 procedure Add_Task_Proc (Typ : Entity_Id) is
18698 Comp : Entity_Id;
18699 Proc : Entity_Id := Empty;
18700
18701 begin
18702 if Is_Task_Type (Typ) then
18703 Proc := Get_Task_Body_Procedure (Typ);
18704
18705 elsif Is_Array_Type (Typ)
18706 and then Has_Task (Base_Type (Typ))
18707 then
18708 Add_Task_Proc (Component_Type (Typ));
18709
18710 elsif Is_Record_Type (Typ)
18711 and then Has_Task (Base_Type (Typ))
18712 then
18713 Comp := First_Component (Typ);
18714 while Present (Comp) loop
18715 Add_Task_Proc (Etype (Comp));
18716 Comp := Next_Component (Comp);
18717 end loop;
18718 end if;
18719
18720 -- If the task type is another unit, we will perform the usual
18721 -- elaboration check on its enclosing unit. If the type is in the
18722 -- same unit, we can trace the task body as for an internal call,
18723 -- but we only need to examine other external calls, because at
18724 -- the point the task is activated, internal subprogram bodies
18725 -- will have been elaborated already. We keep separate lists for
18726 -- each kind of task.
18727
18728 -- Skip this test if errors have occurred, since in this case
18729 -- we can get false indications.
18730
18731 if Serious_Errors_Detected /= 0 then
18732 return;
18733 end if;
18734
18735 if Present (Proc) then
18736 if Outer_Unit (Scope (Proc)) = Enclosing then
18737
18738 if No (Corresponding_Body (Unit_Declaration_Node (Proc)))
18739 and then
18740 (not Is_Generic_Instance (Scope (Proc))
18741 or else Scope (Proc) = Scope (Defining_Identifier (Decl)))
18742 then
18743 Error_Msg_Warn := SPARK_Mode /= On;
18744 Error_Msg_N
18745 ("task will be activated before elaboration of its body<<",
18746 Decl);
18747 Error_Msg_N ("\Program_Error [<<", Decl);
18748
18749 elsif Present
18750 (Corresponding_Body (Unit_Declaration_Node (Proc)))
18751 then
18752 Append_Elmt (Proc, Intra_Procs);
18753 end if;
18754
18755 else
18756 -- No need for multiple entries of the same type
18757
18758 Elmt := First_Elmt (Inter_Procs);
18759 while Present (Elmt) loop
18760 if Node (Elmt) = Proc then
18761 return;
18762 end if;
18763
18764 Next_Elmt (Elmt);
18765 end loop;
18766
18767 Append_Elmt (Proc, Inter_Procs);
18768 end if;
18769 end if;
18770 end Add_Task_Proc;
18771
18772 -------------------
18773 -- Collect_Tasks --
18774 -------------------
18775
18776 procedure Collect_Tasks (Decls : List_Id) is
18777 begin
18778 if Present (Decls) then
18779 Decl := First (Decls);
18780 while Present (Decl) loop
18781 if Nkind (Decl) = N_Object_Declaration
18782 and then Has_Task (Etype (Defining_Identifier (Decl)))
18783 then
18784 Add_Task_Proc (Etype (Defining_Identifier (Decl)));
18785 end if;
18786
18787 Next (Decl);
18788 end loop;
18789 end if;
18790 end Collect_Tasks;
18791
18792 ----------------
18793 -- Outer_Unit --
18794 ----------------
18795
18796 function Outer_Unit (E : Entity_Id) return Entity_Id is
18797 Outer : Entity_Id;
18798
18799 begin
18800 Outer := E;
18801 while Present (Outer) loop
18802 if Elaboration_Checks_Suppressed (Outer) then
18803 Cunit_SC := True;
18804 end if;
18805
18806 exit when Is_Child_Unit (Outer)
18807 or else Scope (Outer) = Standard_Standard
18808 or else Ekind (Outer) /= E_Package;
18809 Outer := Scope (Outer);
18810 end loop;
18811
18812 return Outer;
18813 end Outer_Unit;
18814
18815 -- Start of processing for Check_Task_Activation
18816
18817 begin
18818 pragma Assert (Legacy_Elaboration_Checks);
18819
18820 Enclosing := Outer_Unit (Current_Scope);
18821
18822 -- Find all tasks declared in the current unit
18823
18824 if Nkind (N) = N_Package_Body then
18825 P := Unit_Declaration_Node (Corresponding_Spec (N));
18826
18827 Collect_Tasks (Declarations (N));
18828 Collect_Tasks (Visible_Declarations (Specification (P)));
18829 Collect_Tasks (Private_Declarations (Specification (P)));
18830
18831 elsif Nkind (N) = N_Package_Declaration then
18832 Collect_Tasks (Visible_Declarations (Specification (N)));
18833 Collect_Tasks (Private_Declarations (Specification (N)));
18834
18835 else
18836 Collect_Tasks (Declarations (N));
18837 end if;
18838
18839 -- We only perform detailed checks in all tasks that are library level
18840 -- entities. If the master is a subprogram or task, activation will
18841 -- depend on the activation of the master itself.
18842
18843 -- Should dynamic checks be added in the more general case???
18844
18845 if Ekind (Enclosing) /= E_Package then
18846 return;
18847 end if;
18848
18849 -- For task types defined in other units, we want the unit containing
18850 -- the task body to be elaborated before the current one.
18851
18852 Elmt := First_Elmt (Inter_Procs);
18853 while Present (Elmt) loop
18854 Ent := Node (Elmt);
18855 Task_Scope := Outer_Unit (Scope (Ent));
18856
18857 if not Is_Compilation_Unit (Task_Scope) then
18858 null;
18859
18860 elsif Suppress_Elaboration_Warnings (Task_Scope)
18861 or else Elaboration_Checks_Suppressed (Task_Scope)
18862 then
18863 null;
18864
18865 elsif Dynamic_Elaboration_Checks then
18866 if not Elaboration_Checks_Suppressed (Ent)
18867 and then not Cunit_SC
18868 and then not Restriction_Active
18869 (No_Entry_Calls_In_Elaboration_Code)
18870 then
18871 -- Runtime elaboration check required. Generate check of the
18872 -- elaboration counter for the unit containing the entity.
18873
18874 Insert_Elab_Check (N,
18875 Make_Attribute_Reference (Loc,
18876 Prefix =>
18877 New_Occurrence_Of (Spec_Entity (Task_Scope), Loc),
18878 Attribute_Name => Name_Elaborated));
18879 end if;
18880
18881 else
18882 -- Force the binder to elaborate other unit first
18883
18884 if Elab_Info_Messages
18885 and then not Suppress_Elaboration_Warnings (Ent)
18886 and then not Elaboration_Checks_Suppressed (Ent)
18887 and then not Suppress_Elaboration_Warnings (Task_Scope)
18888 and then not Elaboration_Checks_Suppressed (Task_Scope)
18889 then
18890 Error_Msg_Node_2 := Task_Scope;
18891 Error_Msg_NE
18892 ("info: activation of an instance of task type & requires "
18893 & "pragma Elaborate_All on &?$?", N, Ent);
18894 end if;
18895
18896 Activate_Elaborate_All_Desirable (N, Task_Scope);
18897 Set_Suppress_Elaboration_Warnings (Task_Scope);
18898 end if;
18899
18900 Next_Elmt (Elmt);
18901 end loop;
18902
18903 -- For tasks declared in the current unit, trace other calls within the
18904 -- task procedure bodies, which are available.
18905
18906 if not Debug_Flag_Dot_Y then
18907 In_Task_Activation := True;
18908
18909 Elmt := First_Elmt (Intra_Procs);
18910 while Present (Elmt) loop
18911 Ent := Node (Elmt);
18912 Check_Internal_Call_Continue (N, Ent, Enclosing, Ent);
18913 Next_Elmt (Elmt);
18914 end loop;
18915
18916 In_Task_Activation := False;
18917 end if;
18918 end Check_Task_Activation;
18919
18920 ------------------------
18921 -- Get_Referenced_Ent --
18922 ------------------------
18923
18924 function Get_Referenced_Ent (N : Node_Id) return Entity_Id is
18925 Nam : Node_Id;
18926
18927 begin
18928 if Nkind (N) in N_Has_Entity
18929 and then Present (Entity (N))
18930 and then Ekind (Entity (N)) = E_Variable
18931 then
18932 return Entity (N);
18933 end if;
18934
18935 if Nkind (N) = N_Attribute_Reference then
18936 Nam := Prefix (N);
18937 else
18938 Nam := Name (N);
18939 end if;
18940
18941 if No (Nam) then
18942 return Empty;
18943 elsif Nkind (Nam) = N_Selected_Component then
18944 return Entity (Selector_Name (Nam));
18945 elsif not Is_Entity_Name (Nam) then
18946 return Empty;
18947 else
18948 return Entity (Nam);
18949 end if;
18950 end Get_Referenced_Ent;
18951
18952 ----------------------
18953 -- Has_Generic_Body --
18954 ----------------------
18955
18956 function Has_Generic_Body (N : Node_Id) return Boolean is
18957 Ent : constant Entity_Id := Get_Generic_Entity (N);
18958 Decl : constant Node_Id := Unit_Declaration_Node (Ent);
18959 Scop : Entity_Id;
18960
18961 function Find_Body_In (E : Entity_Id; N : Node_Id) return Node_Id;
18962 -- Determine if the list of nodes headed by N and linked by Next
18963 -- contains a package body for the package spec entity E, and if so
18964 -- return the package body. If not, then returns Empty.
18965
18966 function Load_Package_Body (Nam : Unit_Name_Type) return Node_Id;
18967 -- This procedure is called load the unit whose name is given by Nam.
18968 -- This unit is being loaded to see whether it contains an optional
18969 -- generic body. The returned value is the loaded unit, which is always
18970 -- a package body (only package bodies can contain other entities in the
18971 -- sense in which Has_Generic_Body is interested). We only attempt to
18972 -- load bodies if we are generating code. If we are in semantics check
18973 -- only mode, then it would be wrong to load bodies that are not
18974 -- required from a semantic point of view, so in this case we return
18975 -- Empty. The result is that the caller may incorrectly decide that a
18976 -- generic spec does not have a body when in fact it does, but the only
18977 -- harm in this is that some warnings on elaboration problems may be
18978 -- lost in semantic checks only mode, which is not big loss. We also
18979 -- return Empty if we go for a body and it is not there.
18980
18981 function Locate_Corresponding_Body (PE : Entity_Id) return Node_Id;
18982 -- PE is the entity for a package spec. This function locates the
18983 -- corresponding package body, returning Empty if none is found. The
18984 -- package body returned is fully parsed but may not yet be analyzed,
18985 -- so only syntactic fields should be referenced.
18986
18987 ------------------
18988 -- Find_Body_In --
18989 ------------------
18990
18991 function Find_Body_In (E : Entity_Id; N : Node_Id) return Node_Id is
18992 Nod : Node_Id;
18993
18994 begin
18995 Nod := N;
18996 while Present (Nod) loop
18997
18998 -- If we found the package body we are looking for, return it
18999
19000 if Nkind (Nod) = N_Package_Body
19001 and then Chars (Defining_Unit_Name (Nod)) = Chars (E)
19002 then
19003 return Nod;
19004
19005 -- If we found the stub for the body, go after the subunit,
19006 -- loading it if necessary.
19007
19008 elsif Nkind (Nod) = N_Package_Body_Stub
19009 and then Chars (Defining_Identifier (Nod)) = Chars (E)
19010 then
19011 if Present (Library_Unit (Nod)) then
19012 return Unit (Library_Unit (Nod));
19013
19014 else
19015 return Load_Package_Body (Get_Unit_Name (Nod));
19016 end if;
19017
19018 -- If neither package body nor stub, keep looking on chain
19019
19020 else
19021 Next (Nod);
19022 end if;
19023 end loop;
19024
19025 return Empty;
19026 end Find_Body_In;
19027
19028 -----------------------
19029 -- Load_Package_Body --
19030 -----------------------
19031
19032 function Load_Package_Body (Nam : Unit_Name_Type) return Node_Id is
19033 U : Unit_Number_Type;
19034
19035 begin
19036 if Operating_Mode /= Generate_Code then
19037 return Empty;
19038 else
19039 U :=
19040 Load_Unit
19041 (Load_Name => Nam,
19042 Required => False,
19043 Subunit => False,
19044 Error_Node => N);
19045
19046 if U = No_Unit then
19047 return Empty;
19048 else
19049 return Unit (Cunit (U));
19050 end if;
19051 end if;
19052 end Load_Package_Body;
19053
19054 -------------------------------
19055 -- Locate_Corresponding_Body --
19056 -------------------------------
19057
19058 function Locate_Corresponding_Body (PE : Entity_Id) return Node_Id is
19059 Spec : constant Node_Id := Declaration_Node (PE);
19060 Decl : constant Node_Id := Parent (Spec);
19061 Scop : constant Entity_Id := Scope (PE);
19062 PBody : Node_Id;
19063
19064 begin
19065 if Is_Library_Level_Entity (PE) then
19066
19067 -- If package is a library unit that requires a body, we have no
19068 -- choice but to go after that body because it might contain an
19069 -- optional body for the original generic package.
19070
19071 if Unit_Requires_Body (PE) then
19072
19073 -- Load the body. Note that we are a little careful here to use
19074 -- Spec to get the unit number, rather than PE or Decl, since
19075 -- in the case where the package is itself a library level
19076 -- instantiation, Spec will properly reference the generic
19077 -- template, which is what we really want.
19078
19079 return
19080 Load_Package_Body
19081 (Get_Body_Name (Unit_Name (Get_Source_Unit (Spec))));
19082
19083 -- But if the package is a library unit that does NOT require
19084 -- a body, then no body is permitted, so we are sure that there
19085 -- is no body for the original generic package.
19086
19087 else
19088 return Empty;
19089 end if;
19090
19091 -- Otherwise look and see if we are embedded in a further package
19092
19093 elsif Is_Package_Or_Generic_Package (Scop) then
19094
19095 -- If so, get the body of the enclosing package, and look in
19096 -- its package body for the package body we are looking for.
19097
19098 PBody := Locate_Corresponding_Body (Scop);
19099
19100 if No (PBody) then
19101 return Empty;
19102 else
19103 return Find_Body_In (PE, First (Declarations (PBody)));
19104 end if;
19105
19106 -- If we are not embedded in a further package, then the body
19107 -- must be in the same declarative part as we are.
19108
19109 else
19110 return Find_Body_In (PE, Next (Decl));
19111 end if;
19112 end Locate_Corresponding_Body;
19113
19114 -- Start of processing for Has_Generic_Body
19115
19116 begin
19117 if Present (Corresponding_Body (Decl)) then
19118 return True;
19119
19120 elsif Unit_Requires_Body (Ent) then
19121 return True;
19122
19123 -- Compilation units cannot have optional bodies
19124
19125 elsif Is_Compilation_Unit (Ent) then
19126 return False;
19127
19128 -- Otherwise look at what scope we are in
19129
19130 else
19131 Scop := Scope (Ent);
19132
19133 -- Case of entity is in other than a package spec, in this case
19134 -- the body, if present, must be in the same declarative part.
19135
19136 if not Is_Package_Or_Generic_Package (Scop) then
19137 declare
19138 P : Node_Id;
19139
19140 begin
19141 -- Declaration node may get us a spec, so if so, go to
19142 -- the parent declaration.
19143
19144 P := Declaration_Node (Ent);
19145 while not Is_List_Member (P) loop
19146 P := Parent (P);
19147 end loop;
19148
19149 return Present (Find_Body_In (Ent, Next (P)));
19150 end;
19151
19152 -- If the entity is in a package spec, then we have to locate
19153 -- the corresponding package body, and look there.
19154
19155 else
19156 declare
19157 PBody : constant Node_Id := Locate_Corresponding_Body (Scop);
19158
19159 begin
19160 if No (PBody) then
19161 return False;
19162 else
19163 return
19164 Present
19165 (Find_Body_In (Ent, (First (Declarations (PBody)))));
19166 end if;
19167 end;
19168 end if;
19169 end if;
19170 end Has_Generic_Body;
19171
19172 -----------------------
19173 -- Insert_Elab_Check --
19174 -----------------------
19175
19176 procedure Insert_Elab_Check (N : Node_Id; C : Node_Id := Empty) is
19177 Nod : Node_Id;
19178 Loc : constant Source_Ptr := Sloc (N);
19179
19180 Chk : Node_Id;
19181 -- The check (N_Raise_Program_Error) node to be inserted
19182
19183 begin
19184 -- If expansion is disabled, do not generate any checks. Also
19185 -- skip checks if any subunits are missing because in either
19186 -- case we lack the full information that we need, and no object
19187 -- file will be created in any case.
19188
19189 if not Expander_Active or else Subunits_Missing then
19190 return;
19191 end if;
19192
19193 -- If we have a generic instantiation, where Instance_Spec is set,
19194 -- then this field points to a generic instance spec that has
19195 -- been inserted before the instantiation node itself, so that
19196 -- is where we want to insert a check.
19197
19198 if Nkind (N) in N_Generic_Instantiation
19199 and then Present (Instance_Spec (N))
19200 then
19201 Nod := Instance_Spec (N);
19202 else
19203 Nod := N;
19204 end if;
19205
19206 -- Build check node, possibly with condition
19207
19208 Chk :=
19209 Make_Raise_Program_Error (Loc, Reason => PE_Access_Before_Elaboration);
19210
19211 if Present (C) then
19212 Set_Condition (Chk, Make_Op_Not (Loc, Right_Opnd => C));
19213 end if;
19214
19215 -- If we are inserting at the top level, insert in Aux_Decls
19216
19217 if Nkind (Parent (Nod)) = N_Compilation_Unit then
19218 declare
19219 ADN : constant Node_Id := Aux_Decls_Node (Parent (Nod));
19220
19221 begin
19222 if No (Declarations (ADN)) then
19223 Set_Declarations (ADN, New_List (Chk));
19224 else
19225 Append_To (Declarations (ADN), Chk);
19226 end if;
19227
19228 Analyze (Chk);
19229 end;
19230
19231 -- Otherwise just insert as an action on the node in question
19232
19233 else
19234 Insert_Action (Nod, Chk);
19235 end if;
19236 end Insert_Elab_Check;
19237
19238 -------------------------------
19239 -- Is_Call_Of_Generic_Formal --
19240 -------------------------------
19241
19242 function Is_Call_Of_Generic_Formal (N : Node_Id) return Boolean is
19243 begin
19244 return Nkind_In (N, N_Function_Call, N_Procedure_Call_Statement)
19245
19246 -- Always return False if debug flag -gnatd.G is set
19247
19248 and then not Debug_Flag_Dot_GG
19249
19250 -- For now, we detect this by looking for the strange identifier
19251 -- node, whose Chars reflect the name of the generic formal, but
19252 -- the Chars of the Entity references the generic actual.
19253
19254 and then Nkind (Name (N)) = N_Identifier
19255 and then Chars (Name (N)) /= Chars (Entity (Name (N)));
19256 end Is_Call_Of_Generic_Formal;
19257
19258 -------------------------------
19259 -- Is_Finalization_Procedure --
19260 -------------------------------
19261
19262 function Is_Finalization_Procedure (Id : Entity_Id) return Boolean is
19263 begin
19264 -- Check whether Id is a procedure with at least one parameter
19265
19266 if Ekind (Id) = E_Procedure and then Present (First_Formal (Id)) then
19267 declare
19268 Typ : constant Entity_Id := Etype (First_Formal (Id));
19269 Deep_Fin : Entity_Id := Empty;
19270 Fin : Entity_Id := Empty;
19271
19272 begin
19273 -- If the type of the first formal does not require finalization
19274 -- actions, then this is definitely not [Deep_]Finalize.
19275
19276 if not Needs_Finalization (Typ) then
19277 return False;
19278 end if;
19279
19280 -- At this point we have the following scenario:
19281
19282 -- procedure Name (Param1 : [in] [out] Ctrl[; Param2 : ...]);
19283
19284 -- Recover the two possible versions of [Deep_]Finalize using the
19285 -- type of the first parameter and compare with the input.
19286
19287 Deep_Fin := TSS (Typ, TSS_Deep_Finalize);
19288
19289 if Is_Controlled (Typ) then
19290 Fin := Find_Prim_Op (Typ, Name_Finalize);
19291 end if;
19292
19293 return (Present (Deep_Fin) and then Id = Deep_Fin)
19294 or else (Present (Fin) and then Id = Fin);
19295 end;
19296 end if;
19297
19298 return False;
19299 end Is_Finalization_Procedure;
19300
19301 ------------------
19302 -- Output_Calls --
19303 ------------------
19304
19305 procedure Output_Calls
19306 (N : Node_Id;
19307 Check_Elab_Flag : Boolean)
19308 is
19309 function Emit (Flag : Boolean) return Boolean;
19310 -- Determine whether to emit an error message based on the combination
19311 -- of flags Check_Elab_Flag and Flag.
19312
19313 function Is_Printable_Error_Name return Boolean;
19314 -- An internal function, used to determine if a name, stored in the
19315 -- Name_Buffer, is either a non-internal name, or is an internal name
19316 -- that is printable by the error message circuits (i.e. it has a single
19317 -- upper case letter at the end).
19318
19319 ----------
19320 -- Emit --
19321 ----------
19322
19323 function Emit (Flag : Boolean) return Boolean is
19324 begin
19325 if Check_Elab_Flag then
19326 return Flag;
19327 else
19328 return True;
19329 end if;
19330 end Emit;
19331
19332 -----------------------------
19333 -- Is_Printable_Error_Name --
19334 -----------------------------
19335
19336 function Is_Printable_Error_Name return Boolean is
19337 begin
19338 if not Is_Internal_Name then
19339 return True;
19340
19341 elsif Name_Len = 1 then
19342 return False;
19343
19344 else
19345 Name_Len := Name_Len - 1;
19346 return not Is_Internal_Name;
19347 end if;
19348 end Is_Printable_Error_Name;
19349
19350 -- Local variables
19351
19352 Ent : Entity_Id;
19353
19354 -- Start of processing for Output_Calls
19355
19356 begin
19357 for J in reverse 1 .. Elab_Call.Last loop
19358 Error_Msg_Sloc := Elab_Call.Table (J).Cloc;
19359
19360 Ent := Elab_Call.Table (J).Ent;
19361 Get_Name_String (Chars (Ent));
19362
19363 -- Dynamic elaboration model, warnings controlled by -gnatwl
19364
19365 if Dynamic_Elaboration_Checks then
19366 if Emit (Elab_Warnings) then
19367 if Is_Generic_Unit (Ent) then
19368 Error_Msg_NE ("\\?l?& instantiated #", N, Ent);
19369 elsif Is_Init_Proc (Ent) then
19370 Error_Msg_N ("\\?l?initialization procedure called #", N);
19371 elsif Is_Printable_Error_Name then
19372 Error_Msg_NE ("\\?l?& called #", N, Ent);
19373 else
19374 Error_Msg_N ("\\?l?called #", N);
19375 end if;
19376 end if;
19377
19378 -- Static elaboration model, info messages controlled by -gnatel
19379
19380 else
19381 if Emit (Elab_Info_Messages) then
19382 if Is_Generic_Unit (Ent) then
19383 Error_Msg_NE ("\\?$?& instantiated #", N, Ent);
19384 elsif Is_Init_Proc (Ent) then
19385 Error_Msg_N ("\\?$?initialization procedure called #", N);
19386 elsif Is_Printable_Error_Name then
19387 Error_Msg_NE ("\\?$?& called #", N, Ent);
19388 else
19389 Error_Msg_N ("\\?$?called #", N);
19390 end if;
19391 end if;
19392 end if;
19393 end loop;
19394 end Output_Calls;
19395
19396 ----------------------------
19397 -- Same_Elaboration_Scope --
19398 ----------------------------
19399
19400 function Same_Elaboration_Scope (Scop1, Scop2 : Entity_Id) return Boolean is
19401 S1 : Entity_Id;
19402 S2 : Entity_Id;
19403
19404 begin
19405 -- Find elaboration scope for Scop1
19406 -- This is either a subprogram or a compilation unit.
19407
19408 S1 := Scop1;
19409 while S1 /= Standard_Standard
19410 and then not Is_Compilation_Unit (S1)
19411 and then Ekind_In (S1, E_Package, E_Protected_Type, E_Block)
19412 loop
19413 S1 := Scope (S1);
19414 end loop;
19415
19416 -- Find elaboration scope for Scop2
19417
19418 S2 := Scop2;
19419 while S2 /= Standard_Standard
19420 and then not Is_Compilation_Unit (S2)
19421 and then Ekind_In (S2, E_Package, E_Protected_Type, E_Block)
19422 loop
19423 S2 := Scope (S2);
19424 end loop;
19425
19426 return S1 = S2;
19427 end Same_Elaboration_Scope;
19428
19429 -----------------
19430 -- Set_C_Scope --
19431 -----------------
19432
19433 procedure Set_C_Scope is
19434 begin
19435 while not Is_Compilation_Unit (C_Scope) loop
19436 C_Scope := Scope (C_Scope);
19437 end loop;
19438 end Set_C_Scope;
19439
19440 --------------------------------
19441 -- Set_Elaboration_Constraint --
19442 --------------------------------
19443
19444 procedure Set_Elaboration_Constraint
19445 (Call : Node_Id;
19446 Subp : Entity_Id;
19447 Scop : Entity_Id)
19448 is
19449 Elab_Unit : Entity_Id;
19450
19451 -- Check whether this is a call to an Initialize subprogram for a
19452 -- controlled type. Note that Call can also be a 'Access attribute
19453 -- reference, which now generates an elaboration check.
19454
19455 Init_Call : constant Boolean :=
19456 Nkind (Call) = N_Procedure_Call_Statement
19457 and then Chars (Subp) = Name_Initialize
19458 and then Comes_From_Source (Subp)
19459 and then Present (Parameter_Associations (Call))
19460 and then Is_Controlled (Etype (First_Actual (Call)));
19461
19462 begin
19463 -- If the unit is mentioned in a with_clause of the current unit, it is
19464 -- visible, and we can set the elaboration flag.
19465
19466 if Is_Immediately_Visible (Scop)
19467 or else (Is_Child_Unit (Scop) and then Is_Visible_Lib_Unit (Scop))
19468 then
19469 Activate_Elaborate_All_Desirable (Call, Scop);
19470 Set_Suppress_Elaboration_Warnings (Scop);
19471 return;
19472 end if;
19473
19474 -- If this is not an initialization call or a call using object notation
19475 -- we know that the unit of the called entity is in the context, and we
19476 -- can set the flag as well. The unit need not be visible if the call
19477 -- occurs within an instantiation.
19478
19479 if Is_Init_Proc (Subp)
19480 or else Init_Call
19481 or else Nkind (Original_Node (Call)) = N_Selected_Component
19482 then
19483 null; -- detailed processing follows.
19484
19485 else
19486 Activate_Elaborate_All_Desirable (Call, Scop);
19487 Set_Suppress_Elaboration_Warnings (Scop);
19488 return;
19489 end if;
19490
19491 -- If the unit is not in the context, there must be an intermediate unit
19492 -- that is, on which we need to place to elaboration flag. This happens
19493 -- with init proc calls.
19494
19495 if Is_Init_Proc (Subp) or else Init_Call then
19496
19497 -- The initialization call is on an object whose type is not declared
19498 -- in the same scope as the subprogram. The type of the object must
19499 -- be a subtype of the type of operation. This object is the first
19500 -- actual in the call.
19501
19502 declare
19503 Typ : constant Entity_Id :=
19504 Etype (First (Parameter_Associations (Call)));
19505 begin
19506 Elab_Unit := Scope (Typ);
19507 while (Present (Elab_Unit))
19508 and then not Is_Compilation_Unit (Elab_Unit)
19509 loop
19510 Elab_Unit := Scope (Elab_Unit);
19511 end loop;
19512 end;
19513
19514 -- If original node uses selected component notation, the prefix is
19515 -- visible and determines the scope that must be elaborated. After
19516 -- rewriting, the prefix is the first actual in the call.
19517
19518 elsif Nkind (Original_Node (Call)) = N_Selected_Component then
19519 Elab_Unit := Scope (Etype (First (Parameter_Associations (Call))));
19520
19521 -- Not one of special cases above
19522
19523 else
19524 -- Using previously computed scope. If the elaboration check is
19525 -- done after analysis, the scope is not visible any longer, but
19526 -- must still be in the context.
19527
19528 Elab_Unit := Scop;
19529 end if;
19530
19531 Activate_Elaborate_All_Desirable (Call, Elab_Unit);
19532 Set_Suppress_Elaboration_Warnings (Elab_Unit);
19533 end Set_Elaboration_Constraint;
19534
19535 -----------------
19536 -- Spec_Entity --
19537 -----------------
19538
19539 function Spec_Entity (E : Entity_Id) return Entity_Id is
19540 Decl : Node_Id;
19541
19542 begin
19543 -- Check for case of body entity
19544 -- Why is the check for E_Void needed???
19545
19546 if Ekind_In (E, E_Void, E_Subprogram_Body, E_Package_Body) then
19547 Decl := E;
19548
19549 loop
19550 Decl := Parent (Decl);
19551 exit when Nkind (Decl) in N_Proper_Body;
19552 end loop;
19553
19554 return Corresponding_Spec (Decl);
19555
19556 else
19557 return E;
19558 end if;
19559 end Spec_Entity;
19560
19561 ------------
19562 -- Within --
19563 ------------
19564
19565 function Within (E1, E2 : Entity_Id) return Boolean is
19566 Scop : Entity_Id;
19567 begin
19568 Scop := E1;
19569 loop
19570 if Scop = E2 then
19571 return True;
19572 elsif Scop = Standard_Standard then
19573 return False;
19574 else
19575 Scop := Scope (Scop);
19576 end if;
19577 end loop;
19578 end Within;
19579
19580 --------------------------
19581 -- Within_Elaborate_All --
19582 --------------------------
19583
19584 function Within_Elaborate_All
19585 (Unit : Unit_Number_Type;
19586 E : Entity_Id) return Boolean
19587 is
19588 type Unit_Number_Set is array (Main_Unit .. Last_Unit) of Boolean;
19589 pragma Pack (Unit_Number_Set);
19590
19591 Seen : Unit_Number_Set := (others => False);
19592 -- Seen (X) is True after we have seen unit X in the walk. This is used
19593 -- to prevent processing the same unit more than once.
19594
19595 Result : Boolean := False;
19596
19597 procedure Helper (Unit : Unit_Number_Type);
19598 -- This helper procedure does all the work for Within_Elaborate_All. It
19599 -- walks the dependency graph, and sets Result to True if it finds an
19600 -- appropriate Elaborate_All.
19601
19602 ------------
19603 -- Helper --
19604 ------------
19605
19606 procedure Helper (Unit : Unit_Number_Type) is
19607 CU : constant Node_Id := Cunit (Unit);
19608
19609 Item : Node_Id;
19610 Item2 : Node_Id;
19611 Elab_Id : Entity_Id;
19612 Par : Node_Id;
19613
19614 begin
19615 if Seen (Unit) then
19616 return;
19617 else
19618 Seen (Unit) := True;
19619 end if;
19620
19621 -- First, check for Elaborate_Alls on this unit
19622
19623 Item := First (Context_Items (CU));
19624 while Present (Item) loop
19625 if Nkind (Item) = N_Pragma
19626 and then Pragma_Name (Item) = Name_Elaborate_All
19627 then
19628 -- Return if some previous error on the pragma itself. The
19629 -- pragma may be unanalyzed, because of a previous error, or
19630 -- if it is the context of a subunit, inherited by its parent.
19631
19632 if Error_Posted (Item) or else not Analyzed (Item) then
19633 return;
19634 end if;
19635
19636 Elab_Id :=
19637 Entity
19638 (Expression (First (Pragma_Argument_Associations (Item))));
19639
19640 if E = Elab_Id then
19641 Result := True;
19642 return;
19643 end if;
19644
19645 Par := Parent (Unit_Declaration_Node (Elab_Id));
19646
19647 Item2 := First (Context_Items (Par));
19648 while Present (Item2) loop
19649 if Nkind (Item2) = N_With_Clause
19650 and then Entity (Name (Item2)) = E
19651 and then not Limited_Present (Item2)
19652 then
19653 Result := True;
19654 return;
19655 end if;
19656
19657 Next (Item2);
19658 end loop;
19659 end if;
19660
19661 Next (Item);
19662 end loop;
19663
19664 -- Second, recurse on with's. We could do this as part of the above
19665 -- loop, but it's probably more efficient to have two loops, because
19666 -- the relevant Elaborate_All is likely to be on the initial unit. In
19667 -- other words, we're walking the with's breadth-first. This part is
19668 -- only necessary in the dynamic elaboration model.
19669
19670 if Dynamic_Elaboration_Checks then
19671 Item := First (Context_Items (CU));
19672 while Present (Item) loop
19673 if Nkind (Item) = N_With_Clause
19674 and then not Limited_Present (Item)
19675 then
19676 -- Note: the following call to Get_Cunit_Unit_Number does a
19677 -- linear search, which could be slow, but it's OK because
19678 -- we're about to give a warning anyway. Also, there might
19679 -- be hundreds of units, but not millions. If it turns out
19680 -- to be a problem, we could store the Get_Cunit_Unit_Number
19681 -- in each N_Compilation_Unit node, but that would involve
19682 -- rearranging N_Compilation_Unit_Aux to make room.
19683
19684 Helper (Get_Cunit_Unit_Number (Library_Unit (Item)));
19685
19686 if Result then
19687 return;
19688 end if;
19689 end if;
19690
19691 Next (Item);
19692 end loop;
19693 end if;
19694 end Helper;
19695
19696 -- Start of processing for Within_Elaborate_All
19697
19698 begin
19699 Helper (Unit);
19700 return Result;
19701 end Within_Elaborate_All;
19702
19703 end Sem_Elab;