4 -- Grant of Unlimited Rights
6 -- Under contracts F33600-87-D-0337, F33600-84-D-0280, MDA903-79-C-0687,
7 -- F08630-91-C-0015, and DCA100-97-D-0025, the U.S. Government obtained
8 -- unlimited rights in the software and documentation contained herein.
9 -- Unlimited rights are defined in DFAR 252.227-7013(a)(19). By making
10 -- this public release, the Government intends to confer upon all
11 -- recipients unlimited rights equal to those held by the Government.
12 -- These rights include rights to use, duplicate, release or disclose the
13 -- released technical data and computer software in whole or in part, in
14 -- any manner and for any purpose whatsoever, and to have or permit others
19 -- ALL MATERIALS OR INFORMATION HEREIN RELEASED, MADE AVAILABLE OR
20 -- DISCLOSED ARE AS IS. THE GOVERNMENT MAKES NO EXPRESS OR IMPLIED
21 -- WARRANTY AS TO ANY MATTER WHATSOEVER, INCLUDING THE CONDITIONS OF THE
22 -- SOFTWARE, DOCUMENTATION OR OTHER INFORMATION RELEASED, MADE AVAILABLE
23 -- OR DISCLOSED, OR THE OWNERSHIP, MERCHANTABILITY, OR FITNESS FOR A
24 -- PARTICULAR PURPOSE OF SAID MATERIAL.
28 -- Check that if a finalize procedure invoked by a transfer of control
29 -- due to selection of a terminate alternative attempts to propagate an
30 -- exception, the exception is ignored, but any other finalizations due
31 -- to be performed are performed.
35 -- This test declares a nested controlled data type, and embeds an object
36 -- of that type within a protected type. Objects of the protected type
37 -- are created and destroyed, and the actions of the embedded controlled
38 -- object are checked. The container controlled type causes an exception
39 -- as the last part of it's finalization operation.
41 -- This test utilizes several tasks to accomplish the objective. The
42 -- tasks contain delays to ensure that the expected order of processing
43 -- is indeed accomplished.
46 -- local task object runs to normal completion
49 -- local task aborts a nested task to cause finalization
52 -- local task sleeps long enough to allow procedure started
53 -- asynchronously to go into infinite loop. Procedure is then aborted
54 -- via ATC, causing finalization of objects.
57 -- local task object takes terminate alternative, causing finalization
61 -- 06 JUN 95 SAIC Initial version
62 -- 05 APR 96 SAIC Documentation changes
63 -- 03 MAR 97 PWB.CTA Allowed two finalization orders for ATC test
64 -- 02 DEC 97 EDS Remove duplicate characters from check string.
67 ---------------------------------------------------------------- C761007_0
69 with Ada
.Finalization
;
72 type Internal
is new Ada
.Finalization
.Controlled
77 procedure Finalize
( I
: in out Internal
);
79 Side_Effect
: String(1..80); -- way bigger than needed
80 Side_Effect_Finger
: Natural := 0;
84 -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
87 package body C761007_0
is
89 procedure Finalize
( I
: in out Internal
) is
90 Previous_Side_Effect
: Boolean := False;
92 -- look to see if this character has been finalized yet
93 for SEI
in 1..Side_Effect_Finger
loop
94 Previous_Side_Effect
:= Previous_Side_Effect
95 or Side_Effect
(Side_Effect_Finger
) = I
.Effect
;
98 -- if not, then tack it on to the string, and touch the character
99 if not Previous_Side_Effect
then
100 Side_Effect_Finger
:= Side_Effect_Finger
+1;
101 Side_Effect
(Side_Effect_Finger
) := I
.Effect
;
102 TCTouch
.Touch
(I
.Effect
);
109 ---------------------------------------------------------------- C761007_1
112 with Ada
.Finalization
;
115 type Container
is new Ada
.Finalization
.Controlled
118 Content
: C761007_0
.Internal
;
121 procedure Finalize
( C
: in out Container
);
123 Side_Effect
: String(1..80); -- way bigger than needed
124 Side_Effect_Finger
: Natural := 0;
126 This_Exception_Is_Supposed_To_Be_Ignored
: exception;
130 -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
133 package body C761007_1
is
135 procedure Finalize
( C
: in out Container
) is
136 Previous_Side_Effect
: Boolean := False;
138 -- look to see if this character has been finalized yet
139 for SEI
in 1..Side_Effect_Finger
loop
140 Previous_Side_Effect
:= Previous_Side_Effect
141 or Side_Effect
(Side_Effect_Finger
) = C
.Effect
;
144 -- if not, then tack it on to the string, and touch the character
145 if not Previous_Side_Effect
then
146 Side_Effect_Finger
:= Side_Effect_Finger
+1;
147 Side_Effect
(Side_Effect_Finger
) := C
.Effect
;
148 TCTouch
.Touch
(C
.Effect
);
151 raise This_Exception_Is_Supposed_To_Be_Ignored
;
157 ---------------------------------------------------------------- C761007_2
161 protected type Prot_W_Fin_Obj
is
162 procedure Set_Effects
( Container
, Filling
: Character );
164 The_Data_Under_Test
: C761007_1
.Container
;
165 -- finalization for this will occur when the Prot_W_Fin_Obj object
166 -- "goes out of existence" for whatever reason.
171 -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
173 package body C761007_2
is
175 protected body Prot_W_Fin_Obj
is
176 procedure Set_Effects
( Container
, Filling
: Character ) is
178 The_Data_Under_Test
.Effect
:= Container
; -- A, etc.
179 The_Data_Under_Test
.Content
.Effect
:= Filling
; -- B, etc.
185 ------------------------------------------------------------------ C761007
195 task type Subtests
( Outer
, Inner
: Character) is
200 task body Subtests
is
201 Local_Prot_W_Fin_Obj
: C761007_2
.Prot_W_Fin_Obj
;
203 Local_Prot_W_Fin_Obj
.Set_Effects
( Outer
, Inner
);
209 or terminate; -- used in Subtest 4
212 -- the exception caused by the finalization of Local_Prot_W_Fin_Obj
213 -- should never be visible to this scope.
214 when others => Report
.Failed
("Exception in a Subtest object "
218 procedure Subtest_1
is
219 -- check the case where "nothing special" happens.
221 This_Subtest
: Subtests
( 'A', 'B' );
225 This_Subtest
.Complete
;
227 while not This_Subtest
'Terminated loop -- wait for finalization
228 delay Impdef
.Clear_Ready_Queue
;
231 -- in the finalization of This_Subtest, the controlled object embedded in
232 -- the Prot_W_Fin_Obj will finalize. An exception is raised in the
233 -- container object, after "touching" it's tag character.
234 -- The finalization of the contained controlled object must be performed.
237 TCTouch
.Validate
( "AB", "Item embedded in task" );
241 when others => Report
.Failed
("Undesirable exception in Subtest_1");
245 procedure Subtest_2
is
246 -- check for explicit abort
252 task body Subtest_Task
is
256 Deep_Nesting
: Subtests
( 'E', 'F' );
258 if Report
.Ident_Bool
( True ) then
259 -- controlled objects have been created in the elaboration of
260 -- Deep_Nesting. Deep_Nesting must call the Set_Effects operation
261 -- in the Prot_W_Fin_Obj, and then hang waiting for the Complete
266 Report
.Failed
("Dead code in Nesting");
269 when others => Report
.Failed
("Exception in Subtest_Task.Nesting");
272 Local_2
: C761007_2
.Prot_W_Fin_Obj
;
275 -- Nesting has activated at this point, which implies the activation
276 -- of Deep_Nesting as well.
278 Local_2
.Set_Effects
( 'C', 'D' );
280 -- wait for Nesting to terminate
282 while not Nesting
'Terminated loop
283 delay Impdef
.Clear_Ready_Queue
;
289 when others => Report
.Failed
("Exception in Subtest_Task");
294 -- wait for everything in Subtest_Task to happen
295 Subtest_Task
.Complete
;
297 while not Subtest_Task
'Terminated loop -- wait for finalization
298 delay Impdef
.Clear_Ready_Queue
;
301 TCTouch
.Validate
( "EFCD", "Aborted nested task" );
304 when others => Report
.Failed
("Undesirable exception in Subtest_2");
307 procedure Subtest_3
is
308 -- check abort caused by asynchronous transfer of control
310 task Subtest_3_Task
is
314 procedure Check_Atc_Operation
is
315 Check_Atc
: C761007_2
.Prot_W_Fin_Obj
;
318 Check_Atc
.Set_Effects
( 'G', 'H' );
321 while Report
.Ident_Bool
( True ) loop -- wait to be aborted
322 if Report
.Ident_Bool
( True ) then
323 Impdef
.Exceed_Time_Slice
;
324 delay Impdef
.Switch_To_New_Task
;
326 Report
.Failed
("Optimization prevention");
330 Report
.Failed
("Check_Atc_Operation loop completed");
332 end Check_Atc_Operation
;
334 task body Subtest_3_Task
is
340 Nesting_3
: C761007_2
.Prot_W_Fin_Obj
;
342 Nesting_3
.Set_Effects
( 'G', 'H' );
344 -- give Check_Atc_Operation sufficient time to perform it's
345 -- Set_Effects on it's local Prot_W_Fin_Obj object
346 delay Impdef
.Clear_Ready_Queue
;
350 when others => Report
.Failed
("Exception in Subtest_3_Task.Nesting");
353 Local_3
: C761007_2
.Prot_W_Fin_Obj
;
355 begin -- Subtest_3_Task
357 Local_3
.Set_Effects
( 'I', 'J' );
361 then abort ---------------------------------------------------- cause KL
368 when others => Report
.Failed
("Exception in Subtest_3_Task");
372 Subtest_3_Task
.Complete
;
374 while not Subtest_3_Task
'Terminated loop -- wait for finalization
375 delay Impdef
.Clear_Ready_Queue
;
378 TCTouch
.Validate
( "GHIJ", "Asynchronously aborted operation" );
381 when others => Report
.Failed
("Undesirable exception in Subtest_3");
384 procedure Subtest_4
is
385 -- check the case where transfer is caused by terminate alternative
386 -- highly similar to Subtest_1
388 This_Subtest
: Subtests
( 'M', 'N' );
392 -- don't call This_Subtest.Complete;
395 when others => Report
.Failed
("Undesirable exception in Subtest_4");
399 begin -- Main test procedure.
401 Report
.Test
("C761007", "Check that if a finalize procedure invoked by " &
402 "a transfer of control or selection of a " &
403 "terminate alternative attempts to propagate " &
404 "an exception, the exception is ignored, but " &
405 "any other finalizations due to be performed " &
408 Subtest_1
; -- checks internal
410 Subtest_2
; -- checks internal
412 Subtest_3
; -- checks internal
415 TCTouch
.Validate
( "MN", "transfer due to terminate alternative" );