1------------------------------------------------------------------------------
2--                                                                          --
3--                         GNAT COMPILER COMPONENTS                         --
4--                                                                          --
5--                              P A R . C H 9                               --
6--                                                                          --
7--                                 B o d y                                  --
8--                                                                          --
9--          Copyright (C) 1992-2015, 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
26pragma Style_Checks (All_Checks);
27--  Turn off subprogram body ordering check. Subprograms are in order by RM
28--  section rather than alphabetical.
29
30separate (Par)
31package body Ch9 is
32
33   --  Local subprograms, used only in this chapter
34
35   function P_Accept_Alternative                   return Node_Id;
36   function P_Delay_Alternative                    return Node_Id;
37   function P_Delay_Relative_Statement             return Node_Id;
38   function P_Delay_Until_Statement                return Node_Id;
39   function P_Entry_Barrier                        return Node_Id;
40   function P_Entry_Body_Formal_Part               return Node_Id;
41   function P_Entry_Declaration                    return Node_Id;
42   function P_Entry_Index_Specification            return Node_Id;
43   function P_Protected_Definition                 return Node_Id;
44   function P_Protected_Operation_Declaration_Opt  return Node_Id;
45   function P_Protected_Operation_Items            return List_Id;
46   function P_Task_Items                           return List_Id;
47   function P_Task_Definition return Node_Id;
48
49   -----------------------------
50   -- 9.1  Task (also 10.1.3) --
51   -----------------------------
52
53   --  TASK_TYPE_DECLARATION ::=
54   --    task type DEFINING_IDENTIFIER [KNOWN_DISCRIMINANT_PART]
55   --      [ASPECT_SPECIFICATIONS]
56   --      [is [new INTERFACE_LIST with] TASK_DEFINITION];
57
58   --  SINGLE_TASK_DECLARATION ::=
59   --    task DEFINING_IDENTIFIER
60   --      [ASPECT_SPECIFICATIONS]
61   --      [is [new INTERFACE_LIST with] TASK_DEFINITION];
62
63   --  TASK_BODY ::=
64   --    task body DEFINING_IDENTIFIER [ASPECT_SPECIFICATIONS] is
65   --      DECLARATIVE_PART
66   --    begin
67   --      HANDLED_SEQUENCE_OF_STATEMENTS
68   --    end [task_IDENTIFIER]
69
70   --  TASK_BODY_STUB ::=
71   --    task body DEFINING_IDENTIFIER is separate
72   --      [ASPECT_SPECIFICATIONS];
73
74   --  This routine scans out a task declaration, task body, or task stub
75
76   --  The caller has checked that the initial token is TASK and scanned
77   --  past it, so that Token is set to the token after TASK
78
79   --  Error recovery: cannot raise Error_Resync
80
81   function P_Task return Node_Id is
82      Aspect_Sloc : Source_Ptr;
83      Name_Node   : Node_Id;
84      Task_Node   : Node_Id;
85      Task_Sloc   : Source_Ptr;
86
87      Dummy_Node : constant Node_Id := New_Node (N_Task_Body, Token_Ptr);
88      --  Placeholder node used to hold legal or prematurely declared aspect
89      --  specifications. Depending on the context, the aspect specifications
90      --  may be moved to a new node.
91
92   begin
93      Push_Scope_Stack;
94      Scope.Table (Scope.Last).Etyp := E_Name;
95      Scope.Table (Scope.Last).Ecol := Start_Column;
96      Scope.Table (Scope.Last).Sloc := Token_Ptr;
97      Scope.Table (Scope.Last).Lreq := False;
98      Task_Sloc := Prev_Token_Ptr;
99
100      if Token = Tok_Body then
101         Scan; -- past BODY
102         Name_Node := P_Defining_Identifier (C_Is);
103         Scope.Table (Scope.Last).Labl := Name_Node;
104
105         if Token = Tok_Left_Paren then
106            Error_Msg_SC ("discriminant part not allowed in task body");
107            Discard_Junk_List (P_Known_Discriminant_Part_Opt);
108         end if;
109
110         if Aspect_Specifications_Present then
111            Aspect_Sloc := Token_Ptr;
112            P_Aspect_Specifications (Dummy_Node, Semicolon => False);
113         end if;
114
115         TF_Is;
116
117         --  Task stub
118
119         if Token = Tok_Separate then
120            Scan; -- past SEPARATE
121            Task_Node := New_Node (N_Task_Body_Stub, Task_Sloc);
122            Set_Defining_Identifier (Task_Node, Name_Node);
123
124            if Has_Aspects (Dummy_Node) then
125               Error_Msg
126                 ("aspect specifications must come after SEPARATE",
127                  Aspect_Sloc);
128            end if;
129
130            P_Aspect_Specifications (Task_Node, Semicolon => False);
131            TF_Semicolon;
132            Pop_Scope_Stack; -- remove unused entry
133
134         --  Task body
135
136         else
137            Task_Node := New_Node (N_Task_Body, Task_Sloc);
138            Set_Defining_Identifier (Task_Node, Name_Node);
139
140            --  Move the aspect specifications to the body node
141
142            if Has_Aspects (Dummy_Node) then
143               Move_Aspects (From => Dummy_Node, To => Task_Node);
144            end if;
145
146            Parse_Decls_Begin_End (Task_Node);
147
148            --  The statement list of a task body needs to include at least a
149            --  null statement, so if a parsing error produces an empty list,
150            --  patch it now.
151
152            if No (First (Statements
153                           (Handled_Statement_Sequence (Task_Node))))
154            then
155               Set_Statements (Handled_Statement_Sequence (Task_Node),
156                 New_List (Make_Null_Statement (Token_Ptr)));
157            end if;
158         end if;
159
160         return Task_Node;
161
162      --  Otherwise we must have a task declaration
163
164      else
165         if Token = Tok_Type then
166            Scan; -- past TYPE
167            Task_Node := New_Node (N_Task_Type_Declaration, Task_Sloc);
168            Name_Node := P_Defining_Identifier;
169            Set_Defining_Identifier (Task_Node, Name_Node);
170            Scope.Table (Scope.Last).Labl := Name_Node;
171            Set_Discriminant_Specifications
172              (Task_Node, P_Known_Discriminant_Part_Opt);
173
174         else
175            Task_Node := New_Node (N_Single_Task_Declaration, Task_Sloc);
176            Name_Node := P_Defining_Identifier (C_Is);
177            Set_Defining_Identifier (Task_Node, Name_Node);
178            Scope.Table (Scope.Last).Labl := Name_Node;
179
180            if Token = Tok_Left_Paren then
181               Error_Msg_SC ("discriminant part not allowed for single task");
182               Discard_Junk_List (P_Known_Discriminant_Part_Opt);
183            end if;
184         end if;
185
186         --  Scan aspect specifications, don't eat the semicolon, since it
187         --  might not be there if we have an IS.
188
189         P_Aspect_Specifications (Task_Node, Semicolon => False);
190
191         --  Parse optional task definition. Note that P_Task_Definition scans
192         --  out the semicolon and possible aspect specifications as well as
193         --  the task definition itself.
194
195         if Token = Tok_Semicolon then
196
197            --  A little check, if the next token after semicolon is Entry,
198            --  then surely the semicolon should really be IS
199
200            Scan; -- past semicolon
201
202            if Token = Tok_Entry then
203               Error_Msg_SP -- CODEFIX
204                 ("|"";"" should be IS");
205               Set_Task_Definition (Task_Node, P_Task_Definition);
206            else
207               Pop_Scope_Stack; -- Remove unused entry
208            end if;
209
210         --  Here we have a task definition
211
212         else
213            TF_Is; -- must have IS if no semicolon
214
215            --  Ada 2005 (AI-345)
216
217            if Token = Tok_New then
218               Scan; --  past NEW
219
220               if Ada_Version < Ada_2005 then
221                  Error_Msg_SP ("task interface is an Ada 2005 extension");
222                  Error_Msg_SP ("\unit must be compiled with -gnat05 switch");
223               end if;
224
225               Set_Interface_List (Task_Node, New_List);
226
227               loop
228                  Append (P_Qualified_Simple_Name, Interface_List (Task_Node));
229                  exit when Token /= Tok_And;
230                  Scan; --  past AND
231               end loop;
232
233               if Token /= Tok_With then
234                  Error_Msg_SC -- CODEFIX
235                    ("WITH expected");
236               end if;
237
238               Scan; -- past WITH
239
240               if Token = Tok_Private then
241                  Error_Msg_SP -- CODEFIX
242                    ("PRIVATE not allowed in task type declaration");
243               end if;
244            end if;
245
246            Set_Task_Definition (Task_Node, P_Task_Definition);
247         end if;
248
249         return Task_Node;
250      end if;
251   end P_Task;
252
253   --------------------------------
254   -- 9.1  Task Type Declaration --
255   --------------------------------
256
257   --  Parsed by P_Task (9.1)
258
259   ----------------------------------
260   -- 9.1  Single Task Declaration --
261   ----------------------------------
262
263   --  Parsed by P_Task (9.1)
264
265   --------------------------
266   -- 9.1  Task Definition --
267   --------------------------
268
269   --  TASK_DEFINITION ::=
270   --      {TASK_ITEM}
271   --    [private
272   --      {TASK_ITEM}]
273   --    end [task_IDENTIFIER];
274
275   --  The caller has already made the scope stack entry
276
277   --  Note: there is a small deviation from official syntax here in that we
278   --  regard the semicolon after end as part of the Task_Definition, and in
279   --  the official syntax, it's part of the enclosing declaration. The reason
280   --  for this deviation is that otherwise the end processing would have to
281   --  be special cased, which would be a nuisance.
282
283   --  Error recovery:  cannot raise Error_Resync
284
285   function P_Task_Definition return Node_Id is
286      Def_Node  : Node_Id;
287
288   begin
289      Def_Node := New_Node (N_Task_Definition, Token_Ptr);
290      Set_Visible_Declarations (Def_Node, P_Task_Items);
291
292      if Token = Tok_Private then
293         Scan; -- past PRIVATE
294         Set_Private_Declarations (Def_Node, P_Task_Items);
295
296         --  Deal gracefully with multiple PRIVATE parts
297
298         while Token = Tok_Private loop
299            Error_Msg_SC ("only one private part allowed per task");
300            Scan; -- past PRIVATE
301            Append_List (P_Task_Items, Private_Declarations (Def_Node));
302         end loop;
303      end if;
304
305      End_Statements (Def_Node);
306      return Def_Node;
307   end P_Task_Definition;
308
309   --------------------
310   -- 9.1  Task Item --
311   --------------------
312
313   --  TASK_ITEM ::= ENTRY_DECLARATION | REPRESENTATION_CLAUSE
314
315   --  This subprogram scans a (possibly empty) list of task items and pragmas
316
317   --  Error recovery:  cannot raise Error_Resync
318
319   --  Note: a pragma can also be returned in this position
320
321   function P_Task_Items return List_Id is
322      Items      : List_Id;
323      Item_Node  : Node_Id;
324      Decl_Sloc  : Source_Ptr;
325
326   begin
327      --  Get rid of active SIS entry from outer scope. This means we will
328      --  miss some nested cases, but it doesn't seem worth the effort. See
329      --  discussion in Par for further details
330
331      SIS_Entry_Active := False;
332
333      --  Loop to scan out task items
334
335      Items := New_List;
336
337      Decl_Loop : loop
338         Decl_Sloc := Token_Ptr;
339
340         if Token = Tok_Pragma then
341            Append (P_Pragma, Items);
342
343         --  Ada 2005 (AI-397): Reserved words NOT and OVERRIDING
344         --  may begin an entry declaration.
345
346         elsif Token = Tok_Entry
347           or else Token = Tok_Not
348           or else Token = Tok_Overriding
349         then
350            Append (P_Entry_Declaration, Items);
351
352         elsif Token = Tok_For then
353            --  Representation clause in task declaration. The only rep
354            --  clause which is legal in a protected is an address clause,
355            --  so that is what we try to scan out.
356
357            Item_Node := P_Representation_Clause;
358
359            if Nkind (Item_Node) = N_At_Clause then
360               Append (Item_Node, Items);
361
362            elsif Nkind (Item_Node) = N_Attribute_Definition_Clause
363              and then Chars (Item_Node) = Name_Address
364            then
365               Append (Item_Node, Items);
366
367            else
368               Error_Msg
369                 ("the only representation clause " &
370                  "allowed here is an address clause!", Decl_Sloc);
371            end if;
372
373         elsif Token = Tok_Identifier
374           or else Token in Token_Class_Declk
375         then
376            Error_Msg_SC ("illegal declaration in task definition");
377            Resync_Past_Semicolon;
378
379         else
380            exit Decl_Loop;
381         end if;
382      end loop Decl_Loop;
383
384      return Items;
385   end P_Task_Items;
386
387   --------------------
388   -- 9.1  Task Body --
389   --------------------
390
391   --  Parsed by P_Task (9.1)
392
393   ----------------------------------
394   -- 9.4  Protected (also 10.1.3) --
395   ----------------------------------
396
397   --  PROTECTED_TYPE_DECLARATION ::=
398   --    protected type DEFINING_IDENTIFIER [KNOWN_DISCRIMINANT_PART]
399   --      [ASPECT_SPECIFICATIONS]
400   --    is [new INTERFACE_LIST with] PROTECTED_DEFINITION;
401
402   --  SINGLE_PROTECTED_DECLARATION ::=
403   --    protected DEFINING_IDENTIFIER
404   --      [ASPECT_SPECIFICATIONS]
405   --    is [new INTERFACE_LIST with] PROTECTED_DEFINITION;
406
407   --  PROTECTED_BODY ::=
408   --    protected body DEFINING_IDENTIFIER
409   --      [ASPECT_SPECIFICATIONS]
410   --    is
411   --      {PROTECTED_OPERATION_ITEM}
412   --    end [protected_IDENTIFIER];
413
414   --  PROTECTED_BODY_STUB ::=
415   --    protected body DEFINING_IDENTIFIER is separate
416   --      [ASPECT_SPECIFICATIONS];
417
418   --  This routine scans out a protected declaration, protected body
419   --  or a protected stub.
420
421   --  The caller has checked that the initial token is PROTECTED and
422   --  scanned past it, so Token is set to the following token.
423
424   --  Error recovery: cannot raise Error_Resync
425
426   function P_Protected return Node_Id is
427      Aspect_Sloc    : Source_Ptr;
428      Name_Node      : Node_Id;
429      Protected_Node : Node_Id;
430      Protected_Sloc : Source_Ptr;
431      Scan_State     : Saved_Scan_State;
432
433      Dummy_Node : constant Node_Id := New_Node (N_Protected_Body, Token_Ptr);
434      --  Placeholder node used to hold legal or prematurely declared aspect
435      --  specifications. Depending on the context, the aspect specifications
436      --  may be moved to a new node.
437
438   begin
439      Push_Scope_Stack;
440      Scope.Table (Scope.Last).Etyp := E_Name;
441      Scope.Table (Scope.Last).Ecol := Start_Column;
442      Scope.Table (Scope.Last).Lreq := False;
443      Protected_Sloc := Prev_Token_Ptr;
444
445      if Token = Tok_Body then
446         Scan; -- past BODY
447         Name_Node := P_Defining_Identifier (C_Is);
448         Scope.Table (Scope.Last).Labl := Name_Node;
449
450         if Token = Tok_Left_Paren then
451            Error_Msg_SC ("discriminant part not allowed in protected body");
452            Discard_Junk_List (P_Known_Discriminant_Part_Opt);
453         end if;
454
455         if Aspect_Specifications_Present then
456            Aspect_Sloc := Token_Ptr;
457            P_Aspect_Specifications (Dummy_Node, Semicolon => False);
458         end if;
459
460         TF_Is;
461
462         --  Protected stub
463
464         if Token = Tok_Separate then
465            Scan; -- past SEPARATE
466
467            Protected_Node := New_Node (N_Protected_Body_Stub, Protected_Sloc);
468            Set_Defining_Identifier (Protected_Node, Name_Node);
469
470            if Has_Aspects (Dummy_Node) then
471               Error_Msg
472                 ("aspect specifications must come after SEPARATE",
473                  Aspect_Sloc);
474            end if;
475
476            P_Aspect_Specifications (Protected_Node, Semicolon => False);
477            TF_Semicolon;
478            Pop_Scope_Stack; -- remove unused entry
479
480         --  Protected body
481
482         else
483            Protected_Node := New_Node (N_Protected_Body, Protected_Sloc);
484            Set_Defining_Identifier (Protected_Node, Name_Node);
485
486            Move_Aspects (From => Dummy_Node, To => Protected_Node);
487            Set_Declarations (Protected_Node, P_Protected_Operation_Items);
488            End_Statements (Protected_Node);
489         end if;
490
491         return Protected_Node;
492
493      --  Otherwise we must have a protected declaration
494
495      else
496         if Token = Tok_Type then
497            Scan; -- past TYPE
498            Protected_Node :=
499              New_Node (N_Protected_Type_Declaration, Protected_Sloc);
500            Name_Node := P_Defining_Identifier (C_Is);
501            Set_Defining_Identifier (Protected_Node, Name_Node);
502            Scope.Table (Scope.Last).Labl := Name_Node;
503            Set_Discriminant_Specifications
504              (Protected_Node, P_Known_Discriminant_Part_Opt);
505
506         else
507            Protected_Node :=
508              New_Node (N_Single_Protected_Declaration, Protected_Sloc);
509            Name_Node := P_Defining_Identifier (C_Is);
510            Set_Defining_Identifier (Protected_Node, Name_Node);
511
512            if Token = Tok_Left_Paren then
513               Error_Msg_SC
514                 ("discriminant part not allowed for single protected");
515               Discard_Junk_List (P_Known_Discriminant_Part_Opt);
516            end if;
517
518            Scope.Table (Scope.Last).Labl := Name_Node;
519         end if;
520
521         P_Aspect_Specifications (Protected_Node, Semicolon => False);
522
523         --  Check for semicolon not followed by IS, this is something like
524
525         --    protected type r;
526
527         --  where we want
528
529         --    protected type r IS END;
530
531         if Token = Tok_Semicolon then
532            Save_Scan_State (Scan_State); -- at semicolon
533            Scan; -- past semicolon
534
535            if Token /= Tok_Is then
536               Restore_Scan_State (Scan_State);
537               Error_Msg_SC -- CODEFIX
538                 ("missing IS");
539               Set_Protected_Definition (Protected_Node,
540                 Make_Protected_Definition (Token_Ptr,
541                   Visible_Declarations => Empty_List,
542                   End_Label           => Empty));
543
544               SIS_Entry_Active := False;
545               End_Statements
546                 (Protected_Definition (Protected_Node), Protected_Node);
547               return Protected_Node;
548            end if;
549
550            Error_Msg_SP -- CODEFIX
551              ("|extra ""("" ignored");
552         end if;
553
554         T_Is;
555
556         --  Ada 2005 (AI-345)
557
558         if Token = Tok_New then
559            Scan; --  past NEW
560
561            if Ada_Version < Ada_2005 then
562               Error_Msg_SP ("protected interface is an Ada 2005 extension");
563               Error_Msg_SP ("\unit must be compiled with -gnat05 switch");
564            end if;
565
566            Set_Interface_List (Protected_Node, New_List);
567
568            loop
569               Append (P_Qualified_Simple_Name,
570                 Interface_List (Protected_Node));
571
572               exit when Token /= Tok_And;
573               Scan; --  past AND
574            end loop;
575
576            if Token /= Tok_With then
577               Error_Msg_SC -- CODEFIX
578                 ("WITH expected");
579            end if;
580
581            Scan; -- past WITH
582         end if;
583
584         Set_Protected_Definition (Protected_Node, P_Protected_Definition);
585         return Protected_Node;
586      end if;
587   end P_Protected;
588
589   -------------------------------------
590   -- 9.4  Protected Type Declaration --
591   -------------------------------------
592
593   --  Parsed by P_Protected (9.4)
594
595   ---------------------------------------
596   -- 9.4  Single Protected Declaration --
597   ---------------------------------------
598
599   --  Parsed by P_Protected (9.4)
600
601   -------------------------------
602   -- 9.4  Protected Definition --
603   -------------------------------
604
605   --  PROTECTED_DEFINITION ::=
606   --      {PROTECTED_OPERATION_DECLARATION}
607   --    [private
608   --      {PROTECTED_ELEMENT_DECLARATION}]
609   --    end [protected_IDENTIFIER]
610
611   --  PROTECTED_ELEMENT_DECLARATION ::=
612   --    PROTECTED_OPERATION_DECLARATION
613   --  | COMPONENT_DECLARATION
614
615   --  The caller has already established the scope stack entry
616
617   --  Error recovery: cannot raise Error_Resync
618
619   function P_Protected_Definition return Node_Id is
620      Def_Node  : Node_Id;
621      Item_Node : Node_Id;
622
623   begin
624      Def_Node := New_Node (N_Protected_Definition, Token_Ptr);
625
626      --  Get rid of active SIS entry from outer scope. This means we will
627      --  miss some nested cases, but it doesn't seem worth the effort. See
628      --  discussion in Par for further details
629
630      SIS_Entry_Active := False;
631
632      --  Loop to scan visible declarations (protected operation declarations)
633
634      Set_Visible_Declarations (Def_Node, New_List);
635
636      loop
637         Item_Node := P_Protected_Operation_Declaration_Opt;
638         exit when No (Item_Node);
639         Append (Item_Node, Visible_Declarations (Def_Node));
640      end loop;
641
642      --  Deal with PRIVATE part (including graceful handling of multiple
643      --  PRIVATE parts).
644
645      Private_Loop : while Token = Tok_Private loop
646         if No (Private_Declarations (Def_Node)) then
647            Set_Private_Declarations (Def_Node, New_List);
648         else
649            Error_Msg_SC ("duplicate private part");
650         end if;
651
652         Scan; -- past PRIVATE
653
654         Declaration_Loop : loop
655            if Token = Tok_Identifier then
656               P_Component_Items (Private_Declarations (Def_Node));
657            else
658               Item_Node := P_Protected_Operation_Declaration_Opt;
659               exit Declaration_Loop when No (Item_Node);
660               Append (Item_Node, Private_Declarations (Def_Node));
661            end if;
662         end loop Declaration_Loop;
663      end loop Private_Loop;
664
665      End_Statements (Def_Node);
666      return Def_Node;
667   end P_Protected_Definition;
668
669   ------------------------------------------
670   -- 9.4  Protected Operation Declaration --
671   ------------------------------------------
672
673   --  PROTECTED_OPERATION_DECLARATION ::=
674   --    SUBPROGRAM_DECLARATION
675   --  | ENTRY_DECLARATION
676   --  | REPRESENTATION_CLAUSE
677
678   --  Error recovery: cannot raise Error_Resync
679
680   --  Note: a pragma can also be returned in this position
681
682   --  We are not currently permitting representation clauses to appear as
683   --  protected operation declarations, do we have to rethink this???
684
685   function P_Protected_Operation_Declaration_Opt return Node_Id is
686      L : List_Id;
687      P : Source_Ptr;
688
689      function P_Entry_Or_Subprogram_With_Indicator return Node_Id;
690      --  Ada 2005 (AI-397): Parse an entry or a subprogram with an overriding
691      --  indicator. The caller has checked that the initial token is NOT or
692      --  OVERRIDING.
693
694      ------------------------------------------
695      -- P_Entry_Or_Subprogram_With_Indicator --
696      ------------------------------------------
697
698      function P_Entry_Or_Subprogram_With_Indicator return Node_Id is
699         Decl           : Node_Id := Error;
700         Is_Overriding  : Boolean := False;
701         Not_Overriding : Boolean := False;
702
703      begin
704         if Token = Tok_Not then
705            Scan;  -- past NOT
706
707            if Token = Tok_Overriding then
708               Scan;  -- past OVERRIDING
709               Not_Overriding := True;
710            else
711               Error_Msg_SC -- CODEFIX
712                 ("OVERRIDING expected!");
713            end if;
714
715         else
716            Scan;  -- past OVERRIDING
717            Is_Overriding := True;
718         end if;
719
720         if Is_Overriding or else Not_Overriding then
721            if Ada_Version < Ada_2005 then
722               Error_Msg_SP ("overriding indicator is an Ada 2005 extension");
723               Error_Msg_SP ("\unit must be compiled with -gnat05 switch");
724
725            elsif Token = Tok_Entry then
726               Decl := P_Entry_Declaration;
727
728               Set_Must_Override     (Decl, Is_Overriding);
729               Set_Must_Not_Override (Decl, Not_Overriding);
730
731            elsif Token = Tok_Function or else Token = Tok_Procedure then
732               Decl := P_Subprogram (Pf_Decl_Pexp);
733
734               Set_Must_Override     (Specification (Decl), Is_Overriding);
735               Set_Must_Not_Override (Specification (Decl), Not_Overriding);
736
737            else
738               Error_Msg_SC -- CODEFIX
739                 ("ENTRY, FUNCTION or PROCEDURE expected!");
740            end if;
741         end if;
742
743         return Decl;
744      end P_Entry_Or_Subprogram_With_Indicator;
745
746   --  Start of processing for P_Protected_Operation_Declaration_Opt
747
748   begin
749      --  This loop runs more than once only when a junk declaration
750      --  is skipped.
751
752      loop
753         if Token = Tok_Pragma then
754            return P_Pragma;
755
756         elsif Token = Tok_Not or else Token = Tok_Overriding then
757            return P_Entry_Or_Subprogram_With_Indicator;
758
759         elsif Token = Tok_Entry then
760            return P_Entry_Declaration;
761
762         elsif Token = Tok_Function or else Token = Tok_Procedure then
763            return P_Subprogram (Pf_Decl_Pexp);
764
765         elsif Token = Tok_Identifier then
766            L := New_List;
767            P := Token_Ptr;
768            Skip_Declaration (L);
769
770            if Nkind (First (L)) = N_Object_Declaration then
771               Error_Msg
772                 ("component must be declared in private part of " &
773                  "protected type", P);
774            else
775               Error_Msg
776                 ("illegal declaration in protected definition", P);
777            end if;
778
779         elsif Token in Token_Class_Declk then
780            Error_Msg_SC ("illegal declaration in protected definition");
781            Resync_Past_Semicolon;
782
783            --  Return now to avoid cascaded messages if next declaration
784            --  is a valid component declaration.
785
786            return Error;
787
788         elsif Token = Tok_For then
789            Error_Msg_SC
790              ("representation clause not allowed in protected definition");
791            Resync_Past_Semicolon;
792
793         else
794            return Empty;
795         end if;
796      end loop;
797   end P_Protected_Operation_Declaration_Opt;
798
799   -----------------------------------
800   -- 9.4  Protected Operation Item --
801   -----------------------------------
802
803   --  PROTECTED_OPERATION_ITEM ::=
804   --    SUBPROGRAM_DECLARATION
805   --  | SUBPROGRAM_BODY
806   --  | ENTRY_BODY
807   --  | REPRESENTATION_CLAUSE
808
809   --  This procedure parses and returns a list of protected operation items
810
811   --  We are not currently permitting representation clauses to appear
812   --  as protected operation items, do we have to rethink this???
813
814   function P_Protected_Operation_Items return List_Id is
815      Item_List : List_Id;
816
817   begin
818      Item_List := New_List;
819
820      loop
821         if Token = Tok_Entry or else Bad_Spelling_Of (Tok_Entry) then
822            Append (P_Entry_Body, Item_List);
823
824         --  If the operation starts with procedure, function, or an overriding
825         --  indicator ("overriding" or "not overriding"), parse a subprogram.
826
827         elsif Token = Tok_Function or else Bad_Spelling_Of (Tok_Function)
828                 or else
829               Token = Tok_Procedure or else Bad_Spelling_Of (Tok_Procedure)
830                 or else
831               Token = Tok_Overriding or else Bad_Spelling_Of (Tok_Overriding)
832                 or else
833               Token = Tok_Not or else Bad_Spelling_Of (Tok_Not)
834         then
835            Append (P_Subprogram (Pf_Decl_Pbod_Pexp), Item_List);
836
837         elsif Token = Tok_Pragma or else Bad_Spelling_Of (Tok_Pragma) then
838            P_Pragmas_Opt (Item_List);
839
840         elsif Token = Tok_Private or else Bad_Spelling_Of (Tok_Private) then
841            Error_Msg_SC ("PRIVATE not allowed in protected body");
842            Scan; -- past PRIVATE
843
844         elsif Token = Tok_Identifier then
845            Error_Msg_SC ("all components must be declared in spec!");
846            Resync_Past_Semicolon;
847
848         elsif Token in Token_Class_Declk then
849            Error_Msg_SC ("this declaration not allowed in protected body");
850            Resync_Past_Semicolon;
851
852         else
853            exit;
854         end if;
855      end loop;
856
857      return Item_List;
858   end P_Protected_Operation_Items;
859
860   ------------------------------
861   -- 9.5.2  Entry Declaration --
862   ------------------------------
863
864   --  ENTRY_DECLARATION ::=
865   --    [OVERRIDING_INDICATOR]
866   --    entry DEFINING_IDENTIFIER
867   --      [(DISCRETE_SUBTYPE_DEFINITION)] PARAMETER_PROFILE
868   --        [ASPECT_SPECIFICATIONS];
869
870   --  The caller has checked that the initial token is ENTRY, NOT or
871   --  OVERRIDING.
872
873   --  Error recovery: cannot raise Error_Resync
874
875   function P_Entry_Declaration return Node_Id is
876      Decl_Node  : Node_Id;
877      Scan_State : Saved_Scan_State;
878
879      --  Flags for optional overriding indication. Two flags are needed,
880      --  to distinguish positive and negative overriding indicators from
881      --  the absence of any indicator.
882
883      Is_Overriding  : Boolean := False;
884      Not_Overriding : Boolean := False;
885
886   begin
887      --  Ada 2005 (AI-397): Scan leading overriding indicator
888
889      if Token = Tok_Not then
890         Scan;  -- past NOT
891
892         if Token = Tok_Overriding then
893            Scan;  -- part OVERRIDING
894            Not_Overriding := True;
895         else
896            Error_Msg_SC -- CODEFIX
897              ("OVERRIDING expected!");
898         end if;
899
900      elsif Token = Tok_Overriding then
901         Scan;  -- part OVERRIDING
902         Is_Overriding := True;
903      end if;
904
905      if Is_Overriding or else Not_Overriding then
906         if Ada_Version < Ada_2005 then
907            Error_Msg_SP ("overriding indicator is an Ada 2005 extension");
908            Error_Msg_SP ("\unit must be compiled with -gnat05 switch");
909
910         elsif Token /= Tok_Entry then
911            Error_Msg_SC -- CODEFIX
912              ("ENTRY expected!");
913         end if;
914      end if;
915
916      Decl_Node := New_Node (N_Entry_Declaration, Token_Ptr);
917      Scan; -- past ENTRY
918
919      Set_Defining_Identifier
920        (Decl_Node, P_Defining_Identifier (C_Left_Paren_Semicolon));
921
922      --  If left paren, could be (Discrete_Subtype_Definition) or Formal_Part
923
924      if Token = Tok_Left_Paren then
925         Scan; -- past (
926
927         --  If identifier after left paren, could still be either
928
929         if Token = Tok_Identifier then
930            Save_Scan_State (Scan_State); -- at Id
931            Scan; -- past Id
932
933            --  If comma or colon after Id, must be Formal_Part
934
935            if Token = Tok_Comma or else Token = Tok_Colon then
936               Restore_Scan_State (Scan_State); -- to Id
937               Set_Parameter_Specifications (Decl_Node, P_Formal_Part);
938
939            --  Else if Id without comma or colon, must be discrete subtype
940            --  defn
941
942            else
943               Restore_Scan_State (Scan_State); -- to Id
944               Set_Discrete_Subtype_Definition
945                 (Decl_Node, P_Discrete_Subtype_Definition);
946               T_Right_Paren;
947               Set_Parameter_Specifications (Decl_Node, P_Parameter_Profile);
948            end if;
949
950         --  If no Id, must be discrete subtype definition
951
952         else
953            Set_Discrete_Subtype_Definition
954              (Decl_Node, P_Discrete_Subtype_Definition);
955            T_Right_Paren;
956            Set_Parameter_Specifications (Decl_Node, P_Parameter_Profile);
957         end if;
958      end if;
959
960      if Is_Overriding then
961         Set_Must_Override (Decl_Node);
962      elsif Not_Overriding then
963         Set_Must_Not_Override (Decl_Node);
964      end if;
965
966      --  Error recovery check for illegal return
967
968      if Token = Tok_Return then
969         Error_Msg_SC ("entry cannot have return value!");
970         Scan;
971         Discard_Junk_Node (P_Subtype_Indication);
972      end if;
973
974      --  Error recovery check for improper use of entry barrier in spec
975
976      if Token = Tok_When then
977         Error_Msg_SC ("barrier not allowed here (belongs in body)");
978         Scan; -- past WHEN;
979         Discard_Junk_Node (P_Expression_No_Right_Paren);
980      end if;
981
982      P_Aspect_Specifications (Decl_Node);
983      return Decl_Node;
984
985   exception
986      when Error_Resync =>
987         Resync_Past_Semicolon;
988         return Error;
989   end P_Entry_Declaration;
990
991   -----------------------------
992   -- 9.5.2  Accept Statement --
993   -----------------------------
994
995   --  ACCEPT_STATEMENT ::=
996   --    accept entry_DIRECT_NAME
997   --      [(ENTRY_INDEX)] PARAMETER_PROFILE [do
998   --        HANDLED_SEQUENCE_OF_STATEMENTS
999   --    end [entry_IDENTIFIER]];
1000
1001   --  The caller has checked that the initial token is ACCEPT
1002
1003   --  Error recovery: cannot raise Error_Resync. If an error occurs, the
1004   --  scan is resynchronized past the next semicolon and control returns.
1005
1006   function P_Accept_Statement return Node_Id is
1007      Scan_State  : Saved_Scan_State;
1008      Accept_Node : Node_Id;
1009      Hand_Seq    : Node_Id;
1010
1011   begin
1012      Push_Scope_Stack;
1013      Scope.Table (Scope.Last).Sloc := Token_Ptr;
1014      Scope.Table (Scope.Last).Ecol := Start_Column;
1015
1016      Accept_Node := New_Node (N_Accept_Statement, Token_Ptr);
1017      Scan; -- past ACCEPT
1018      Scope.Table (Scope.Last).Labl := Token_Node;
1019
1020      Set_Entry_Direct_Name (Accept_Node, P_Identifier (C_Do));
1021
1022      --  Left paren could be (Entry_Index) or Formal_Part, determine which
1023
1024      if Token = Tok_Left_Paren then
1025         Save_Scan_State (Scan_State); -- at left paren
1026         Scan; -- past left paren
1027
1028         --  If first token after left paren not identifier, then Entry_Index
1029
1030         if Token /= Tok_Identifier then
1031            Set_Entry_Index (Accept_Node, P_Expression);
1032            T_Right_Paren;
1033            Set_Parameter_Specifications (Accept_Node, P_Parameter_Profile);
1034
1035         --  First token after left paren is identifier, could be either case
1036
1037         else -- Token = Tok_Identifier
1038            Scan; -- past identifier
1039
1040            --  If identifier followed by comma or colon, must be Formal_Part
1041
1042            if Token = Tok_Comma or else Token = Tok_Colon then
1043               Restore_Scan_State (Scan_State); -- to left paren
1044               Set_Parameter_Specifications (Accept_Node, P_Parameter_Profile);
1045
1046            --  If identifier not followed by comma/colon, must be entry index
1047
1048            else
1049               Restore_Scan_State (Scan_State); -- to left paren
1050               Scan; -- past left paren (again)
1051               Set_Entry_Index (Accept_Node, P_Expression);
1052               T_Right_Paren;
1053               Set_Parameter_Specifications (Accept_Node, P_Parameter_Profile);
1054            end if;
1055         end if;
1056      end if;
1057
1058      --  Scan out DO if present
1059
1060      if Token = Tok_Do then
1061         Scope.Table (Scope.Last).Etyp := E_Name;
1062         Scope.Table (Scope.Last).Lreq := False;
1063         Scan; -- past DO
1064         Hand_Seq := P_Handled_Sequence_Of_Statements;
1065         Set_Handled_Statement_Sequence (Accept_Node, Hand_Seq);
1066         End_Statements (Handled_Statement_Sequence (Accept_Node));
1067
1068         --  Exception handlers not allowed in Ada 95 node
1069
1070         if Present (Exception_Handlers (Hand_Seq)) then
1071            if Ada_Version = Ada_83 then
1072               Error_Msg_N
1073                 ("(Ada 83) exception handlers in accept not allowed",
1074                  First_Non_Pragma (Exception_Handlers (Hand_Seq)));
1075            end if;
1076         end if;
1077
1078      else
1079         Pop_Scope_Stack; -- discard unused entry
1080         TF_Semicolon;
1081      end if;
1082
1083      return Accept_Node;
1084
1085   --  If error, resynchronize past semicolon
1086
1087   exception
1088      when Error_Resync =>
1089         Resync_Past_Semicolon;
1090         Pop_Scope_Stack; -- discard unused entry
1091         return Error;
1092   end P_Accept_Statement;
1093
1094   ------------------------
1095   -- 9.5.2  Entry Index --
1096   ------------------------
1097
1098   --  Parsed by P_Expression (4.4)
1099
1100   --------------------------
1101   -- 9.5.2  Entry Barrier --
1102   --------------------------
1103
1104   --  ENTRY_BARRIER ::= when CONDITION
1105
1106   --  Error_Recovery: cannot raise Error_Resync
1107
1108   function P_Entry_Barrier return Node_Id is
1109      Bnode : Node_Id;
1110
1111   begin
1112      if Token = Tok_When then
1113         Scan; -- past WHEN;
1114         Bnode := P_Expression_No_Right_Paren;
1115
1116         if Token = Tok_Colon_Equal then
1117            Error_Msg_SC -- CODEFIX
1118              ("|"":="" should be ""=""");
1119            Scan;
1120            Bnode := P_Expression_No_Right_Paren;
1121         end if;
1122
1123      else
1124         T_When; -- to give error message
1125         Bnode := Error;
1126      end if;
1127
1128      return Bnode;
1129   end P_Entry_Barrier;
1130
1131   -----------------------
1132   -- 9.5.2  Entry Body --
1133   -----------------------
1134
1135   --  ENTRY_BODY ::=
1136   --    entry DEFINING_IDENTIFIER ENTRY_BODY_FORMAL_PART
1137   --      [ASPECT_SPECIFICATIONS] ENTRY_BARRIER
1138   --    is
1139   --      DECLARATIVE_PART
1140   --    begin
1141   --      HANDLED_SEQUENCE_OF_STATEMENTS
1142   --    end [entry_IDENTIFIER];
1143
1144   --  The caller has checked that the initial token is ENTRY
1145
1146   --  Error_Recovery: cannot raise Error_Resync
1147
1148   function P_Entry_Body return Node_Id is
1149      Dummy_Node       : Node_Id;
1150      Entry_Node       : Node_Id;
1151      Formal_Part_Node : Node_Id;
1152      Name_Node        : Node_Id;
1153
1154   begin
1155      Push_Scope_Stack;
1156      Entry_Node := New_Node (N_Entry_Body, Token_Ptr);
1157      Scan; -- past ENTRY
1158
1159      Scope.Table (Scope.Last).Ecol := Start_Column;
1160      Scope.Table (Scope.Last).Lreq := False;
1161      Scope.Table (Scope.Last).Etyp := E_Name;
1162      Scope.Table (Scope.Last).Sloc := Token_Ptr;
1163
1164      Name_Node := P_Defining_Identifier;
1165      Set_Defining_Identifier (Entry_Node, Name_Node);
1166      Scope.Table (Scope.Last).Labl := Name_Node;
1167
1168      Formal_Part_Node := P_Entry_Body_Formal_Part;
1169      Set_Entry_Body_Formal_Part (Entry_Node, Formal_Part_Node);
1170
1171      --  Ada 2012 (AI12-0169): Aspect specifications may appear on an entry
1172      --  body immediately after the formal part. Do not parse the aspect
1173      --  specifications directly because the "when" of the entry barrier may
1174      --  be interpreted as a misused "with".
1175
1176      if Token = Tok_With then
1177         P_Aspect_Specifications (Entry_Node, Semicolon => False);
1178      end if;
1179
1180      Set_Condition (Formal_Part_Node, P_Entry_Barrier);
1181
1182      --  Detect an illegal placement of aspect specifications following the
1183      --  entry barrier.
1184
1185      --    entry E ... when Barrier with Aspect is
1186
1187      if Token = Tok_With then
1188         Error_Msg_SC ("aspect specifications must come before entry barrier");
1189
1190         --  Consume the illegal aspects to allow for parsing to continue
1191
1192         Dummy_Node := New_Node (N_Entry_Body, Sloc (Entry_Node));
1193         P_Aspect_Specifications (Dummy_Node, Semicolon => False);
1194      end if;
1195
1196      TF_Is;
1197      Parse_Decls_Begin_End (Entry_Node);
1198
1199      return Entry_Node;
1200   end P_Entry_Body;
1201
1202   -----------------------------------
1203   -- 9.5.2  Entry Body Formal Part --
1204   -----------------------------------
1205
1206   --  ENTRY_BODY_FORMAL_PART ::=
1207   --    [(ENTRY_INDEX_SPECIFICATION)] [PARAMETER_PART]
1208
1209   --  Error_Recovery: cannot raise Error_Resync
1210
1211   function P_Entry_Body_Formal_Part return Node_Id is
1212      Fpart_Node : Node_Id;
1213      Scan_State : Saved_Scan_State;
1214
1215   begin
1216      Fpart_Node := New_Node (N_Entry_Body_Formal_Part, Token_Ptr);
1217
1218      --  See if entry index specification present, and if so parse it
1219
1220      if Token = Tok_Left_Paren then
1221         Save_Scan_State (Scan_State); -- at left paren
1222         Scan; -- past left paren
1223
1224         if Token = Tok_For then
1225            Set_Entry_Index_Specification
1226              (Fpart_Node, P_Entry_Index_Specification);
1227            T_Right_Paren;
1228         else
1229            Restore_Scan_State (Scan_State); -- to left paren
1230         end if;
1231
1232      --  Check for (common?) case of left paren omitted before FOR. This
1233      --  is a tricky case, because the corresponding missing left paren
1234      --  can cause real havoc if a formal part is present which gets
1235      --  treated as part of the discrete subtype definition of the
1236      --  entry index specification, so just give error and resynchronize
1237
1238      elsif Token = Tok_For then
1239         T_Left_Paren; -- to give error message
1240         Resync_To_When;
1241      end if;
1242
1243      Set_Parameter_Specifications (Fpart_Node, P_Parameter_Profile);
1244      return Fpart_Node;
1245   end P_Entry_Body_Formal_Part;
1246
1247   --------------------------------------
1248   -- 9.5.2  Entry Index Specification --
1249   --------------------------------------
1250
1251   --  ENTRY_INDEX_SPECIFICATION ::=
1252   --    for DEFINING_IDENTIFIER in DISCRETE_SUBTYPE_DEFINITION
1253
1254   --  Error recovery: can raise Error_Resync
1255
1256   function P_Entry_Index_Specification return Node_Id is
1257      Iterator_Node : Node_Id;
1258
1259   begin
1260      Iterator_Node := New_Node (N_Entry_Index_Specification, Token_Ptr);
1261      T_For; -- past FOR
1262      Set_Defining_Identifier (Iterator_Node, P_Defining_Identifier (C_In));
1263      T_In;
1264      Set_Discrete_Subtype_Definition
1265        (Iterator_Node, P_Discrete_Subtype_Definition);
1266      return Iterator_Node;
1267   end P_Entry_Index_Specification;
1268
1269   ---------------------------------
1270   -- 9.5.3  Entry Call Statement --
1271   ---------------------------------
1272
1273   --  Parsed by P_Name (4.1). Within a select, an entry call is parsed
1274   --  by P_Select_Statement (9.7)
1275
1276   ------------------------------
1277   -- 9.5.4  Requeue Statement --
1278   ------------------------------
1279
1280   --  REQUEUE_STATEMENT ::= requeue entry_NAME [with abort];
1281
1282   --  The caller has checked that the initial token is requeue
1283
1284   --  Error recovery: can raise Error_Resync
1285
1286   function P_Requeue_Statement return Node_Id is
1287      Requeue_Node : Node_Id;
1288
1289   begin
1290      Requeue_Node := New_Node (N_Requeue_Statement, Token_Ptr);
1291      Scan; -- past REQUEUE
1292      Set_Name (Requeue_Node, P_Name);
1293
1294      if Token = Tok_With then
1295         Scan; -- past WITH
1296         T_Abort;
1297         Set_Abort_Present (Requeue_Node, True);
1298      end if;
1299
1300      TF_Semicolon;
1301      return Requeue_Node;
1302   end P_Requeue_Statement;
1303
1304   --------------------------
1305   -- 9.6  Delay Statement --
1306   --------------------------
1307
1308   --  DELAY_STATEMENT ::=
1309   --    DELAY_UNTIL_STATEMENT
1310   --  | DELAY_RELATIVE_STATEMENT
1311
1312   --  The caller has checked that the initial token is DELAY
1313
1314   --  Error recovery: cannot raise Error_Resync
1315
1316   function P_Delay_Statement return Node_Id is
1317   begin
1318      Scan; -- past DELAY
1319
1320      --  The following check for delay until misused in Ada 83 doesn't catch
1321      --  all cases, but it's good enough to catch most of them.
1322
1323      if Token_Name = Name_Until then
1324         Check_95_Keyword (Tok_Until, Tok_Left_Paren);
1325         Check_95_Keyword (Tok_Until, Tok_Identifier);
1326      end if;
1327
1328      if Token = Tok_Until then
1329         return P_Delay_Until_Statement;
1330      else
1331         return P_Delay_Relative_Statement;
1332      end if;
1333   end P_Delay_Statement;
1334
1335   --------------------------------
1336   -- 9.6  Delay Until Statement --
1337   --------------------------------
1338
1339   --  DELAY_UNTIL_STATEMENT ::= delay until delay_EXPRESSION;
1340
1341   --  The caller has checked that the initial token is DELAY, scanned it
1342   --  out and checked that the current token is UNTIL
1343
1344   --  Error recovery: cannot raise Error_Resync
1345
1346   function P_Delay_Until_Statement return Node_Id is
1347      Delay_Node : Node_Id;
1348
1349   begin
1350      Delay_Node := New_Node (N_Delay_Until_Statement, Prev_Token_Ptr);
1351      Scan; -- past UNTIL
1352      Set_Expression (Delay_Node, P_Expression_No_Right_Paren);
1353      TF_Semicolon;
1354      return Delay_Node;
1355   end P_Delay_Until_Statement;
1356
1357   -----------------------------------
1358   -- 9.6  Delay Relative Statement --
1359   -----------------------------------
1360
1361   --  DELAY_RELATIVE_STATEMENT ::= delay delay_EXPRESSION;
1362
1363   --  The caller has checked that the initial token is DELAY, scanned it
1364   --  out and determined that the current token is not UNTIL
1365
1366   --  Error recovery: cannot raise Error_Resync
1367
1368   function P_Delay_Relative_Statement return Node_Id is
1369      Delay_Node : Node_Id;
1370
1371   begin
1372      Delay_Node := New_Node (N_Delay_Relative_Statement, Prev_Token_Ptr);
1373      Set_Expression (Delay_Node, P_Expression_No_Right_Paren);
1374      Check_Simple_Expression_In_Ada_83 (Expression (Delay_Node));
1375      TF_Semicolon;
1376      return Delay_Node;
1377   end P_Delay_Relative_Statement;
1378
1379   ---------------------------
1380   -- 9.7  Select Statement --
1381   ---------------------------
1382
1383   --  SELECT_STATEMENT ::=
1384   --    SELECTIVE_ACCEPT
1385   --  | TIMED_ENTRY_CALL
1386   --  | CONDITIONAL_ENTRY_CALL
1387   --  | ASYNCHRONOUS_SELECT
1388
1389   --  SELECTIVE_ACCEPT ::=
1390   --    select
1391   --      [GUARD]
1392   --        SELECT_ALTERNATIVE
1393   --    {or
1394   --      [GUARD]
1395   --        SELECT_ALTERNATIVE
1396   --    [else
1397   --      SEQUENCE_OF_STATEMENTS]
1398   --    end select;
1399
1400   --  GUARD ::= when CONDITION =>
1401
1402   --  Note: the guard preceding a select alternative is included as part
1403   --  of the node generated for a selective accept alternative.
1404
1405   --  SELECT_ALTERNATIVE ::=
1406   --    ACCEPT_ALTERNATIVE
1407   --  | DELAY_ALTERNATIVE
1408   --  | TERMINATE_ALTERNATIVE
1409
1410   --  TIMED_ENTRY_CALL ::=
1411   --    select
1412   --      ENTRY_CALL_ALTERNATIVE
1413   --    or
1414   --      DELAY_ALTERNATIVE
1415   --    end select;
1416
1417   --  CONDITIONAL_ENTRY_CALL ::=
1418   --    select
1419   --      ENTRY_CALL_ALTERNATIVE
1420   --    else
1421   --      SEQUENCE_OF_STATEMENTS
1422   --    end select;
1423
1424   --  ENTRY_CALL_ALTERNATIVE ::=
1425   --    ENTRY_CALL_STATEMENT [SEQUENCE_OF_STATEMENTS]
1426
1427   --  ASYNCHRONOUS_SELECT ::=
1428   --    select
1429   --      TRIGGERING_ALTERNATIVE
1430   --    then abort
1431   --      ABORTABLE_PART
1432   --    end select;
1433
1434   --  TRIGGERING_ALTERNATIVE ::=
1435   --    TRIGGERING_STATEMENT [SEQUENCE_OF_STATEMENTS]
1436
1437   --  TRIGGERING_STATEMENT ::= ENTRY_CALL_STATEMENT | DELAY_STATEMENT
1438
1439   --  The caller has checked that the initial token is SELECT
1440
1441   --  Error recovery: can raise Error_Resync
1442
1443   function P_Select_Statement return Node_Id is
1444      Select_Node    : Node_Id;
1445      Select_Sloc    : Source_Ptr;
1446      Stmnt_Sloc     : Source_Ptr;
1447      Ecall_Node     : Node_Id;
1448      Alternative    : Node_Id;
1449      Select_Pragmas : List_Id;
1450      Alt_Pragmas    : List_Id;
1451      Statement_List : List_Id;
1452      Alt_List       : List_Id;
1453      Cond_Expr      : Node_Id;
1454      Delay_Stmnt    : Node_Id;
1455
1456   begin
1457      Push_Scope_Stack;
1458      Scope.Table (Scope.Last).Etyp := E_Select;
1459      Scope.Table (Scope.Last).Ecol := Start_Column;
1460      Scope.Table (Scope.Last).Sloc := Token_Ptr;
1461      Scope.Table (Scope.Last).Labl := Error;
1462
1463      Select_Sloc := Token_Ptr;
1464      Scan; -- past SELECT
1465      Stmnt_Sloc := Token_Ptr;
1466      Select_Pragmas := P_Pragmas_Opt;
1467
1468      --  If first token after select is designator, then we have an entry
1469      --  call, which must be the start of a conditional entry call, timed
1470      --  entry call or asynchronous select
1471
1472      if Token in Token_Class_Desig then
1473
1474         --  Scan entry call statement
1475
1476         begin
1477            Ecall_Node := P_Name;
1478
1479            --  ??  The following two clauses exactly parallel code in ch5
1480            --      and should be combined sometime
1481
1482            if Nkind (Ecall_Node) = N_Indexed_Component then
1483               declare
1484                  Prefix_Node : constant Node_Id := Prefix (Ecall_Node);
1485                  Exprs_Node  : constant List_Id := Expressions (Ecall_Node);
1486
1487               begin
1488                  Change_Node (Ecall_Node, N_Procedure_Call_Statement);
1489                  Set_Name (Ecall_Node, Prefix_Node);
1490                  Set_Parameter_Associations (Ecall_Node, Exprs_Node);
1491               end;
1492
1493            elsif Nkind (Ecall_Node) = N_Function_Call then
1494               declare
1495                  Fname_Node  : constant Node_Id := Name (Ecall_Node);
1496                  Params_List : constant List_Id :=
1497                                  Parameter_Associations (Ecall_Node);
1498
1499               begin
1500                  Change_Node (Ecall_Node, N_Procedure_Call_Statement);
1501                  Set_Name (Ecall_Node, Fname_Node);
1502                  Set_Parameter_Associations (Ecall_Node, Params_List);
1503               end;
1504
1505            elsif Nkind (Ecall_Node) = N_Identifier
1506              or else Nkind (Ecall_Node) = N_Selected_Component
1507            then
1508               --  Case of a call to a parameterless entry
1509
1510               declare
1511                  C_Node : constant Node_Id :=
1512                         New_Node (N_Procedure_Call_Statement, Stmnt_Sloc);
1513               begin
1514                  Set_Name (C_Node, Ecall_Node);
1515                  Set_Parameter_Associations (C_Node, No_List);
1516                  Ecall_Node := C_Node;
1517               end;
1518            end if;
1519
1520            TF_Semicolon;
1521
1522         exception
1523            when Error_Resync =>
1524               Resync_Past_Semicolon;
1525               return Error;
1526         end;
1527
1528         Statement_List := P_Sequence_Of_Statements (SS_Eltm_Ortm_Tatm);
1529
1530         --  OR follows, we have a timed entry call
1531
1532         if Token = Tok_Or then
1533            Scan; -- past OR
1534            Alt_Pragmas := P_Pragmas_Opt;
1535
1536            Select_Node := New_Node (N_Timed_Entry_Call, Select_Sloc);
1537            Set_Entry_Call_Alternative (Select_Node,
1538              Make_Entry_Call_Alternative (Stmnt_Sloc,
1539                Entry_Call_Statement => Ecall_Node,
1540                Pragmas_Before       => Select_Pragmas,
1541                Statements           => Statement_List));
1542
1543            --  Only possibility is delay alternative. If we have anything
1544            --  else, give message, and treat as conditional entry call.
1545
1546            if Token /= Tok_Delay then
1547               Error_Msg_SC
1548                 ("only allowed alternative in timed entry call is delay!");
1549               Discard_Junk_List (P_Sequence_Of_Statements (SS_Sreq));
1550               Set_Delay_Alternative (Select_Node, Error);
1551
1552            else
1553               Set_Delay_Alternative (Select_Node, P_Delay_Alternative);
1554               Set_Pragmas_Before
1555                 (Delay_Alternative (Select_Node), Alt_Pragmas);
1556            end if;
1557
1558         --  ELSE follows, we have a conditional entry call
1559
1560         elsif Token = Tok_Else then
1561            Scan; -- past ELSE
1562            Select_Node := New_Node (N_Conditional_Entry_Call, Select_Sloc);
1563
1564            Set_Entry_Call_Alternative (Select_Node,
1565              Make_Entry_Call_Alternative (Stmnt_Sloc,
1566                Entry_Call_Statement => Ecall_Node,
1567                Pragmas_Before       => Select_Pragmas,
1568                Statements           => Statement_List));
1569
1570            Set_Else_Statements
1571              (Select_Node, P_Sequence_Of_Statements (SS_Sreq));
1572
1573         --  Only remaining case is THEN ABORT (asynchronous select)
1574
1575         elsif Token = Tok_Abort then
1576            Select_Node :=
1577              Make_Asynchronous_Select (Select_Sloc,
1578                Triggering_Alternative =>
1579                  Make_Triggering_Alternative (Stmnt_Sloc,
1580                    Triggering_Statement => Ecall_Node,
1581                    Pragmas_Before       => Select_Pragmas,
1582                    Statements           => Statement_List),
1583                Abortable_Part => P_Abortable_Part);
1584
1585         --  Else error
1586
1587         else
1588            if Ada_Version = Ada_83 then
1589               Error_Msg_BC ("OR or ELSE expected");
1590            else
1591               Error_Msg_BC ("OR or ELSE or THEN ABORT expected");
1592            end if;
1593
1594            Select_Node := Error;
1595         end if;
1596
1597         End_Statements;
1598
1599      --  Here we have a selective accept or an asynchronous select (first
1600      --  token after SELECT is other than a designator token).
1601
1602      else
1603         --  If we have delay with no guard, could be asynchronous select
1604
1605         if Token = Tok_Delay then
1606            Delay_Stmnt := P_Delay_Statement;
1607            Statement_List := P_Sequence_Of_Statements (SS_Eltm_Ortm_Tatm);
1608
1609            --  Asynchronous select
1610
1611            if Token = Tok_Abort then
1612               Select_Node :=
1613                 Make_Asynchronous_Select (Select_Sloc,
1614                   Triggering_Alternative =>
1615                     Make_Triggering_Alternative (Stmnt_Sloc,
1616                       Triggering_Statement => Delay_Stmnt,
1617                       Pragmas_Before       => Select_Pragmas,
1618                       Statements           => Statement_List),
1619                     Abortable_Part => P_Abortable_Part);
1620
1621               End_Statements;
1622               return Select_Node;
1623
1624            --  Delay which was not an asynchronous select. Must be a selective
1625            --  accept, and since at least one accept statement is required,
1626            --  we must have at least one OR phrase present.
1627
1628            else
1629               Alt_List := New_List (
1630                 Make_Delay_Alternative (Stmnt_Sloc,
1631                   Delay_Statement => Delay_Stmnt,
1632                   Pragmas_Before  => Select_Pragmas,
1633                   Statements      => Statement_List));
1634               T_Or;
1635               Alt_Pragmas := P_Pragmas_Opt;
1636            end if;
1637
1638         --  If not a delay statement, then must be another possibility for
1639         --  a selective accept alternative, or perhaps a guard is present
1640
1641         else
1642            Alt_List := New_List;
1643            Alt_Pragmas := Select_Pragmas;
1644         end if;
1645
1646         Select_Node := New_Node (N_Selective_Accept, Select_Sloc);
1647         Set_Select_Alternatives (Select_Node, Alt_List);
1648
1649         --  Scan out selective accept alternatives. On entry to this loop,
1650         --  we are just past a SELECT or OR token, and any pragmas that
1651         --  immediately follow the SELECT or OR are in Alt_Pragmas.
1652
1653         loop
1654            if Token = Tok_When then
1655
1656               if Present (Alt_Pragmas) then
1657                  Error_Msg_SC ("pragmas may not precede guard");
1658               end if;
1659
1660               Scan; --  past WHEN
1661               Cond_Expr := P_Expression_No_Right_Paren;
1662               T_Arrow;
1663               Alt_Pragmas := P_Pragmas_Opt;
1664
1665            else
1666               Cond_Expr := Empty;
1667            end if;
1668
1669            if Token = Tok_Accept then
1670               Alternative := P_Accept_Alternative;
1671
1672               --  Check for junk attempt at asynchronous select using
1673               --  an Accept alternative as the triggering statement
1674
1675               if Token = Tok_Abort
1676                 and then Is_Empty_List (Alt_List)
1677                 and then No (Cond_Expr)
1678               then
1679                  Error_Msg
1680                    ("triggering statement must be entry call or delay",
1681                     Sloc (Alternative));
1682                  Scan; -- past junk ABORT
1683                  Discard_Junk_List (P_Sequence_Of_Statements (SS_Sreq));
1684                  End_Statements;
1685                  return Error;
1686               end if;
1687
1688            elsif Token = Tok_Delay then
1689               Alternative := P_Delay_Alternative;
1690
1691            elsif Token = Tok_Terminate then
1692               Alternative := P_Terminate_Alternative;
1693
1694            else
1695               Error_Msg_SC
1696                 ("select alternative (ACCEPT, ABORT, DELAY) expected");
1697               Alternative := Error;
1698
1699               if Token = Tok_Semicolon then
1700                  Scan; -- past junk semicolon
1701               end if;
1702            end if;
1703
1704            --  THEN ABORT at this stage is just junk
1705
1706            if Token = Tok_Abort then
1707               Error_Msg_SP ("misplaced `THEN ABORT`");
1708               Scan; -- past junk ABORT
1709               Discard_Junk_List (P_Sequence_Of_Statements (SS_Sreq));
1710               End_Statements;
1711               return Error;
1712
1713            else
1714               if Alternative /= Error then
1715                  Set_Condition (Alternative, Cond_Expr);
1716                  Set_Pragmas_Before (Alternative, Alt_Pragmas);
1717                  Append (Alternative, Alt_List);
1718               end if;
1719
1720               exit when Token /= Tok_Or;
1721            end if;
1722
1723            T_Or;
1724            Alt_Pragmas := P_Pragmas_Opt;
1725         end loop;
1726
1727         if Token = Tok_Else then
1728            Scan; -- past ELSE
1729            Set_Else_Statements
1730              (Select_Node, P_Sequence_Of_Statements (SS_Ortm_Sreq));
1731
1732            if Token = Tok_Or then
1733               Error_Msg_SC ("select alternative cannot follow else part!");
1734            end if;
1735         end if;
1736
1737         End_Statements;
1738      end if;
1739
1740      return Select_Node;
1741   end P_Select_Statement;
1742
1743   -----------------------------
1744   -- 9.7.1  Selective Accept --
1745   -----------------------------
1746
1747   --  Parsed by P_Select_Statement (9.7)
1748
1749   ------------------
1750   -- 9.7.1  Guard --
1751   ------------------
1752
1753   --  Parsed by P_Select_Statement (9.7)
1754
1755   -------------------------------
1756   -- 9.7.1  Select Alternative --
1757   -------------------------------
1758
1759   --  SELECT_ALTERNATIVE ::=
1760   --    ACCEPT_ALTERNATIVE
1761   --  | DELAY_ALTERNATIVE
1762   --  | TERMINATE_ALTERNATIVE
1763
1764   --  Note: the guard preceding a select alternative is included as part
1765   --  of the node generated for a selective accept alternative.
1766
1767   --  Error recovery: cannot raise Error_Resync
1768
1769   -------------------------------
1770   -- 9.7.1  Accept Alternative --
1771   -------------------------------
1772
1773   --  ACCEPT_ALTERNATIVE ::=
1774   --    ACCEPT_STATEMENT [SEQUENCE_OF_STATEMENTS]
1775
1776   --  Error_Recovery: Cannot raise Error_Resync
1777
1778   --  Note: the caller is responsible for setting the Pragmas_Before
1779   --  field of the returned N_Terminate_Alternative node.
1780
1781   function P_Accept_Alternative return Node_Id is
1782      Accept_Alt_Node : Node_Id;
1783
1784   begin
1785      Accept_Alt_Node := New_Node (N_Accept_Alternative, Token_Ptr);
1786      Set_Accept_Statement (Accept_Alt_Node, P_Accept_Statement);
1787
1788      --  Note: the reason that we accept THEN ABORT as a terminator for
1789      --  the sequence of statements is for error recovery which allows
1790      --  for misuse of an accept statement as a triggering statement.
1791
1792      Set_Statements
1793        (Accept_Alt_Node, P_Sequence_Of_Statements (SS_Eltm_Ortm_Tatm));
1794      return Accept_Alt_Node;
1795   end P_Accept_Alternative;
1796
1797   ------------------------------
1798   -- 9.7.1  Delay Alternative --
1799   ------------------------------
1800
1801   --  DELAY_ALTERNATIVE ::=
1802   --    DELAY_STATEMENT [SEQUENCE_OF_STATEMENTS]
1803
1804   --  Error_Recovery: Cannot raise Error_Resync
1805
1806   --  Note: the caller is responsible for setting the Pragmas_Before
1807   --  field of the returned N_Terminate_Alternative node.
1808
1809   function P_Delay_Alternative return Node_Id is
1810      Delay_Alt_Node : Node_Id;
1811
1812   begin
1813      Delay_Alt_Node := New_Node (N_Delay_Alternative, Token_Ptr);
1814      Set_Delay_Statement (Delay_Alt_Node, P_Delay_Statement);
1815
1816      --  Note: the reason that we accept THEN ABORT as a terminator for
1817      --  the sequence of statements is for error recovery which allows
1818      --  for misuse of an accept statement as a triggering statement.
1819
1820      Set_Statements
1821        (Delay_Alt_Node, P_Sequence_Of_Statements (SS_Eltm_Ortm_Tatm));
1822      return Delay_Alt_Node;
1823   end P_Delay_Alternative;
1824
1825   ----------------------------------
1826   -- 9.7.1  Terminate Alternative --
1827   ----------------------------------
1828
1829   --  TERMINATE_ALTERNATIVE ::= terminate;
1830
1831   --  Error_Recovery: Cannot raise Error_Resync
1832
1833   --  Note: the caller is responsible for setting the Pragmas_Before
1834   --  field of the returned N_Terminate_Alternative node.
1835
1836   function P_Terminate_Alternative return Node_Id is
1837      Terminate_Alt_Node : Node_Id;
1838
1839   begin
1840      Terminate_Alt_Node := New_Node (N_Terminate_Alternative, Token_Ptr);
1841      Scan; -- past TERMINATE
1842      TF_Semicolon;
1843
1844      --  For all other select alternatives, the sequence of statements
1845      --  after the alternative statement will swallow up any pragmas
1846      --  coming in this position. But the terminate alternative has no
1847      --  sequence of statements, so the pragmas here must be treated
1848      --  specially.
1849
1850      Set_Pragmas_After (Terminate_Alt_Node, P_Pragmas_Opt);
1851      return Terminate_Alt_Node;
1852   end P_Terminate_Alternative;
1853
1854   -----------------------------
1855   -- 9.7.2  Timed Entry Call --
1856   -----------------------------
1857
1858   --  Parsed by P_Select_Statement (9.7)
1859
1860   -----------------------------------
1861   -- 9.7.2  Entry Call Alternative --
1862   -----------------------------------
1863
1864   --  Parsed by P_Select_Statement (9.7)
1865
1866   -----------------------------------
1867   -- 9.7.3  Conditional Entry Call --
1868   -----------------------------------
1869
1870   --  Parsed by P_Select_Statement (9.7)
1871
1872   --------------------------------
1873   -- 9.7.4  Asynchronous Select --
1874   --------------------------------
1875
1876   --  Parsed by P_Select_Statement (9.7)
1877
1878   -----------------------------------
1879   -- 9.7.4  Triggering Alternative --
1880   -----------------------------------
1881
1882   --  Parsed by P_Select_Statement (9.7)
1883
1884   ---------------------------------
1885   -- 9.7.4  Triggering Statement --
1886   ---------------------------------
1887
1888   --  Parsed by P_Select_Statement (9.7)
1889
1890   ---------------------------
1891   -- 9.7.4  Abortable Part --
1892   ---------------------------
1893
1894   --  ABORTABLE_PART ::= SEQUENCE_OF_STATEMENTS
1895
1896   --  The caller has verified that THEN ABORT is present, and Token is
1897   --  pointing to the ABORT on entry (or if not, then we have an error)
1898
1899   --  Error recovery: cannot raise Error_Resync
1900
1901   function P_Abortable_Part return Node_Id is
1902      Abortable_Part_Node : Node_Id;
1903
1904   begin
1905      Abortable_Part_Node := New_Node (N_Abortable_Part, Token_Ptr);
1906      T_Abort; -- scan past ABORT
1907
1908      if Ada_Version = Ada_83 then
1909         Error_Msg_SP ("(Ada 83) asynchronous select not allowed!");
1910      end if;
1911
1912      Set_Statements (Abortable_Part_Node, P_Sequence_Of_Statements (SS_Sreq));
1913      return Abortable_Part_Node;
1914   end P_Abortable_Part;
1915
1916   --------------------------
1917   -- 9.8  Abort Statement --
1918   --------------------------
1919
1920   --  ABORT_STATEMENT ::= abort task_NAME {, task_NAME};
1921
1922   --  The caller has checked that the initial token is ABORT
1923
1924   --  Error recovery: cannot raise Error_Resync
1925
1926   function P_Abort_Statement return Node_Id is
1927      Abort_Node : Node_Id;
1928
1929   begin
1930      Abort_Node := New_Node (N_Abort_Statement, Token_Ptr);
1931      Scan; -- past ABORT
1932      Set_Names (Abort_Node, New_List);
1933
1934      loop
1935         Append (P_Name, Names (Abort_Node));
1936         exit when Token /= Tok_Comma;
1937         Scan; -- past comma
1938      end loop;
1939
1940      TF_Semicolon;
1941      return Abort_Node;
1942   end P_Abort_Statement;
1943
1944end Ch9;
1945