PR sanitizer/80403
[official-gcc.git] / gcc / ada / exp_ch7.ads
blob0db3df5f07684c7ba2c4038c0cdc4219f5b07290
1 ------------------------------------------------------------------------------
2 -- --
3 -- GNAT COMPILER COMPONENTS --
4 -- --
5 -- E X P _ C H 7 --
6 -- --
7 -- S p e c --
8 -- --
9 -- Copyright (C) 1992-2016, 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 ------------------------------------------------------------------------------
26 with Namet; use Namet;
27 with Types; use Types;
29 package Exp_Ch7 is
31 procedure Expand_N_Package_Body (N : Node_Id);
32 procedure Expand_N_Package_Declaration (N : Node_Id);
34 -----------------------------
35 -- Finalization Management --
36 -----------------------------
38 procedure Build_Anonymous_Master (Ptr_Typ : Entity_Id);
39 -- Build a finalization master for an anonymous access-to-controlled type
40 -- denoted by Ptr_Typ. The master is inserted in the declarations of the
41 -- current unit.
43 procedure Build_Controlling_Procs (Typ : Entity_Id);
44 -- Typ is a record, and array type having controlled components.
45 -- Create the procedures Deep_Initialize, Deep_Adjust and Deep_Finalize
46 -- that take care of finalization management at run-time.
48 -- Support of exceptions from user finalization procedures
50 -- There is a specific mechanism to handle these exceptions, continue
51 -- finalization and then raise PE. This mechanism is used by this package
52 -- but also by exp_intr for Ada.Unchecked_Deallocation.
54 -- There are 3 subprograms to use this mechanism, and the type
55 -- Finalization_Exception_Data carries internal data between these
56 -- subprograms:
58 -- 1. Build_Object_Declaration: create the variables for the next two
59 -- subprograms.
60 -- 2. Build_Exception_Handler: create the exception handler for a call
61 -- to a user finalization procedure.
62 -- 3. Build_Raise_Stmt: create code to potentially raise a PE exception
63 -- if an exception was raise in a user finalization procedure.
65 type Finalization_Exception_Data is record
66 Loc : Source_Ptr;
67 -- Sloc for the added nodes
69 Abort_Id : Entity_Id;
70 -- Boolean variable set to true if the finalization was triggered by
71 -- an abort.
73 E_Id : Entity_Id;
74 -- Variable containing the exception occurrence raised by user code
76 Raised_Id : Entity_Id;
77 -- Boolean variable set to true if an exception was raised in user code
78 end record;
80 function Build_Exception_Handler
81 (Data : Finalization_Exception_Data;
82 For_Library : Boolean := False) return Node_Id;
83 -- Subsidiary to Build_Finalizer, Make_Deep_Array_Body and Make_Deep_Record
84 -- _Body. Create an exception handler of the following form:
86 -- when others =>
87 -- if not Raised_Id then
88 -- Raised_Id := True;
89 -- Save_Occurrence (E_Id, Get_Current_Excep.all.all);
90 -- end if;
92 -- If flag For_Library is set (and not in restricted profile):
94 -- when others =>
95 -- if not Raised_Id then
96 -- Raised_Id := True;
97 -- Save_Library_Occurrence (Get_Current_Excep.all);
98 -- end if;
100 -- E_Id denotes the defining identifier of a local exception occurrence.
101 -- Raised_Id is the entity of a local boolean flag. Flag For_Library is
102 -- used when operating at the library level, when enabled the current
103 -- exception will be saved to a global location.
105 procedure Build_Finalization_Master
106 (Typ : Entity_Id;
107 For_Lib_Level : Boolean := False;
108 For_Private : Boolean := False;
109 Context_Scope : Entity_Id := Empty;
110 Insertion_Node : Node_Id := Empty);
111 -- Build a finalization master for an access type. The designated type may
112 -- not necessarily be controlled or need finalization actions depending on
113 -- the context. Flag For_Lib_Level must be set when creating a master for a
114 -- build-in-place function call access result type. Flag For_Private must
115 -- be set when the designated type contains a private component. Parameters
116 -- Context_Scope and Insertion_Node must be used in conjunction with flag
117 -- For_Private. Context_Scope is the scope of the context where the
118 -- finalization master must be analyzed. Insertion_Node is the insertion
119 -- point before which the master is to be inserted.
121 procedure Build_Invariant_Procedure_Body
122 (Typ : Entity_Id;
123 Partial_Invariant : Boolean := False);
124 -- Create the body of the procedure which verifies the invariants of type
125 -- Typ at runtime. Flag Partial_Invariant should be set when Typ denotes a
126 -- private type, otherwise it is assumed that Typ denotes the full view of
127 -- a private type.
129 procedure Build_Invariant_Procedure_Declaration
130 (Typ : Entity_Id;
131 Partial_Invariant : Boolean := False);
132 -- Create the declaration of the procedure which verifies the invariants of
133 -- type Typ at runtime. Flag Partial_Invariant should be set when building
134 -- the invariant procedure for a private type.
136 procedure Build_Late_Proc (Typ : Entity_Id; Nam : Name_Id);
137 -- Build one controlling procedure when a late body overrides one of the
138 -- controlling operations.
140 procedure Build_Object_Declarations
141 (Data : out Finalization_Exception_Data;
142 Decls : List_Id;
143 Loc : Source_Ptr;
144 For_Package : Boolean := False);
145 -- Subsidiary to Make_Deep_Array_Body and Make_Deep_Record_Body. Create the
146 -- list List containing the object declarations of boolean flag Abort_Id,
147 -- the exception occurrence E_Id and boolean flag Raised_Id.
149 -- Abort_Id : constant Boolean :=
150 -- Exception_Identity (Get_Current_Excep.all) =
151 -- Standard'Abort_Signal'Identity;
152 -- <or>
153 -- Abort_Id : constant Boolean := False; -- no abort or For_Package
155 -- E_Id : Exception_Occurrence;
156 -- Raised_Id : Boolean := False;
158 function Build_Raise_Statement
159 (Data : Finalization_Exception_Data) return Node_Id;
160 -- Subsidiary to routines Build_Finalizer, Make_Deep_Array_Body and Make_
161 -- Deep_Record_Body. Generate the following conditional raise statement:
163 -- if Raised_Id and then not Abort_Id then
164 -- Raise_From_Controlled_Operation (E_Id);
165 -- end if;
167 -- Abort_Id is a local boolean flag which is set when the finalization was
168 -- triggered by an abort, E_Id denotes the defining identifier of a local
169 -- exception occurrence, Raised_Id is the entity of a local boolean flag.
171 function CW_Or_Has_Controlled_Part (T : Entity_Id) return Boolean;
172 -- True if T is a class-wide type, or if it has controlled parts ("part"
173 -- means T or any of its subcomponents). Same as Needs_Finalization, except
174 -- when pragma Restrictions (No_Finalization) applies, in which case we
175 -- know that class-wide objects do not contain controlled parts.
177 function Has_New_Controlled_Component (E : Entity_Id) return Boolean;
178 -- E is a type entity. Give the same result as Has_Controlled_Component
179 -- except for tagged extensions where the result is True only if the
180 -- latest extension contains a controlled component.
182 function Make_Adjust_Call
183 (Obj_Ref : Node_Id;
184 Typ : Entity_Id;
185 Skip_Self : Boolean := False) return Node_Id;
186 -- Create a call to either Adjust or Deep_Adjust depending on the structure
187 -- of type Typ. Obj_Ref is an expression with no side effects (not required
188 -- to have been previously analyzed) that references the object to be
189 -- adjusted. Typ is the expected type of Obj_Ref. When Skip_Self is set,
190 -- only the components (if any) are adjusted. Return Empty if Adjust or
191 -- Deep_Adjust is not available, possibly due to previous errors.
193 function Make_Detach_Call (Obj_Ref : Node_Id) return Node_Id;
194 -- Create a call to unhook an object from an arbitrary list. Obj_Ref is the
195 -- object. Generate the following:
197 -- Ada.Finalization.Heap_Management.Detach
198 -- (System.Finalization_Root.Root_Controlled_Ptr (Obj_Ref));
200 function Make_Final_Call
201 (Obj_Ref : Node_Id;
202 Typ : Entity_Id;
203 Skip_Self : Boolean := False) return Node_Id;
204 -- Create a call to either Finalize or Deep_Finalize, depending on the
205 -- structure of type Typ. Obj_Ref is an expression (with no side effects
206 -- and is not required to have been previously analyzed) that references
207 -- the object to be finalized. Typ is the expected type of Obj_Ref. When
208 -- Skip_Self is set, only the components (if any) are finalized. Return
209 -- Empty if Finalize or Deep_Finalize is not available, possibly due to
210 -- previous errors.
212 procedure Make_Finalize_Address_Body (Typ : Entity_Id);
213 -- Create the body of TSS routine Finalize_Address if Typ is controlled and
214 -- does not have a TSS entry for Finalize_Address. The procedure converts
215 -- an address into a pointer and subsequently calls Deep_Finalize on the
216 -- dereference.
218 function Make_Init_Call
219 (Obj_Ref : Node_Id;
220 Typ : Entity_Id) return Node_Id;
221 -- Create a call to either Initialize or Deep_Initialize, depending on the
222 -- structure of type Typ. Obj_Ref is an expression with no side effects
223 -- (not required to have been previously analyzed) that references the
224 -- object to be initialized. Typ is the expected type of Obj_Ref. Return
225 -- Empty if Initialize or Deep_Initialize is not available, possibly due to
226 -- previous errors.
228 function Make_Handler_For_Ctrl_Operation (Loc : Source_Ptr) return Node_Id;
229 -- Generate an implicit exception handler with an 'others' choice,
230 -- converting any occurrence to a raise of Program_Error.
232 function Make_Local_Deep_Finalize
233 (Typ : Entity_Id;
234 Nam : Entity_Id) return Node_Id;
235 -- Create a special version of Deep_Finalize with identifier Nam. The
236 -- routine has state information and can perform partial finalization.
238 function Make_Set_Finalize_Address_Call
239 (Loc : Source_Ptr;
240 Ptr_Typ : Entity_Id) return Node_Id;
241 -- Associate the Finalize_Address primitive of the designated type with the
242 -- finalization master of access type Ptr_Typ. The returned call is:
244 -- Set_Finalize_Address
245 -- (<Ptr_Typ>FM, <Desig_Typ>FD'Unrestricted_Access);
247 --------------------------------------------
248 -- Task and Protected Object finalization --
249 --------------------------------------------
251 function Cleanup_Array
252 (N : Node_Id;
253 Obj : Node_Id;
254 Typ : Entity_Id) return List_Id;
255 -- Generate loops to finalize any tasks or simple protected objects that
256 -- are subcomponents of an array.
258 function Cleanup_Protected_Object
259 (N : Node_Id;
260 Ref : Node_Id) return Node_Id;
261 -- Generate code to finalize a protected object without entries
263 function Cleanup_Record
264 (N : Node_Id;
265 Obj : Node_Id;
266 Typ : Entity_Id) return List_Id;
267 -- For each subcomponent of a record that contains tasks or simple
268 -- protected objects, generate the appropriate finalization call.
270 function Cleanup_Task
271 (N : Node_Id;
272 Ref : Node_Id) return Node_Id;
273 -- Generate code to finalize a task
275 function Has_Simple_Protected_Object (T : Entity_Id) return Boolean;
276 -- Check whether composite type contains a simple protected component
278 function Is_Simple_Protected_Type (T : Entity_Id) return Boolean;
279 -- Determine whether T denotes a protected type without entries whose
280 -- _object field is of type System.Tasking.Protected_Objects.Protection.
281 -- Something wrong here, implementation was changed to test Lock_Free
282 -- but this spec does not mention that ???
284 --------------------------------
285 -- Transient Scope Management --
286 --------------------------------
288 procedure Expand_Cleanup_Actions (N : Node_Id);
289 -- Expand the necessary stuff into a scope to enable finalization of local
290 -- objects and deallocation of transient data when exiting the scope. N is
291 -- a "scope node" that is to say one of the following: N_Block_Statement,
292 -- N_Subprogram_Body, N_Task_Body, N_Entry_Body.
294 procedure Establish_Transient_Scope (N : Node_Id; Sec_Stack : Boolean);
295 -- Push a new transient scope on the scope stack. N is the node responsible
296 -- for the need of a transient scope. If Sec_Stack is True then the
297 -- secondary stack is brought in, otherwise it isn't.
299 function Node_To_Be_Wrapped return Node_Id;
300 -- Return the node to be wrapped if the current scope is transient
302 procedure Store_Before_Actions_In_Scope (L : List_Id);
303 -- Append the list L of actions to the end of the before-actions store in
304 -- the top of the scope stack (also analyzes these actions).
306 procedure Store_After_Actions_In_Scope (L : List_Id);
307 -- Prepend the list L of actions to the beginning of the after-actions
308 -- stored in the top of the scope stack (also analyzes these actions).
310 -- Note that we are prepending here rather than appending. This means that
311 -- if several calls are made to this procedure for the same scope, the
312 -- actions will be executed in reverse order of the calls (actions for the
313 -- last call executed first). Within the list L for a single call, the
314 -- actions are executed in the order in which they appear in this list.
316 procedure Store_Cleanup_Actions_In_Scope (L : List_Id);
317 -- Prepend the list L of actions to the beginning of the cleanup-actions
318 -- store in the top of the scope stack.
320 procedure Wrap_Transient_Declaration (N : Node_Id);
321 -- N is an object declaration. Expand the finalization calls after the
322 -- declaration and make the outer scope being the transient one.
324 procedure Wrap_Transient_Expression (N : Node_Id);
325 -- N is a sub-expression. Expand a transient block around an expression
327 procedure Wrap_Transient_Statement (N : Node_Id);
328 -- N is a statement. Expand a transient block around an instruction
330 end Exp_Ch7;