------------------------------------------------------------------------------
--                                                                          --
--                         GNAT COMPILER COMPONENTS                         --
--                                                                          --
--                              P A R . C H 3                               --
--                                                                          --
--                                 B o d y                                  --
--                                                                          --
--          Copyright (C) 1992-2021, Free Software Foundation, Inc.         --
--                                                                          --
-- GNAT is free software;  you can  redistribute it  and/or modify it under --
-- terms of the  GNU General Public License as published  by the Free Soft- --
-- ware  Foundation;  either version 3,  or (at your option) any later ver- --
-- sion.  GNAT is distributed in the hope that it will be useful, but WITH- --
-- OUT ANY WARRANTY;  without even the  implied warranty of MERCHANTABILITY --
-- or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License --
-- for  more details.  You should have  received  a copy of the GNU General --
-- Public License  distributed with GNAT; see file COPYING3.  If not, go to --
-- http://www.gnu.org/licenses for a complete copy of the license.          --
--                                                                          --
-- GNAT was originally developed  by the GNAT team at  New York University. --
-- Extensive contributions were provided by Ada Core Technologies Inc.      --
--                                                                          --
------------------------------------------------------------------------------

pragma Style_Checks (All_Checks);
--  Turn off subprogram body ordering check. Subprograms are in order
--  by RM section rather than alphabetical.

with Sinfo.CN;       use Sinfo.CN;

separate (Par)

---------
-- Ch3 --
---------

package body Ch3 is

   -----------------------
   -- Local Subprograms --
   -----------------------

   function P_Component_List                               return Node_Id;
   function P_Defining_Character_Literal                   return Node_Id;
   function P_Delta_Constraint                             return Node_Id;
   function P_Derived_Type_Def_Or_Private_Ext_Decl         return Node_Id;
   function P_Digits_Constraint                            return Node_Id;
   function P_Discriminant_Association                     return Node_Id;
   function P_Enumeration_Literal_Specification            return Node_Id;
   function P_Enumeration_Type_Definition                  return Node_Id;
   function P_Fixed_Point_Definition                       return Node_Id;
   function P_Floating_Point_Definition                    return Node_Id;
   function P_Index_Or_Discriminant_Constraint             return Node_Id;
   function P_Real_Range_Specification_Opt                 return Node_Id;
   function P_Subtype_Declaration                          return Node_Id;
   function P_Type_Declaration                             return Node_Id;
   function P_Modular_Type_Definition                      return Node_Id;
   function P_Variant                                      return Node_Id;
   function P_Variant_Part                                 return Node_Id;

   procedure Check_Restricted_Expression (N : Node_Id);
   --  Check that the expression N meets the Restricted_Expression syntax.
   --  The syntax is as follows:
   --
   --    RESTRICTED_EXPRESSION ::=
   --        RESTRICTED_RELATION {and RESTRICTED_RELATION}
   --      | RESTRICTED_RELATION {and then RESTRICTED_RELATION}
   --      | RESTRICTED_RELATION {or RESTRICTED_RELATION}
   --      | RESTRICTED_RELATION {or else RESTRICTED_RELATION}
   --      | RESTRICTED_RELATION {xor RESTRICTED_RELATION}
   --
   --    RESTRICTED_RELATION ::=
   --       SIMPLE_EXPRESSION [RELATIONAL_OPERATOR SIMPLE_EXPRESSION]
   --
   --  This syntax is used for choices when extensions (and set notations)
   --  are enabled, to remove the ambiguity of "when X in A | B". We consider
   --  it very unlikely that this will ever arise in practice.

   procedure P_Declarative_Items
     (Decls              : List_Id;
      Done               : out Boolean;
      Declare_Expression : Boolean;
      In_Spec            : Boolean);
   --  Scans out a single declarative item, or, in the case of a declaration
   --  with a list of identifiers, a list of declarations, one for each of the
   --  identifiers in the list. The declaration or declarations scanned are
   --  appended to the given list. Done indicates whether or not there may be
   --  additional declarative items to scan. If Done is True, then a decision
   --  has been made that there are no more items to scan. If Done is False,
   --  then there may be additional declarations to scan.
   --
   --  Declare_Expression is true if we are parsing a declare_expression, in
   --  which case we want to suppress certain style checking.
   --
   --  In_Spec is true if we are scanning a package declaration, and is used to
   --  generate an appropriate message if a statement is encountered in such a
   --  context.

   procedure P_Identifier_Declarations
     (Decls   : List_Id;
      Done    : out Boolean;
      In_Spec : Boolean);
   --  Scans out a set of declarations for an identifier or list of
   --  identifiers, and appends them to the given list. The parameters have
   --  the same significance as for P_Declarative_Items.

   procedure Statement_When_Declaration_Expected
     (Decls   : List_Id;
      Done    : out Boolean;
      In_Spec : Boolean);
   --  Called when a statement is found at a point where a declaration was
   --  expected. The parameters are as described for P_Declarative_Items.

   procedure Set_Declaration_Expected;
   --  Posts a "declaration expected" error messages at the start of the
   --  current token, and if this is the first such message issued, saves
   --  the message id in Missing_Begin_Msg, for possible later replacement.

   ---------------------------------
   -- Check_Restricted_Expression --
   ---------------------------------

   procedure Check_Restricted_Expression (N : Node_Id) is
   begin
      if Nkind (N) in N_Op_And | N_Op_Or | N_Op_Xor | N_And_Then | N_Or_Else
      then
         Check_Restricted_Expression (Left_Opnd (N));
         Check_Restricted_Expression (Right_Opnd (N));

      elsif Nkind (N) in N_In | N_Not_In
        and then Paren_Count (N) = 0
      then
         Error_Msg_N ("|this expression must be parenthesized!", N);
      end if;
   end Check_Restricted_Expression;

   -------------------
   -- Init_Expr_Opt --
   -------------------

   function Init_Expr_Opt (P : Boolean := False) return Node_Id is
   begin
      --  For colon, assume it means := unless it is at the end of
      --  a line, in which case guess that it means a semicolon.

      if Token = Tok_Colon then
         if Token_Is_At_End_Of_Line then
            T_Semicolon;
            return Empty;
         end if;

      --  Here if := or something that we will take as equivalent

      elsif Token = Tok_Colon_Equal
        or else Token = Tok_Equal
        or else Token = Tok_Is
      then
         null;

      --  Another possibility. If we have a literal followed by a semicolon,
      --  we assume that we have a missing colon-equal.

      elsif Token in Token_Class_Literal then
         declare
            Scan_State : Saved_Scan_State;

         begin
            Save_Scan_State (Scan_State);
            Scan; -- past literal or identifier

            if Token = Tok_Semicolon then
               Restore_Scan_State (Scan_State);
            else
               Restore_Scan_State (Scan_State);
               return Empty;
            end if;
         end;

      --  Otherwise we definitely have no initialization expression

      else
         return Empty;
      end if;

      --  Merge here if we have an initialization expression

      T_Colon_Equal;

      if P then
         return P_Expression;
      else
         return P_Expression_No_Right_Paren;
      end if;
   end Init_Expr_Opt;

   ----------------------------
   -- 3.1  Basic Declaration --
   ----------------------------

   --  Parsed by P_Basic_Declarative_Items (3.9)

   ------------------------------
   -- 3.1  Defining Identifier --
   ------------------------------

   --  DEFINING_IDENTIFIER ::= IDENTIFIER

   --  Error recovery: can raise Error_Resync

   function P_Defining_Identifier (C : Id_Check := None) return Node_Id is
      Ident_Node : Node_Id;

   begin
      --  Scan out the identifier. Note that this code is essentially identical
      --  to P_Identifier, except that in the call to Scan_Reserved_Identifier
      --  we set Force_Msg to True, since we want at least one message for each
      --  separate declaration (but not use) of a reserved identifier.

      --  Duplication should be removed, common code should be factored???

      if Token = Tok_Identifier then
         Check_Future_Keyword;

      --  If we have a reserved identifier, manufacture an identifier with
      --  a corresponding name after posting an appropriate error message

      elsif Is_Reserved_Identifier (C) then
         Scan_Reserved_Identifier (Force_Msg => True);

      --  Otherwise we have junk that cannot be interpreted as an identifier

      else
         T_Identifier; -- to give message
         raise Error_Resync;
      end if;

      if Style_Check then
         Style.Check_Defining_Identifier_Casing;
      end if;

      Ident_Node := Token_Node;
      Scan; -- past the identifier

      --  If we already have a defining identifier, clean it out and make
      --  a new clean identifier. This situation arises in some error cases
      --  and we need to fix it.

      if Nkind (Ident_Node) = N_Defining_Identifier then
         Ident_Node := Make_Identifier (Sloc (Ident_Node), Chars (Ident_Node));
      end if;

      --  Change identifier to defining identifier if not in error

      if Ident_Node /= Error then
         Change_Identifier_To_Defining_Identifier (Ident_Node);

         --  Warn if standard redefinition, except that we never warn on a
         --  record field definition (since this is always a harmless case).

         if not Inside_Record_Definition then
            Warn_If_Standard_Redefinition (Ident_Node);
         end if;
      end if;

      return Ident_Node;
   end P_Defining_Identifier;

   -----------------------------
   -- 3.2.1  Type Declaration --
   -----------------------------

   --  TYPE_DECLARATION ::=
   --    FULL_TYPE_DECLARATION
   --  | INCOMPLETE_TYPE_DECLARATION
   --  | PRIVATE_TYPE_DECLARATION
   --  | PRIVATE_EXTENSION_DECLARATION

   --  FULL_TYPE_DECLARATION ::=
   --    type DEFINING_IDENTIFIER [KNOWN_DISCRIMINANT_PART] is TYPE_DEFINITION
   --      [ASPECT_SPECIFICATIONS];
   --  | CONCURRENT_TYPE_DECLARATION

   --  INCOMPLETE_TYPE_DECLARATION ::=
   --    type DEFINING_IDENTIFIER [DISCRIMINANT_PART] [is tagged];

   --  PRIVATE_TYPE_DECLARATION ::=
   --    type DEFINING_IDENTIFIER [DISCRIMINANT_PART]
   --      is [abstract] [tagged] [limited] private
   --        [ASPECT_SPECIFICATIONS];

   --  PRIVATE_EXTENSION_DECLARATION ::=
   --    type DEFINING_IDENTIFIER [DISCRIMINANT_PART] is
   --      [abstract] [limited | synchronized]
   --        new ancestor_SUBTYPE_INDICATION [and INTERFACE_LIST]
   --          with private [ASPECT_SPECIFICATIONS];

   --  TYPE_DEFINITION ::=
   --    ENUMERATION_TYPE_DEFINITION  | INTEGER_TYPE_DEFINITION
   --  | REAL_TYPE_DEFINITION         | ARRAY_TYPE_DEFINITION
   --  | RECORD_TYPE_DEFINITION       | ACCESS_TYPE_DEFINITION
   --  | DERIVED_TYPE_DEFINITION      | INTERFACE_TYPE_DEFINITION

   --  INTEGER_TYPE_DEFINITION ::=
   --    SIGNED_INTEGER_TYPE_DEFINITION
   --    MODULAR_TYPE_DEFINITION

   --  INTERFACE_TYPE_DEFINITION ::=
   --    [limited | task | protected | synchronized ] interface
   --      [and INTERFACE_LIST]

   --  Error recovery: can raise Error_Resync

   --  The processing for full type declarations, incomplete type declarations,
   --  private type declarations and type definitions is included in this
   --  function. The processing for concurrent type declarations is NOT here,
   --  but rather in chapter 9 (this function handles only declarations
   --  starting with TYPE).

   function P_Type_Declaration return Node_Id is
      Abstract_Present : Boolean := False;
      Abstract_Loc     : Source_Ptr := No_Location;
      Decl_Node        : Node_Id;
      Discr_List       : List_Id;
      Discr_Sloc       : Source_Ptr;
      End_Labl         : Node_Id;
      Ident_Node       : Node_Id;
      Is_Derived_Iface : Boolean := False;
      Type_Loc         : Source_Ptr;
      Type_Start_Col   : Column_Number;
      Unknown_Dis      : Boolean;

      Typedef_Node : Node_Id;
      --  Normally holds type definition, except in the case of a private
      --  extension declaration, in which case it holds the declaration itself

   begin
      Type_Loc := Token_Ptr;
      Type_Start_Col := Start_Column;

      --  If we have TYPE, then proceed ahead and scan identifier

      if Token = Tok_Type then
         Type_Token_Location := Type_Loc;
         Scan; -- past TYPE
         Ident_Node := P_Defining_Identifier (C_Is);

      --  Otherwise this is an error case

      else
         T_Type;
         Type_Token_Location := Type_Loc;
         Ident_Node := P_Defining_Identifier (C_Is);
      end if;

      Discr_Sloc := Token_Ptr;

      if P_Unknown_Discriminant_Part_Opt then
         Unknown_Dis := True;
         Discr_List := No_List;
      else
         Unknown_Dis := False;
         Discr_List := P_Known_Discriminant_Part_Opt;
      end if;

      --  Incomplete type declaration. We complete the processing for this
      --  case here and return the resulting incomplete type declaration node

      if Token = Tok_Semicolon then
         Scan; -- past ;
         Decl_Node := New_Node (N_Incomplete_Type_Declaration, Type_Loc);
         Set_Defining_Identifier (Decl_Node, Ident_Node);
         Set_Unknown_Discriminants_Present (Decl_Node, Unknown_Dis);
         Set_Discriminant_Specifications (Decl_Node, Discr_List);
         return Decl_Node;

      else
         Decl_Node := Empty;
      end if;

      --  Full type declaration or private type declaration, must have IS

      if Token = Tok_Equal then
         TF_Is;
         Scan; -- past = used in place of IS

      elsif Token = Tok_Renames then
         Error_Msg_SC  -- CODEFIX
           ("RENAMES should be IS");
         Scan; -- past RENAMES used in place of IS

      else
         TF_Is;
      end if;

      --  First an error check, if we have two identifiers in a row, a likely
      --  possibility is that the first of the identifiers is an incorrectly
      --  spelled keyword.

      if Token = Tok_Identifier then
         declare
            SS : Saved_Scan_State;
            I2 : Boolean;

         begin
            Save_Scan_State (SS);
            Scan; -- past initial identifier
            I2 := (Token = Tok_Identifier);
            Restore_Scan_State (SS);

            if I2
              and then
                (Bad_Spelling_Of (Tok_Abstract) or else
                 Bad_Spelling_Of (Tok_Access)   or else
                 Bad_Spelling_Of (Tok_Aliased)  or else
                 Bad_Spelling_Of (Tok_Constant))
            then
               null;
            end if;
         end;
      end if;

      --  Check for misuse of Ada 95 keyword abstract in Ada 83 mode

      if Token_Name = Name_Abstract then
         Check_95_Keyword (Tok_Abstract, Tok_Tagged);
         Check_95_Keyword (Tok_Abstract, Tok_New);
      end if;

      --  Check cases of misuse of ABSTRACT

      if Token = Tok_Abstract then
         Abstract_Present := True;
         Abstract_Loc     := Token_Ptr;
         Scan; -- past ABSTRACT

         --  Ada 2005 (AI-419): AARM 3.4 (2/2)

         if (Ada_Version < Ada_2005 and then Token = Tok_Limited)
           or else Token = Tok_Private
           or else Token = Tok_Record
           or else Token = Tok_Null
         then
            Error_Msg_AP ("TAGGED expected");
         end if;
      end if;

      --  Check for misuse of Ada 95 keyword Tagged

      if Token_Name = Name_Tagged then
         Check_95_Keyword (Tok_Tagged, Tok_Private);
         Check_95_Keyword (Tok_Tagged, Tok_Limited);
         Check_95_Keyword (Tok_Tagged, Tok_Record);
      end if;

      --  Special check for misuse of Aliased

      if Token = Tok_Aliased or else Token_Name = Name_Aliased then
         Error_Msg_SC ("ALIASED not allowed in type definition");
         Scan; -- past ALIASED
      end if;

      --  The following processing deals with either a private type declaration
      --  or a full type declaration. In the private type case, we build the
      --  N_Private_Type_Declaration node, setting its Tagged_Present and
      --  Limited_Present flags, on encountering the Private keyword, and
      --  leave Typedef_Node set to Empty. For the full type declaration
      --  case, Typedef_Node gets set to the type definition.

      Typedef_Node := Empty;

      --  Switch on token following the IS. The loop normally runs once. It
      --  only runs more than once if an error is detected, to try again after
      --  detecting and fixing up the error.

      loop
         case Token is
            when Tok_Access
               | Tok_Not  --  Ada 2005 (AI-231)
            =>
               Typedef_Node := P_Access_Type_Definition;
               exit;

            when Tok_Array =>
               Typedef_Node := P_Array_Type_Definition;
               exit;

            when Tok_Delta =>
               Typedef_Node := P_Fixed_Point_Definition;
               exit;

            when Tok_Digits =>
               Typedef_Node := P_Floating_Point_Definition;
               exit;

            when Tok_In =>
               Ignore (Tok_In);

            when Tok_Integer_Literal =>
               T_Range;
               Typedef_Node := P_Signed_Integer_Type_Definition;
               exit;

            when Tok_Null =>
               Typedef_Node := P_Record_Definition;
               exit;

            when Tok_Left_Paren =>
               Typedef_Node := P_Enumeration_Type_Definition;

               End_Labl := Make_Identifier (Token_Ptr, Chars (Ident_Node));
               Set_Comes_From_Source (End_Labl, False);

               Set_End_Label (Typedef_Node, End_Labl);
               exit;

            when Tok_Mod =>
               Typedef_Node := P_Modular_Type_Definition;
               exit;

            when Tok_New =>
               Typedef_Node := P_Derived_Type_Def_Or_Private_Ext_Decl;

               if Nkind (Typedef_Node) = N_Derived_Type_Definition
                 and then Present (Record_Extension_Part (Typedef_Node))
               then
                  End_Labl := Make_Identifier (Token_Ptr, Chars (Ident_Node));
                  Set_Comes_From_Source (End_Labl, False);

                  Set_End_Label
                    (Record_Extension_Part (Typedef_Node), End_Labl);
               end if;

               exit;

            when Tok_Range =>
               Typedef_Node := P_Signed_Integer_Type_Definition;
               exit;

            when Tok_Record =>
               Typedef_Node := P_Record_Definition;

               End_Labl := Make_Identifier (Token_Ptr, Chars (Ident_Node));
               Set_Comes_From_Source (End_Labl, False);

               Set_End_Label (Typedef_Node, End_Labl);
               exit;

            when Tok_Tagged =>
               Scan; -- past TAGGED

               --  Ada 2005 (AI-326): If the words IS TAGGED appear, the type
               --  is a tagged incomplete type.

               if Ada_Version >= Ada_2005
                 and then Token = Tok_Semicolon
               then
                  Scan; -- past ;

                  Decl_Node :=
                    New_Node (N_Incomplete_Type_Declaration, Type_Loc);
                  Set_Defining_Identifier           (Decl_Node, Ident_Node);
                  Set_Tagged_Present                (Decl_Node);
                  Set_Unknown_Discriminants_Present (Decl_Node, Unknown_Dis);
                  Set_Discriminant_Specifications   (Decl_Node, Discr_List);

                  return Decl_Node;
               end if;

               if Token = Tok_Abstract then
                  Error_Msg_SC -- CODEFIX
                    ("ABSTRACT must come before TAGGED");
                  Abstract_Present := True;
                  Abstract_Loc := Token_Ptr;
                  Scan; -- past ABSTRACT
               end if;

               if Token = Tok_Limited then
                  Scan; -- past LIMITED

                  --  TAGGED LIMITED PRIVATE case

                  if Token = Tok_Private then
                     Decl_Node :=
                       New_Node (N_Private_Type_Declaration, Type_Loc);
                     Set_Tagged_Present (Decl_Node, True);
                     Set_Limited_Present (Decl_Node, True);
                     Scan; -- past PRIVATE

                  --  TAGGED LIMITED RECORD

                  else
                     Typedef_Node := P_Record_Definition;
                     Set_Tagged_Present (Typedef_Node, True);
                     Set_Limited_Present (Typedef_Node, True);

                     End_Labl :=
                       Make_Identifier (Token_Ptr, Chars (Ident_Node));
                     Set_Comes_From_Source (End_Labl, False);

                     Set_End_Label (Typedef_Node, End_Labl);
                  end if;

               else
                  --  TAGGED PRIVATE

                  if Token = Tok_Private then
                     Decl_Node :=
                       New_Node (N_Private_Type_Declaration, Type_Loc);
                     Set_Tagged_Present (Decl_Node, True);
                     Scan; -- past PRIVATE

                  --  TAGGED RECORD

                  else
                     Typedef_Node := P_Record_Definition;
                     Set_Tagged_Present (Typedef_Node, True);

                     End_Labl :=
                       Make_Identifier (Token_Ptr, Chars (Ident_Node));
                     Set_Comes_From_Source (End_Labl, False);

                     Set_End_Label (Typedef_Node, End_Labl);
                  end if;
               end if;

               exit;

            when Tok_Limited =>
               Scan; -- past LIMITED

               loop
                  if Token = Tok_Tagged then
                     Error_Msg_SC -- CODEFIX
                       ("TAGGED must come before LIMITED");
                     Scan; -- past TAGGED

                  elsif Token = Tok_Abstract then
                     Error_Msg_SC -- CODEFIX
                       ("ABSTRACT must come before LIMITED");
                     Scan; -- past ABSTRACT

                  else
                     exit;
                  end if;
               end loop;

               --  LIMITED RECORD or LIMITED NULL RECORD

               if Token = Tok_Record or else Token = Tok_Null then
                  if Ada_Version = Ada_83 then
                     Error_Msg_SP
                       ("(Ada 83) limited record declaration not allowed!");

                  --  In Ada 2005, "abstract limited" can appear before "new",
                  --  but it cannot be part of an untagged record declaration.

                  elsif Abstract_Present
                    and then Prev_Token /= Tok_Tagged
                  then
                     Error_Msg_SP ("TAGGED expected");
                  end if;

                  Typedef_Node := P_Record_Definition;
                  Set_Limited_Present (Typedef_Node, True);
                  End_Labl := Make_Identifier (Token_Ptr, Chars (Ident_Node));
                  Set_Comes_From_Source (End_Labl, False);

                  Set_End_Label (Typedef_Node, End_Labl);

               --  Ada 2005 (AI-251): LIMITED INTERFACE

               --  If we are compiling in Ada 83 or Ada 95 mode, "interface"
               --  is not a reserved word but we force its analysis to
               --  generate the corresponding usage error.

               elsif Token = Tok_Interface
                 or else (Token = Tok_Identifier
                           and then Chars (Token_Node) = Name_Interface)
               then
                  Typedef_Node :=
                    P_Interface_Type_Definition (Abstract_Present);
                  Abstract_Present := True;
                  Set_Limited_Present (Typedef_Node);

                  if Nkind (Typedef_Node) = N_Derived_Type_Definition then
                     Is_Derived_Iface := True;
                  end if;

                  --  Ada 2005 (AI-419): LIMITED NEW

               elsif Token = Tok_New then
                  Error_Msg_Ada_2005_Extension ("LIMITED in derived type");

                  Typedef_Node := P_Derived_Type_Def_Or_Private_Ext_Decl;
                  Set_Limited_Present (Typedef_Node);

                  if Nkind (Typedef_Node) = N_Derived_Type_Definition
                    and then Present (Record_Extension_Part (Typedef_Node))
                  then
                     End_Labl :=
                       Make_Identifier (Token_Ptr, Chars (Ident_Node));
                     Set_Comes_From_Source (End_Labl, False);

                     Set_End_Label
                       (Record_Extension_Part (Typedef_Node), End_Labl);
                  end if;

               --  LIMITED PRIVATE is the only remaining possibility here

               else
                  Decl_Node := New_Node (N_Private_Type_Declaration, Type_Loc);
                  Set_Limited_Present (Decl_Node, True);
                  T_Private; -- past PRIVATE (or complain if not there)
               end if;

               exit;

            --  Here we have an identifier after the IS, which is certainly
            --  wrong and which might be one of several different mistakes.

            when Tok_Identifier =>

               --  First case, if identifier is on same line, then probably we
               --  have something like "type X is Integer .." and the best
               --  diagnosis is a missing NEW. Note: the missing new message
               --  will be posted by P_Derived_Type_Def_Or_Private_Ext_Decl.

               if not Token_Is_At_Start_Of_Line then
                  Typedef_Node := P_Derived_Type_Def_Or_Private_Ext_Decl;

               --  If the identifier is at the start of the line, and is in the
               --  same column as the type declaration itself then we consider
               --  that we had a missing type definition on the previous line

               elsif Start_Column <= Type_Start_Col then
                  Error_Msg_AP ("type definition expected");
                  Typedef_Node := Error;

               --  If the identifier is at the start of the line, and is in
               --  a column to the right of the type declaration line, then we
               --  may have something like:

               --    type x is
               --       r : integer

               --  and the best diagnosis is a missing record keyword

               else
                  Typedef_Node := P_Record_Definition;
               end if;

               exit;

            --  Ada 2005 (AI-251): INTERFACE

            when Tok_Interface =>
               Typedef_Node := P_Interface_Type_Definition (Abstract_Present);
               Abstract_Present := True;
               exit;

            when Tok_Private =>
               Decl_Node := New_Node (N_Private_Type_Declaration, Type_Loc);
               Scan; -- past PRIVATE

               --  Check error cases of private [abstract] tagged

               if Token = Tok_Abstract then
                  Error_Msg_SC ("`ABSTRACT TAGGED` must come before PRIVATE");
                  Scan; -- past ABSTRACT

                  if Token = Tok_Tagged then
                     Scan; -- past TAGGED
                  end if;

               elsif Token = Tok_Tagged then
                  Error_Msg_SC ("TAGGED must come before PRIVATE");
                  Scan; -- past TAGGED
               end if;

               exit;

            --  Ada 2005 (AI-345): Protected, synchronized or task interface
            --  or Ada 2005 (AI-443): Synchronized private extension.

            when Tok_Protected
               | Tok_Synchronized
               | Tok_Task
            =>
               declare
                  Saved_Token : constant Token_Type := Token;

               begin
                  Scan; -- past TASK, PROTECTED or SYNCHRONIZED

                  --  Synchronized private extension

                  if Token = Tok_New then
                     Typedef_Node := P_Derived_Type_Def_Or_Private_Ext_Decl;

                     if Saved_Token = Tok_Synchronized then
                        if Nkind (Typedef_Node) =
                          N_Derived_Type_Definition
                        then
                           Error_Msg_N
                             ("SYNCHRONIZED not allowed for record extension",
                              Typedef_Node);
                        else
                           Set_Synchronized_Present (Typedef_Node);
                        end if;

                     else
                        Error_Msg_SC ("invalid kind of private extension");
                     end if;

                  --  Interface

                  else
                     if Token /= Tok_Interface then
                        Error_Msg_SC ("NEW or INTERFACE expected");
                     end if;

                     Typedef_Node :=
                       P_Interface_Type_Definition (Abstract_Present);
                     Abstract_Present := True;

                     case Saved_Token is
                        when Tok_Task =>
                           Set_Task_Present         (Typedef_Node);

                        when Tok_Protected =>
                           Set_Protected_Present    (Typedef_Node);

                        when Tok_Synchronized =>
                           Set_Synchronized_Present (Typedef_Node);

                        when others =>
                           pragma Assert (False);
                           null;
                     end case;
                  end if;
               end;

               exit;

            --  Anything else is an error

            when others =>
               if Bad_Spelling_Of (Tok_Access)
                    or else
                  Bad_Spelling_Of (Tok_Array)
                    or else
                  Bad_Spelling_Of (Tok_Delta)
                    or else
                  Bad_Spelling_Of (Tok_Digits)
                    or else
                  Bad_Spelling_Of (Tok_Limited)
                    or else
                  Bad_Spelling_Of (Tok_Private)
                    or else
                  Bad_Spelling_Of (Tok_Range)
                    or else
                  Bad_Spelling_Of (Tok_Record)
                    or else
                  Bad_Spelling_Of (Tok_Tagged)
               then
                  null;

               else
                  Error_Msg_AP ("type definition expected");
                  raise Error_Resync;
               end if;
         end case;
      end loop;

      --  For the private type declaration case, the private type declaration
      --  node has been built, with the Tagged_Present and Limited_Present
      --  flags set as needed, and Typedef_Node is left set to Empty.

      if No (Typedef_Node) then
         Set_Unknown_Discriminants_Present (Decl_Node, Unknown_Dis);
         Set_Abstract_Present (Decl_Node, Abstract_Present);

      --  For a private extension declaration, Typedef_Node contains the
      --  N_Private_Extension_Declaration node, which we now complete. Note
      --  that the private extension declaration, unlike a full type
      --  declaration, does permit unknown discriminants.

      elsif Nkind (Typedef_Node) = N_Private_Extension_Declaration then
         Decl_Node := Typedef_Node;
         Set_Sloc (Decl_Node, Type_Loc);
         Set_Unknown_Discriminants_Present (Decl_Node, Unknown_Dis);
         Set_Abstract_Present (Typedef_Node, Abstract_Present);

      --  In the full type declaration case, Typedef_Node has the type
      --  definition and here is where we build the full type declaration
      --  node. This is also where we check for improper use of an unknown
      --  discriminant part (not allowed for full type declaration).

      else
         if Nkind (Typedef_Node) = N_Record_Definition
           or else (Nkind (Typedef_Node) = N_Derived_Type_Definition
                      and then Present (Record_Extension_Part (Typedef_Node)))
           or else Is_Derived_Iface
         then
            Set_Abstract_Present (Typedef_Node, Abstract_Present);

         elsif Abstract_Present then
            Error_Msg ("ABSTRACT not allowed here, ignored", Abstract_Loc);
         end if;

         Decl_Node := New_Node (N_Full_Type_Declaration, Type_Loc);
         Set_Type_Definition (Decl_Node, Typedef_Node);

         if Unknown_Dis then
            Error_Msg
              ("full type declaration cannot have unknown discriminants",
                Discr_Sloc);
         end if;
      end if;

      --  Remaining processing is common for all three cases

      Set_Defining_Identifier (Decl_Node, Ident_Node);
      Set_Discriminant_Specifications (Decl_Node, Discr_List);
      P_Aspect_Specifications (Decl_Node);
      return Decl_Node;
   end P_Type_Declaration;

   ----------------------------------
   -- 3.2.1  Full Type Declaration --
   ----------------------------------

   --  Parsed by P_Type_Declaration (3.2.1)

   ----------------------------
   -- 3.2.1  Type Definition --
   ----------------------------

   --  Parsed by P_Type_Declaration (3.2.1)

   --------------------------------
   -- 3.2.2  Subtype Declaration --
   --------------------------------

   --  SUBTYPE_DECLARATION ::=
   --    subtype DEFINING_IDENTIFIER is [NULL_EXCLUSION] SUBTYPE_INDICATION
   --      [ASPECT_SPECIFICATIONS];

   --  The caller has checked that the initial token is SUBTYPE

   --  Error recovery: can raise Error_Resync

   function P_Subtype_Declaration return Node_Id is
      Decl_Node        : Node_Id;
      Not_Null_Present : Boolean := False;

   begin
      Decl_Node := New_Node (N_Subtype_Declaration, Token_Ptr);
      Scan; -- past SUBTYPE
      Set_Defining_Identifier (Decl_Node, P_Defining_Identifier (C_Is));
      TF_Is;

      if Token = Tok_New then
         Error_Msg_SC  -- CODEFIX
           ("NEW ignored (only allowed in type declaration)");
         Scan; -- past NEW
      end if;

      Not_Null_Present := P_Null_Exclusion; --  Ada 2005 (AI-231)
      Set_Null_Exclusion_Present (Decl_Node, Not_Null_Present);

      Set_Subtype_Indication
        (Decl_Node, P_Subtype_Indication (Not_Null_Present));
      P_Aspect_Specifications (Decl_Node);
      return Decl_Node;
   end P_Subtype_Declaration;

   -------------------------------
   -- 3.2.2  Subtype Indication --
   -------------------------------

   --  SUBTYPE_INDICATION ::=
   --    [not null] SUBTYPE_MARK [CONSTRAINT]

   --  Error recovery: can raise Error_Resync

   function P_Null_Exclusion
     (Allow_Anonymous_In_95 : Boolean := False) return Boolean
   is
      Not_Loc : constant Source_Ptr := Token_Ptr;
      --  Source position of "not", if present

   begin
      if Token /= Tok_Not then
         return False;

      else
         Scan; --  past NOT

         if Token = Tok_Null then
            Scan; --  past NULL

            --  Ada 2005 (AI-441, AI-447): null_exclusion is illegal in Ada 95,
            --  except in the case of anonymous access types.

            --  Allow_Anonymous_In_95 will be True if we're parsing a formal
            --  parameter or discriminant, which are the only places where
            --  anonymous access types occur in Ada 95. "Formal : not null
            --  access ..." is legal in Ada 95, whereas "Formal : not null
            --  Named_Access_Type" is not.

            if Ada_Version >= Ada_2005
              or else (Ada_Version >= Ada_95
                        and then Allow_Anonymous_In_95
                        and then Token = Tok_Access)
            then
               null; -- OK

            else
               Error_Msg
                 ("`NOT NULL` access type is an Ada 2005 extension", Not_Loc);
               Error_Msg
                 ("\unit should be compiled with -gnat05 switch", Not_Loc);
            end if;

         else
            Error_Msg_SP ("NULL expected");
         end if;

         if Token = Tok_New then
            Error_Msg ("`NOT NULL` comes after NEW, not before", Not_Loc);
         end if;

         return True;
      end if;
   end P_Null_Exclusion;

   function P_Subtype_Indication
     (Not_Null_Present : Boolean := False) return Node_Id
   is
      Type_Node : Node_Id;

   begin
      if Token = Tok_Identifier or else Token = Tok_Operator_Symbol then
         Type_Node := P_Subtype_Mark;
         return P_Subtype_Indication (Type_Node, Not_Null_Present);

      else
         --  Check for error of using record definition and treat it nicely,
         --  otherwise things are really messed up, so resynchronize.

         if Token = Tok_Record then
            Error_Msg_SC ("anonymous record definition not permitted");
            Discard_Junk_Node (P_Record_Definition);
            return Error;

         else
            Error_Msg_AP ("subtype indication expected");
            raise Error_Resync;
         end if;
      end if;
   end P_Subtype_Indication;

   --  The following function is identical except that it is called with
   --  the subtype mark already scanned out, and it scans out the constraint

   --  Error recovery: can raise Error_Resync

   function P_Subtype_Indication
     (Subtype_Mark     : Node_Id;
      Not_Null_Present : Boolean := False) return Node_Id
   is
      Indic_Node  : Node_Id;
      Constr_Node : Node_Id;

   begin
      Constr_Node := P_Constraint_Opt;

      if No (Constr_Node)
        or else
          (Nkind (Constr_Node) = N_Range_Constraint
             and then Nkind (Range_Expression (Constr_Node)) = N_Error)
      then
         return Subtype_Mark;
      else
         if Not_Null_Present then
            Error_Msg_SP ("`NOT NULL` not allowed if constraint given");
         end if;

         Indic_Node := New_Node (N_Subtype_Indication, Sloc (Subtype_Mark));
         Set_Subtype_Mark (Indic_Node, Check_Subtype_Mark (Subtype_Mark));
         Set_Constraint (Indic_Node, Constr_Node);
         return Indic_Node;
      end if;
   end P_Subtype_Indication;

   -------------------------
   -- 3.2.2  Subtype Mark --
   -------------------------

   --  SUBTYPE_MARK ::= subtype_NAME;

   --  Note: The subtype mark which appears after an IN or NOT IN
   --  operator is parsed by P_Range_Or_Subtype_Mark (3.5)

   --  Error recovery: cannot raise Error_Resync

   function P_Subtype_Mark return Node_Id is
   begin
      return P_Subtype_Mark_Resync;
   exception
      when Error_Resync =>
         return Error;
   end P_Subtype_Mark;

   --  This routine differs from P_Subtype_Mark in that it insists that an
   --  identifier be present, and if it is not, it raises Error_Resync.

   --  Error recovery: can raise Error_Resync

   function P_Subtype_Mark_Resync return Node_Id is
      Type_Node : Node_Id;

   begin
      if Token = Tok_Access then
         Error_Msg_SC ("anonymous access type definition not allowed here");
         Scan; -- past ACCESS
      end if;

      if Token = Tok_Array then
         Error_Msg_SC ("anonymous array definition not allowed here");
         Discard_Junk_Node (P_Array_Type_Definition);
         return Error;

      else
         Type_Node := P_Qualified_Simple_Name_Resync;

         --  Check for a subtype mark attribute. The only valid possibilities
         --  are 'CLASS and 'BASE. Anything else is a definite error. We may
         --  as well catch it here.

         if Token = Tok_Apostrophe then
            return P_Subtype_Mark_Attribute (Type_Node);
         else
            return Type_Node;
         end if;
      end if;
   end P_Subtype_Mark_Resync;

   --  The following function is called to scan out a subtype mark attribute.
   --  The caller has already scanned out the subtype mark, which is passed in
   --  as the argument, and has checked that the current token is apostrophe.

   --  Only a special subclass of attributes, called type attributes
   --  (see Snames package) are allowed in this syntactic position.

   --  Note: if the apostrophe is followed by other than an identifier, then
   --  the input expression is returned unchanged, and the scan pointer is
   --  left pointing to the apostrophe.

   --  Error recovery: can raise Error_Resync

   function P_Subtype_Mark_Attribute (Type_Node : Node_Id) return Node_Id is
      Attr_Node  : Node_Id := Empty;
      Scan_State : Saved_Scan_State;
      Prefix     : Node_Id;

   begin
      Prefix := Check_Subtype_Mark (Type_Node);

      if Prefix = Error then
         raise Error_Resync;
      end if;

      --  Loop through attributes appearing (more than one can appear as for
      --  for example in X'Base'Class). We are at an apostrophe on entry to
      --  this loop, and it runs once for each attribute parsed, with
      --  Prefix being the current possible prefix if it is an attribute.

      loop
         Save_Scan_State (Scan_State); -- at Apostrophe
         Scan; -- past apostrophe

         if Token /= Tok_Identifier then
            Restore_Scan_State (Scan_State); -- to apostrophe
            return Prefix; -- no attribute after all

         elsif not Is_Type_Attribute_Name (Token_Name) then
            Error_Msg_N
              ("attribute & may not be used in a subtype mark", Token_Node);
            raise Error_Resync;

         else
            Attr_Node :=
              Make_Attribute_Reference (Prev_Token_Ptr,
                Prefix => Prefix,
                Attribute_Name => Token_Name);
            Scan; -- past type attribute identifier
         end if;

         exit when Token /= Tok_Apostrophe;
         Prefix := Attr_Node;
      end loop;

      --  Fall through here after scanning type attribute

      return Attr_Node;
   end P_Subtype_Mark_Attribute;

   -----------------------
   -- 3.2.2  Constraint --
   -----------------------

   --  CONSTRAINT ::= SCALAR_CONSTRAINT | COMPOSITE_CONSTRAINT

   --  SCALAR_CONSTRAINT ::=
   --    RANGE_CONSTRAINT | DIGITS_CONSTRAINT | DELTA_CONSTRAINT

   --  COMPOSITE_CONSTRAINT ::=
   --    INDEX_CONSTRAINT | DISCRIMINANT_CONSTRAINT

   --  If no constraint is present, this function returns Empty

   --  Error recovery: can raise Error_Resync

   function P_Constraint_Opt return Node_Id is
   begin
      if Token = Tok_Range or else Bad_Spelling_Of (Tok_Range) then
         return P_Range_Constraint;

      elsif Token = Tok_Digits or else Bad_Spelling_Of (Tok_Digits) then
         return P_Digits_Constraint;

      elsif Token = Tok_Delta or else Bad_Spelling_Of (Tok_Delta) then
         return P_Delta_Constraint;

      elsif Token = Tok_Left_Paren then
         return P_Index_Or_Discriminant_Constraint;

      elsif Token = Tok_In then
         Ignore (Tok_In);
         return P_Constraint_Opt;

      --  One more possibility is e.g. 1 .. 10 (i.e. missing RANGE keyword)

      elsif Token = Tok_Identifier      or else
            Token = Tok_Integer_Literal or else
            Token = Tok_Real_Literal
      then
         declare
            Scan_State : Saved_Scan_State;

         begin
            Save_Scan_State (Scan_State); -- at identifier or literal
            Scan; -- past identifier or literal

            if Token = Tok_Dot_Dot then
               Restore_Scan_State (Scan_State);
               Error_Msg_BC ("missing RANGE keyword");
               return P_Range_Constraint;
            else
               Restore_Scan_State (Scan_State);
               return Empty;
            end if;
         end;

      --  Nothing worked, no constraint there

      else
         return Empty;
      end if;
   end P_Constraint_Opt;

   ------------------------------
   -- 3.2.2  Scalar Constraint --
   ------------------------------

   --  Parsed by P_Constraint_Opt (3.2.2)

   ---------------------------------
   -- 3.2.2  Composite Constraint --
   ---------------------------------

   --  Parsed by P_Constraint_Opt (3.2.2)

   --------------------------------------------------------
   -- 3.3  Identifier Declarations (Also 7.4, 8.5, 11.1) --
   --------------------------------------------------------

   --  This routine scans out a declaration starting with an identifier:

   --  OBJECT_DECLARATION ::=
   --    DEFINING_IDENTIFIER_LIST : [aliased] [constant]
   --      [NULL_EXCLUSION] SUBTYPE_INDICATION [:= EXPRESSION]
   --        [ASPECT_SPECIFICATIONS];
   --  | DEFINING_IDENTIFIER_LIST : [aliased] [constant]
   --      ACCESS_DEFINITION [:= EXPRESSION]
   --        [ASPECT_SPECIFICATIONS];
   --  | DEFINING_IDENTIFIER_LIST : [aliased] [constant]
   --      ARRAY_TYPE_DEFINITION [:= EXPRESSION]
   --        [ASPECT_SPECIFICATIONS];

   --  NUMBER_DECLARATION ::=
   --    DEFINING_IDENTIFIER_LIST : constant ::= static_EXPRESSION;

   --  OBJECT_RENAMING_DECLARATION ::=
   --    DEFINING_IDENTIFIER :
   --      [NULL_EXCLUSION] SUBTYPE_MARK renames object_NAME
   --        [ASPECT_SPECIFICATIONS];
   --  | DEFINING_IDENTIFIER :
   --      ACCESS_DEFINITION renames object_NAME
   --        [ASPECT_SPECIFICATIONS];

   --  EXCEPTION_RENAMING_DECLARATION ::=
   --    DEFINING_IDENTIFIER : exception renames exception_NAME
   --      [ASPECT_SPECIFICATIONS];

   --  EXCEPTION_DECLARATION ::=
   --    DEFINING_IDENTIFIER_LIST : exception
   --      [ASPECT_SPECIFICATIONS];

   --  Note that the ALIASED indication in an object declaration is
   --  marked by a flag in the parent node.

   --  The caller has checked that the initial token is an identifier

   --  The value returned is a list of declarations, one for each identifier
   --  in the list (as described in Sinfo, we always split up multiple
   --  declarations into the equivalent sequence of single declarations
   --  using the More_Ids and Prev_Ids flags to preserve the source).

   --  If the identifier turns out to be a probable statement rather than
   --  an identifier, then the scan is left pointing to the identifier and
   --  No_List is returned.

   --  Error recovery: can raise Error_Resync

   procedure P_Identifier_Declarations
     (Decls   : List_Id;
      Done    : out Boolean;
      In_Spec : Boolean)
   is
      Acc_Node         : Node_Id;
      Decl_Node        : Node_Id;
      Type_Node        : Node_Id;
      Ident_Sloc       : Source_Ptr;
      Scan_State       : Saved_Scan_State;
      List_OK          : Boolean := True;
      Ident            : Nat;
      Init_Expr        : Node_Id;
      Init_Loc         : Source_Ptr;
      Con_Loc          : Source_Ptr;
      Not_Null_Present : Boolean := False;

      Idents : array (Int range 1 .. 4096) of Entity_Id;
      --  Used to save identifiers in the identifier list. The upper bound
      --  of 4096 is expected to be infinite in practice, and we do not even
      --  bother to check if this upper bound is exceeded.

      Num_Idents : Nat := 1;
      --  Number of identifiers stored in Idents

      procedure No_List;
      --  This procedure is called in renames cases to make sure that we do
      --  not have more than one identifier. If we do have more than one
      --  then an error message is issued (and the declaration is split into
      --  multiple declarations)

      function Token_Is_Renames return Boolean;
      --  Checks if current token is RENAMES, and if so, scans past it and
      --  returns True, otherwise returns False. Includes checking for some
      --  common error cases.

      -------------
      -- No_List --
      -------------

      procedure No_List is
      begin
         if Num_Idents > 1 then
            Error_Msg_N
              ("identifier list not allowed for RENAMES",
               Idents (2));
         end if;

         List_OK := False;
      end No_List;

      ----------------------
      -- Token_Is_Renames --
      ----------------------

      function Token_Is_Renames return Boolean is
         At_Colon : Saved_Scan_State;

      begin
         if Token = Tok_Colon then
            Save_Scan_State (At_Colon);
            Scan; -- past colon
            Check_Misspelling_Of (Tok_Renames);

            if Token = Tok_Renames then
               Error_Msg_SP -- CODEFIX
                 ("|extra "":"" ignored");
               Scan; -- past RENAMES
               return True;
            else
               Restore_Scan_State (At_Colon);
               return False;
            end if;

         else
            Check_Misspelling_Of (Tok_Renames);

            if Token = Tok_Renames then
               Scan; -- past RENAMES
               return True;
            else
               return False;
            end if;
         end if;
      end Token_Is_Renames;

   --  Start of processing for P_Identifier_Declarations

   begin
      Ident_Sloc := Token_Ptr;
      Save_Scan_State (Scan_State); -- at first identifier
      Idents (1) := P_Defining_Identifier (C_Comma_Colon);

      --  If we have a colon after the identifier, then we can assume that
      --  this is in fact a valid identifier declaration and can steam ahead.

      if Token = Tok_Colon then
         Scan; -- past colon

      --  If we have a comma, then scan out the list of identifiers

      elsif Token = Tok_Comma then
         while Comma_Present loop
            Num_Idents := Num_Idents + 1;
            Idents (Num_Idents) := P_Defining_Identifier (C_Comma_Colon);
         end loop;

         Save_Scan_State (Scan_State); -- at colon
         T_Colon;

      --  If we have identifier followed by := then we assume that what is
      --  really meant is an assignment statement. The assignment statement
      --  is scanned out and added to the list of declarations. An exception
      --  occurs if the := is followed by the keyword constant, in which case
      --  we assume it was meant to be a colon.

      elsif Token = Tok_Colon_Equal then
         Scan; -- past :=

         if Token = Tok_Constant then
            Error_Msg_SP ("colon expected");

         else
            Restore_Scan_State (Scan_State);

            --  Reset Token_Node, because it already got changed from an
            --  Identifier to a Defining_Identifier, and we don't want that
            --  for a statement!

            Token_Node :=
              Make_Identifier (Sloc (Token_Node), Chars (Token_Node));

            --  And now scan out one or more statements

            Statement_When_Declaration_Expected (Decls, Done, In_Spec);
            return;
         end if;

      --  If we have an IS keyword, then assume the TYPE keyword was missing

      elsif Token = Tok_Is then
         Restore_Scan_State (Scan_State);
         Append_To (Decls, P_Type_Declaration);
         Done := False;
         return;

      --  AI12-0275: Object renaming declaration without subtype_mark or
      --  access_definition

      elsif Token = Tok_Renames then
         Error_Msg_Ada_2022_Feature
           ("object renaming without subtype", Token_Ptr);

         Scan; -- past renames

         Decl_Node :=
           New_Node (N_Object_Renaming_Declaration, Ident_Sloc);
         Set_Name (Decl_Node, P_Name);
         Set_Defining_Identifier (Decl_Node, Idents (1));

         P_Aspect_Specifications (Decl_Node, Semicolon => False);

         T_Semicolon;

         Append (Decl_Node, Decls);
         Done := False;

         return;

      --  Otherwise we have an error situation

      else
         Restore_Scan_State (Scan_State);

         --  First case is possible misuse of PROTECTED in Ada 83 mode. If
         --  so, fix the keyword and return to scan the protected declaration.

         if Token_Name = Name_Protected then
            Check_95_Keyword (Tok_Protected, Tok_Identifier);
            Check_95_Keyword (Tok_Protected, Tok_Type);
            Check_95_Keyword (Tok_Protected, Tok_Body);

            if Token = Tok_Protected then
               Done := False;
               return;
            end if;

         --  Check misspelling possibilities. If so, correct the misspelling
         --  and return to scan out the resulting declaration.

         elsif Bad_Spelling_Of (Tok_Function)
           or else Bad_Spelling_Of (Tok_Procedure)
           or else Bad_Spelling_Of (Tok_Package)
           or else Bad_Spelling_Of (Tok_Pragma)
           or else Bad_Spelling_Of (Tok_Protected)
           or else Bad_Spelling_Of (Tok_Generic)
           or else Bad_Spelling_Of (Tok_Subtype)
           or else Bad_Spelling_Of (Tok_Type)
           or else Bad_Spelling_Of (Tok_Task)
           or else Bad_Spelling_Of (Tok_Use)
           or else Bad_Spelling_Of (Tok_For)
         then
            Done := False;
            return;

         --  Otherwise we definitely have an ordinary identifier with a junk
         --  token after it.

         else
            --  If in -gnatd.2 mode, try for statements

            if Debug_Flag_Dot_2 then
               Restore_Scan_State (Scan_State);

               --  Reset Token_Node, because it already got changed from an
               --  Identifier to a Defining_Identifier, and we don't want that
               --  for a statement!

               Token_Node :=
                 Make_Identifier (Sloc (Token_Node), Chars (Token_Node));

               --  And now scan out one or more statements

               Statement_When_Declaration_Expected (Decls, Done, In_Spec);
               return;

            --  Normal case, just complain and skip to semicolon

            else
               Set_Declaration_Expected;
               Resync_Past_Semicolon;
               Done := False;
               return;
            end if;
         end if;
      end if;

      --  Come here with an identifier list and colon scanned out. We now
      --  build the nodes for the declarative items. One node is built for
      --  each identifier in the list, with the type information being
      --  repeated by rescanning the appropriate section of source.

      --  First an error check, if we have two identifiers in a row, a likely
      --  possibility is that the first of the identifiers is an incorrectly
      --  spelled keyword.

      if Token = Tok_Identifier then
         declare
            SS : Saved_Scan_State;
            I2 : Boolean;

         begin
            Save_Scan_State (SS);
            Scan; -- past initial identifier
            I2 := (Token = Tok_Identifier);
            Restore_Scan_State (SS);

            if I2
              and then
                (Bad_Spelling_Of (Tok_Access)   or else
                 Bad_Spelling_Of (Tok_Aliased)  or else
                 Bad_Spelling_Of (Tok_Constant))
            then
               null;
            end if;
         end;
      end if;

      --  Loop through identifiers

      Ident := 1;
      Ident_Loop : loop

         --  Check for some cases of misused Ada 95 keywords

         if Token_Name = Name_Aliased then
            Check_95_Keyword (Tok_Aliased, Tok_Array);
            Check_95_Keyword (Tok_Aliased, Tok_Identifier);
            Check_95_Keyword (Tok_Aliased, Tok_Constant);
         end if;

         --  Constant cases

         if Token = Tok_Constant then
            Con_Loc := Token_Ptr;
            Scan; -- past CONSTANT

            --  Number declaration, initialization required

            Init_Expr := Init_Expr_Opt;

            if Present (Init_Expr) then
               if Not_Null_Present then
                  Error_Msg_SP
                    ("`NOT NULL` not allowed in numeric expression");
               end if;

               Decl_Node := New_Node (N_Number_Declaration, Ident_Sloc);
               Set_Expression (Decl_Node, Init_Expr);

            --  Constant object declaration

            else
               Decl_Node := New_Node (N_Object_Declaration, Ident_Sloc);
               Set_Constant_Present (Decl_Node, True);

               if Token_Name = Name_Aliased then
                  Check_95_Keyword (Tok_Aliased, Tok_Array);
                  Check_95_Keyword (Tok_Aliased, Tok_Identifier);
               end if;

               if Token = Tok_Aliased then
                  Error_Msg_SC -- CODEFIX
                    ("ALIASED should be before CONSTANT");
                  Scan; -- past ALIASED
                  Set_Aliased_Present (Decl_Node, True);
               end if;

               if Token = Tok_Array then
                  Set_Object_Definition
                    (Decl_Node, P_Array_Type_Definition);

               else
                  Not_Null_Present := P_Null_Exclusion; --  Ada 2005 (AI-231)
                  Set_Null_Exclusion_Present (Decl_Node, Not_Null_Present);

                  if Token = Tok_Access then
                     Error_Msg_Ada_2005_Extension
                       ("generalized use of anonymous access types");

                     Set_Object_Definition
                       (Decl_Node, P_Access_Definition (Not_Null_Present));
                  else
                     Set_Object_Definition
                       (Decl_Node, P_Subtype_Indication (Not_Null_Present));
                  end if;
               end if;

               if Token = Tok_Renames then
                  Error_Msg
                    ("CONSTANT not permitted in renaming declaration",
                     Con_Loc);
                  Scan; -- Past renames
                  Discard_Junk_Node (P_Name);
               end if;
            end if;

         --  Exception cases

         elsif Token = Tok_Exception then
            Scan; -- past EXCEPTION

            if Token_Is_Renames then
               No_List;
               Decl_Node :=
                 New_Node (N_Exception_Renaming_Declaration, Ident_Sloc);
               Set_Name (Decl_Node, P_Qualified_Simple_Name_Resync);
               No_Constraint;
            else
               Decl_Node := New_Node (N_Exception_Declaration, Prev_Token_Ptr);
            end if;

         --  Aliased case (note that an object definition is required)

         elsif Token = Tok_Aliased then
            Scan; -- past ALIASED
            Decl_Node := New_Node (N_Object_Declaration, Ident_Sloc);
            Set_Aliased_Present (Decl_Node, True);

            if Token = Tok_Constant then
               Scan; -- past CONSTANT
               Set_Constant_Present (Decl_Node, True);
            end if;

            if Token = Tok_Array then
               Set_Object_Definition
                 (Decl_Node, P_Array_Type_Definition);

            else
               Not_Null_Present := P_Null_Exclusion; --  Ada 2005 (AI-231)
               Set_Null_Exclusion_Present (Decl_Node, Not_Null_Present);

               --  Access definition (AI-406) or subtype indication

               if Token = Tok_Access then
                  Error_Msg_Ada_2005_Extension
                    ("generalized use of anonymous access types");

                  Set_Object_Definition
                    (Decl_Node, P_Access_Definition (Not_Null_Present));
               else
                  Set_Object_Definition
                    (Decl_Node, P_Subtype_Indication (Not_Null_Present));
               end if;
            end if;

         --  Array case

         elsif Token = Tok_Array then
            Decl_Node := New_Node (N_Object_Declaration, Ident_Sloc);
            Set_Object_Definition (Decl_Node, P_Array_Type_Definition);

         --  Ada 2005 (AI-254, AI-406)

         elsif Token = Tok_Not then

            --  OBJECT_DECLARATION ::=
            --    DEFINING_IDENTIFIER_LIST : [aliased] [constant]
            --      [NULL_EXCLUSION] SUBTYPE_INDICATION [:= EXPRESSION]
            --        [ASPECT_SPECIFICATIONS];
            --  | DEFINING_IDENTIFIER_LIST : [aliased] [constant]
            --      ACCESS_DEFINITION [:= EXPRESSION]
            --        [ASPECT_SPECIFICATIONS];

            --  OBJECT_RENAMING_DECLARATION ::=
            --    DEFINING_IDENTIFIER :
            --      [NULL_EXCLUSION] SUBTYPE_MARK renames object_NAME
            --        [ASPECT_SPECIFICATIONS];
            --  | DEFINING_IDENTIFIER :
            --      ACCESS_DEFINITION renames object_NAME
            --        [ASPECT_SPECIFICATIONS];

            Not_Null_Present := P_Null_Exclusion;  --  Ada 2005 (AI-231/423)

            if Token = Tok_Access then
               Error_Msg_Ada_2005_Extension
                 ("generalized use of anonymous access types");

               Acc_Node := P_Access_Definition (Not_Null_Present);

               if Token /= Tok_Renames then
                  Decl_Node := New_Node (N_Object_Declaration, Ident_Sloc);
                  Set_Object_Definition (Decl_Node, Acc_Node);

               else
                  Scan; --  past renames
                  No_List;
                  Decl_Node :=
                    New_Node (N_Object_Renaming_Declaration, Ident_Sloc);
                  Set_Access_Definition (Decl_Node, Acc_Node);
                  Set_Name (Decl_Node, P_Name);
               end if;

            else
               Type_Node := P_Subtype_Mark;

               --  Object renaming declaration

               if Token_Is_Renames then
                  if Ada_Version < Ada_2005 then
                     Error_Msg_SP
                       ("`NOT NULL` not allowed in object renaming");
                     raise Error_Resync;

                  --  Ada 2005 (AI-423): Object renaming declaration with
                  --  a null exclusion.

                  else
                     No_List;
                     Decl_Node :=
                       New_Node (N_Object_Renaming_Declaration, Ident_Sloc);
                     Set_Null_Exclusion_Present (Decl_Node, Not_Null_Present);
                     Set_Subtype_Mark (Decl_Node, Type_Node);
                     Set_Name (Decl_Node, P_Name);
                  end if;

               --  Object declaration

               else
                  Decl_Node := New_Node (N_Object_Declaration, Ident_Sloc);
                  Set_Null_Exclusion_Present (Decl_Node, Not_Null_Present);
                  Set_Object_Definition
                    (Decl_Node,
                     P_Subtype_Indication (Type_Node, Not_Null_Present));

                  --  RENAMES at this point means that we had the combination
                  --  of a constraint on the Type_Node and renames, which is
                  --  illegal

                  if Token_Is_Renames then
                     Error_Msg_N
                       ("constraint not allowed in object renaming "
                        & "declaration",
                        Constraint (Object_Definition (Decl_Node)));
                     raise Error_Resync;
                  end if;
               end if;
            end if;

         --  Ada 2005 (AI-230): Access Definition case

         elsif Token = Tok_Access then
            Error_Msg_Ada_2005_Extension
              ("generalized use of anonymous access types");

            Acc_Node := P_Access_Definition (Null_Exclusion_Present => False);

            --  Object declaration with access definition, or renaming

            if Token /= Tok_Renames then
               Decl_Node := New_Node (N_Object_Declaration, Ident_Sloc);
               Set_Object_Definition (Decl_Node, Acc_Node);

            else
               Scan; --  past renames
               No_List;
               Decl_Node :=
                 New_Node (N_Object_Renaming_Declaration, Ident_Sloc);
               Set_Access_Definition (Decl_Node, Acc_Node);
               Set_Name (Decl_Node, P_Name);
            end if;

         --  Subtype indication case

         else
            Type_Node := P_Subtype_Mark;

            --  Object renaming declaration

            if Token_Is_Renames then
               No_List;
               Decl_Node :=
                 New_Node (N_Object_Renaming_Declaration, Ident_Sloc);
               Set_Subtype_Mark (Decl_Node, Type_Node);
               Set_Name (Decl_Node, P_Name);

            --  Object declaration

            else
               Decl_Node := New_Node (N_Object_Declaration, Ident_Sloc);
               Set_Null_Exclusion_Present (Decl_Node, Not_Null_Present);
               Set_Object_Definition
                 (Decl_Node,
                  P_Subtype_Indication (Type_Node, Not_Null_Present));

               --  RENAMES at this point means that we had the combination of
               --  a constraint on the Type_Node and renames, which is illegal

               if Token_Is_Renames then
                  Error_Msg_N
                    ("constraint not allowed in object renaming declaration",
                     Constraint (Object_Definition (Decl_Node)));
                  raise Error_Resync;
               end if;
            end if;
         end if;

         --  Scan out initialization, allowed only for object declaration

         Init_Loc := Token_Ptr;
         Init_Expr := Init_Expr_Opt;

         if Present (Init_Expr) then
            if Nkind (Decl_Node) = N_Object_Declaration then
               Set_Expression (Decl_Node, Init_Expr);
               Set_Has_Init_Expression (Decl_Node);
            else
               Error_Msg ("initialization not allowed here", Init_Loc);
            end if;
         end if;

         Set_Defining_Identifier (Decl_Node, Idents (Ident));
         P_Aspect_Specifications (Decl_Node, Semicolon => False);

         --  Allow initialization expression to follow aspects (note that in
         --  this case P_Aspect_Specifications already issued an error msg).

         if Token = Tok_Colon_Equal then
            if Is_Non_Empty_List (Aspect_Specifications (Decl_Node)) then
               Error_Msg
                 ("aspect specifications must come after initialization "
                  & "expression",
                  Sloc (First (Aspect_Specifications (Decl_Node))));

            else
               --  In any case, the assignment symbol doesn't belong.

               Error_Msg ("misplaced assignment symbol", Scan_Ptr);
            end if;

            Set_Expression (Decl_Node, Init_Expr_Opt);
            Set_Has_Init_Expression (Decl_Node);
         end if;

         --  Now scan out the semicolon, which we deferred above

         T_Semicolon;

         if List_OK then
            if Ident < Num_Idents then
               Set_More_Ids (Decl_Node, True);
            end if;

            if Ident > 1 then
               Set_Prev_Ids (Decl_Node, True);
            end if;
         end if;

         Append (Decl_Node, Decls);
         exit Ident_Loop when Ident = Num_Idents;
         Restore_Scan_State (Scan_State);
         T_Colon;
         Ident := Ident + 1;
      end loop Ident_Loop;

      Done := False;
   end P_Identifier_Declarations;

   -------------------------------
   -- 3.3.1  Object Declaration --
   -------------------------------

   --  OBJECT DECLARATION ::=
   --    DEFINING_IDENTIFIER_LIST : [aliased] [constant]
   --      SUBTYPE_INDICATION [:= EXPRESSION];
   --  | DEFINING_IDENTIFIER_LIST : [aliased] [constant]
   --      ARRAY_TYPE_DEFINITION [:= EXPRESSION];
   --  | SINGLE_TASK_DECLARATION
   --  | SINGLE_PROTECTED_DECLARATION

   --  Cases starting with TASK are parsed by P_Task (9.1)
   --  Cases starting with PROTECTED are parsed by P_Protected (9.4)
   --  All other cases are parsed by P_Identifier_Declarations (3.3)

   -------------------------------------
   -- 3.3.1  Defining Identifier List --
   -------------------------------------

   --  DEFINING_IDENTIFIER_LIST ::=
   --    DEFINING_IDENTIFIER {, DEFINING_IDENTIFIER}

   --  Always parsed by the construct in which it appears. See special
   --  section on "Handling of Defining Identifier Lists" in this unit.

   -------------------------------
   -- 3.3.2  Number Declaration --
   -------------------------------

   --  Parsed by P_Identifier_Declarations (3.3)

   -------------------------------------------------------------------------
   -- 3.4  Derived Type Definition or Private Extension Declaration (7.3) --
   -------------------------------------------------------------------------

   --  DERIVED_TYPE_DEFINITION ::=
   --    [abstract] [limited] new [NULL_EXCLUSION] parent_SUBTYPE_INDICATION
   --    [[and INTERFACE_LIST] RECORD_EXTENSION_PART]

   --  PRIVATE_EXTENSION_DECLARATION ::=
   --     type DEFINING_IDENTIFIER [DISCRIMINANT_PART] is
   --       [abstract] [limited | synchronized]
   --          new ancestor_SUBTYPE_INDICATION [and INTERFACE_LIST]
   --            with private [ASPECT_SPECIFICATIONS];

   --  RECORD_EXTENSION_PART ::= with RECORD_DEFINITION

   --  The caller has already scanned out the part up to the NEW, and Token
   --  either contains Tok_New (or ought to, if it doesn't this procedure
   --  will post an appropriate "NEW expected" message).

   --  Note: the caller is responsible for filling in the Sloc field of
   --  the returned node in the private extension declaration case as
   --  well as the stuff relating to the discriminant part.

   --  Error recovery: can raise Error_Resync;

   function P_Derived_Type_Def_Or_Private_Ext_Decl return Node_Id is
      Typedef_Node     : Node_Id;
      Typedecl_Node    : Node_Id;
      Not_Null_Present : Boolean := False;

   begin
      Typedef_Node := New_Node (N_Derived_Type_Definition, Token_Ptr);

      if Ada_Version < Ada_2005
        and then Token = Tok_Identifier
        and then Token_Name = Name_Interface
      then
         Error_Msg_SP
           ("abstract interface is an Ada 2005 extension");
         Error_Msg_SP ("\unit must be compiled with -gnat05 switch");
      else
         T_New;
      end if;

      if Token = Tok_Abstract then
         Error_Msg_SC -- CODEFIX
           ("ABSTRACT must come before NEW, not after");
         Scan;
      end if;

      Not_Null_Present := P_Null_Exclusion; --  Ada 2005 (AI-231)
      Set_Null_Exclusion_Present (Typedef_Node, Not_Null_Present);
      Set_Subtype_Indication (Typedef_Node,
         P_Subtype_Indication (Not_Null_Present));

      --  Ada 2005 (AI-251): Deal with interfaces

      if Token = Tok_And then
         Scan; -- past AND

         Error_Msg_Ada_2005_Extension ("abstract interface");

         Set_Interface_List (Typedef_Node, New_List);

         loop
            Append (P_Qualified_Simple_Name, Interface_List (Typedef_Node));
            exit when Token /= Tok_And;
            Scan; -- past AND
         end loop;

         if Token /= Tok_With then
            Error_Msg_SC ("WITH expected");
            raise Error_Resync;
         end if;
      end if;

      --  Deal with record extension, note that we assume that a WITH is
      --  missing in the case of "type X is new Y record ..." or in the
      --  case of "type X is new Y null record".

      --  First make sure we don't have an aspect specification. If we do
      --  return now, so that our caller can check it (the WITH here is not
      --  part of a type extension).

      if Aspect_Specifications_Present then
         return Typedef_Node;

      --  OK, not an aspect specification, so continue test for extension

      elsif Token = Tok_With
        or else Token = Tok_Record
        or else Token = Tok_Null
      then
         T_With; -- past WITH or give error message

         if Token = Tok_Limited then
            Error_Msg_SC ("LIMITED keyword not allowed in private extension");
            Scan; -- ignore LIMITED
         end if;

         --  Private extension declaration

         if Token = Tok_Private then
            Scan; -- past PRIVATE

            --  Throw away the type definition node and build the type
            --  declaration node. Note the caller must set the Sloc,
            --  Discriminant_Specifications, Unknown_Discriminants_Present,
            --  and Defined_Identifier fields in the returned node.

            Typedecl_Node :=
              Make_Private_Extension_Declaration (No_Location,
                Defining_Identifier => Empty,
                Subtype_Indication  => Subtype_Indication (Typedef_Node),
                Abstract_Present    => Abstract_Present (Typedef_Node),
                Interface_List      => Interface_List (Typedef_Node));

            return Typedecl_Node;

         --  Derived type definition with record extension part

         else
            Set_Record_Extension_Part (Typedef_Node, P_Record_Definition);
            return Typedef_Node;
         end if;

      --  Derived type definition with no record extension part

      else
         return Typedef_Node;
      end if;
   end P_Derived_Type_Def_Or_Private_Ext_Decl;

   ---------------------------
   -- 3.5  Range Constraint --
   ---------------------------

   --  RANGE_CONSTRAINT ::= range RANGE

   --  The caller has checked that the initial token is RANGE or some
   --  misspelling of it, or it may be absent completely (and a message
   --  has already been issued).

   --  Error recovery: cannot raise Error_Resync

   function P_Range_Constraint return Node_Id is
      Range_Node : Node_Id;

   begin
      Range_Node := New_Node (N_Range_Constraint, Token_Ptr);

      --  Skip range keyword if present

      if Token = Tok_Range or else Bad_Spelling_Of (Tok_Range) then
         Scan; -- past RANGE
      end if;

      Set_Range_Expression (Range_Node, P_Range);
      return Range_Node;
   end P_Range_Constraint;

   ----------------
   -- 3.5  Range --
   ----------------

   --  RANGE ::=
   --    RANGE_ATTRIBUTE_REFERENCE | SIMPLE_EXPRESSION .. SIMPLE_EXPRESSION

   --  Note: the range that appears in a membership test is parsed by
   --  P_Range_Or_Subtype_Mark (3.5).

   --  Error recovery: cannot raise Error_Resync

   function P_Range return Node_Id is
      Expr_Node  : Node_Id;
      Range_Node : Node_Id;

   begin
      Expr_Node := P_Simple_Expression_Or_Range_Attribute;

      if Expr_Form = EF_Range_Attr then
         return Expr_Node;

      elsif Token = Tok_Dot_Dot then
         Range_Node := New_Node (N_Range, Token_Ptr);
         Set_Low_Bound (Range_Node, Expr_Node);
         Scan; -- past ..
         Expr_Node := P_Expression;
         Check_Simple_Expression (Expr_Node);
         Set_High_Bound (Range_Node, Expr_Node);
         return Range_Node;

      --  Anything else is an error

      else
         T_Dot_Dot; -- force missing .. message
         return Error;
      end if;
   end P_Range;

   ----------------------------------
   -- 3.5  P_Range_Or_Subtype_Mark --
   ----------------------------------

   --  RANGE ::=
   --    RANGE_ATTRIBUTE_REFERENCE
   --  | SIMPLE_EXPRESSION .. SIMPLE_EXPRESSION

   --  This routine scans out the range or subtype mark that forms the right
   --  operand of a membership test (it is not used in any other contexts, and
   --  error messages are specialized with this knowledge in mind).

   --  Note: as documented in the Sinfo interface, although the syntax only
   --  allows a subtype mark, we in fact allow any simple expression to be
   --  returned from this routine. The semantics is responsible for issuing
   --  an appropriate message complaining if the argument is not a name.
   --  This simplifies the coding and error recovery processing in the
   --  parser, and in any case it is preferable not to consider this a
   --  syntax error and to continue with the semantic analysis.

   --  Error recovery: cannot raise Error_Resync

   function P_Range_Or_Subtype_Mark
     (Allow_Simple_Expression : Boolean := False) return Node_Id
   is
      Expr_Node  : Node_Id;
      Range_Node : Node_Id;
      Save_Loc   : Source_Ptr;

   --  Start of processing for P_Range_Or_Subtype_Mark

   begin
      --  Save location of possible junk parentheses

      Save_Loc := Token_Ptr;

      --  Scan out either a simple expression or a range (this accepts more
      --  than is legal here, but as explained above, we like to allow more
      --  with a proper diagnostic, and in the case of a membership operation
      --  where sets are allowed, a simple expression is permissible anyway.

      Expr_Node := P_Simple_Expression_Or_Range_Attribute;

      --  Range attribute

      if Expr_Form = EF_Range_Attr then
         return Expr_Node;

      --  Simple_Expression .. Simple_Expression

      elsif Token = Tok_Dot_Dot then
         Check_Simple_Expression (Expr_Node);
         Range_Node := New_Node (N_Range, Token_Ptr);
         Set_Low_Bound (Range_Node, Expr_Node);
         Scan; -- past ..
         Set_High_Bound (Range_Node, P_Simple_Expression);
         return Range_Node;

      --  Case of subtype mark (optionally qualified simple name or an
      --  attribute whose prefix is an optionally qualified simple name)

      elsif Expr_Form = EF_Simple_Name
        or else Nkind (Expr_Node) = N_Attribute_Reference
      then
         --  Check for error of range constraint after a subtype mark

         if Token = Tok_Range then
            Error_Msg_SC ("range constraint not allowed in membership test");
            Scan; -- past RANGE
            raise Error_Resync;

         --  Check for error of DIGITS or DELTA after a subtype mark

         elsif Token = Tok_Digits or else Token = Tok_Delta then
            Error_Msg_SC
              ("accuracy definition not allowed in membership test");
            Scan; -- past DIGITS or DELTA
            raise Error_Resync;

         --  Attribute reference, may or may not be OK, but in any case we
         --  will scan it out

         elsif Token = Tok_Apostrophe then
            return P_Subtype_Mark_Attribute (Expr_Node);

         --  OK case of simple name, just return it

         else
            return Expr_Node;
         end if;

      --  Simple expression case

      elsif Expr_Form = EF_Simple and then Allow_Simple_Expression then
         return Expr_Node;

      --  Here we have some kind of error situation. Check for junk parens
      --  then return what we have, caller will deal with other errors.

      else
         if Nkind (Expr_Node) in N_Subexpr
           and then Paren_Count (Expr_Node) /= 0
         then
            Error_Msg ("|parentheses not allowed for subtype mark", Save_Loc);
            Set_Paren_Count (Expr_Node, 0);
         end if;

         return Expr_Node;
      end if;
   end P_Range_Or_Subtype_Mark;

   ----------------------------------------
   -- 3.5.1  Enumeration Type Definition --
   ----------------------------------------

   --  ENUMERATION_TYPE_DEFINITION ::=
   --    (ENUMERATION_LITERAL_SPECIFICATION
   --      {, ENUMERATION_LITERAL_SPECIFICATION})

   --  The caller has already scanned out the TYPE keyword

   --  Error recovery: can raise Error_Resync;

   function P_Enumeration_Type_Definition return Node_Id is
      Typedef_Node : Node_Id;

   begin
      Typedef_Node := New_Node (N_Enumeration_Type_Definition, Token_Ptr);
      Set_Literals (Typedef_Node, New_List);

      T_Left_Paren;

      loop
         Append (P_Enumeration_Literal_Specification, Literals (Typedef_Node));
         exit when not Comma_Present;
      end loop;

      T_Right_Paren;
      return Typedef_Node;
   end P_Enumeration_Type_Definition;

   ----------------------------------------------
   -- 3.5.1  Enumeration Literal Specification --
   ----------------------------------------------

   --  ENUMERATION_LITERAL_SPECIFICATION ::=
   --    DEFINING_IDENTIFIER | DEFINING_CHARACTER_LITERAL

   --  Error recovery: can raise Error_Resync

   function P_Enumeration_Literal_Specification return Node_Id is
   begin
      if Token = Tok_Char_Literal then
         return P_Defining_Character_Literal;
      else
         return P_Defining_Identifier (C_Comma_Right_Paren);
      end if;
   end P_Enumeration_Literal_Specification;

   ---------------------------------------
   -- 3.5.1  Defining_Character_Literal --
   ---------------------------------------

   --  DEFINING_CHARACTER_LITERAL ::= CHARACTER_LITERAL

   --  Error recovery: cannot raise Error_Resync

   --  The caller has checked that the current token is a character literal

   function P_Defining_Character_Literal return Node_Id is
      Literal_Node : Node_Id;
   begin
      Literal_Node := Token_Node;
      Change_Character_Literal_To_Defining_Character_Literal (Literal_Node);
      Scan; -- past character literal
      return Literal_Node;
   end P_Defining_Character_Literal;

   ------------------------------------
   -- 3.5.4  Integer Type Definition --
   ------------------------------------

   --  Parsed by P_Type_Declaration (3.2.1)

   -------------------------------------------
   -- 3.5.4  Signed Integer Type Definition --
   -------------------------------------------

   --  SIGNED_INTEGER_TYPE_DEFINITION ::=
   --    range static_SIMPLE_EXPRESSION .. static_SIMPLE_EXPRESSION

   --  Normally the initial token on entry is RANGE, but in some
   --  error conditions, the range token was missing and control is
   --  passed with Token pointing to first token of the first expression.

   --  Error recovery: cannot raise Error_Resync

   function P_Signed_Integer_Type_Definition return Node_Id is
      Typedef_Node : Node_Id;
      Expr_Node    : Node_Id;

   begin
      Typedef_Node := New_Node (N_Signed_Integer_Type_Definition, Token_Ptr);

      if Token = Tok_Range then
         Scan; -- past RANGE
      end if;

      Expr_Node := P_Expression_Or_Range_Attribute;

      --  Range case (not permitted by the grammar, this is surprising but
      --  the grammar in the RM is as quoted above, and does not allow Range).

      if Expr_Form = EF_Range_Attr then
         Error_Msg_N
           ("Range attribute not allowed here, use First .. Last", Expr_Node);
         Set_Low_Bound (Typedef_Node, Expr_Node);
         Set_Attribute_Name (Expr_Node, Name_First);
         Set_High_Bound (Typedef_Node, Copy_Separate_Tree (Expr_Node));
         Set_Attribute_Name (High_Bound (Typedef_Node), Name_Last);

      --  Normal case of explicit range

      else
         Check_Simple_Expression (Expr_Node);
         Set_Low_Bound (Typedef_Node, Expr_Node);
         T_Dot_Dot;
         Expr_Node := P_Expression;
         Check_Simple_Expression (Expr_Node);
         Set_High_Bound (Typedef_Node, Expr_Node);
      end if;

      return Typedef_Node;
   end P_Signed_Integer_Type_Definition;

   ------------------------------------
   -- 3.5.4  Modular Type Definition --
   ------------------------------------

   --  MODULAR_TYPE_DEFINITION ::= mod static_EXPRESSION

   --  The caller has checked that the initial token is MOD

   --  Error recovery: cannot raise Error_Resync

   function P_Modular_Type_Definition return Node_Id is
      Typedef_Node : Node_Id;

   begin
      if Ada_Version = Ada_83 then
         Error_Msg_SC ("(Ada 83) modular types not allowed");
      end if;

      Typedef_Node := New_Node (N_Modular_Type_Definition, Token_Ptr);
      Scan; -- past MOD
      Set_Expression (Typedef_Node, P_Expression_No_Right_Paren);

      --  Handle mod L..R cleanly

      if Token = Tok_Dot_Dot then
         Error_Msg_SC ("range not allowed for modular type");
         Scan; -- past ..
         Set_Expression (Typedef_Node, P_Expression_No_Right_Paren);
      end if;

      return Typedef_Node;
   end P_Modular_Type_Definition;

   ---------------------------------
   -- 3.5.6  Real Type Definition --
   ---------------------------------

   --  Parsed by P_Type_Declaration (3.2.1)

   --------------------------------------
   -- 3.5.7  Floating Point Definition --
   --------------------------------------

   --  FLOATING_POINT_DEFINITION ::=
   --    digits static_EXPRESSION [REAL_RANGE_SPECIFICATION]

   --  Note: In Ada-83, the EXPRESSION must be a SIMPLE_EXPRESSION

   --  The caller has checked that the initial token is DIGITS

   --  Error recovery: cannot raise Error_Resync

   function P_Floating_Point_Definition return Node_Id is
      Digits_Loc : constant Source_Ptr := Token_Ptr;
      Def_Node   : Node_Id;
      Expr_Node  : Node_Id;

   begin
      Scan; -- past DIGITS
      Expr_Node := P_Expression_No_Right_Paren;
      Check_Simple_Expression_In_Ada_83 (Expr_Node);

      --  Handle decimal fixed-point defn with DIGITS/DELTA in wrong order

      if Token = Tok_Delta then
         Error_Msg_SC -- CODEFIX
           ("|DELTA must come before DIGITS");
         Def_Node := New_Node (N_Decimal_Fixed_Point_Definition, Digits_Loc);
         Scan; -- past DELTA
         Set_Delta_Expression (Def_Node, P_Expression_No_Right_Paren);

      --  OK floating-point definition

      else
         Def_Node := New_Node (N_Floating_Point_Definition, Digits_Loc);
      end if;

      Set_Digits_Expression (Def_Node, Expr_Node);
      Set_Real_Range_Specification (Def_Node, P_Real_Range_Specification_Opt);
      return Def_Node;
   end P_Floating_Point_Definition;

   -------------------------------------
   -- 3.5.7  Real Range Specification --
   -------------------------------------

   --  REAL_RANGE_SPECIFICATION ::=
   --    range static_SIMPLE_EXPRESSION .. static_SIMPLE_EXPRESSION

   --  Error recovery: cannot raise Error_Resync

   function P_Real_Range_Specification_Opt return Node_Id is
      Specification_Node : Node_Id;
      Expr_Node          : Node_Id;

   begin
      if Token = Tok_Range then
         Specification_Node :=
           New_Node (N_Real_Range_Specification, Token_Ptr);
         Scan; -- past RANGE
         Expr_Node := P_Expression_No_Right_Paren;
         Check_Simple_Expression (Expr_Node);
         Set_Low_Bound (Specification_Node, Expr_Node);
         T_Dot_Dot;
         Expr_Node := P_Expression_No_Right_Paren;
         Check_Simple_Expression (Expr_Node);
         Set_High_Bound (Specification_Node, Expr_Node);
         return Specification_Node;
      else
         return Empty;
      end if;
   end P_Real_Range_Specification_Opt;

   -----------------------------------
   -- 3.5.9  Fixed Point Definition --
   -----------------------------------

   --  FIXED_POINT_DEFINITION ::=
   --    ORDINARY_FIXED_POINT_DEFINITION | DECIMAL_FIXED_POINT_DEFINITION

   --  ORDINARY_FIXED_POINT_DEFINITION ::=
   --    delta static_EXPRESSION REAL_RANGE_SPECIFICATION

   --  DECIMAL_FIXED_POINT_DEFINITION ::=
   --    delta static_EXPRESSION
   --      digits static_EXPRESSION [REAL_RANGE_SPECIFICATION]

   --  The caller has checked that the initial token is DELTA

   --  Error recovery: cannot raise Error_Resync

   function P_Fixed_Point_Definition return Node_Id is
      Delta_Node : Node_Id;
      Delta_Loc  : Source_Ptr;
      Def_Node   : Node_Id;
      Expr_Node  : Node_Id;

   begin
      Delta_Loc := Token_Ptr;
      Scan; -- past DELTA
      Delta_Node := P_Expression_No_Right_Paren;
      Check_Simple_Expression_In_Ada_83 (Delta_Node);

      if Token = Tok_Digits then
         if Ada_Version = Ada_83 then
            Error_Msg_SC ("(Ada 83) decimal fixed type not allowed!");
         end if;

         Def_Node := New_Node (N_Decimal_Fixed_Point_Definition, Delta_Loc);
         Scan; -- past DIGITS
         Expr_Node := P_Expression_No_Right_Paren;
         Check_Simple_Expression_In_Ada_83 (Expr_Node);
         Set_Digits_Expression (Def_Node, Expr_Node);

      else
         Def_Node := New_Node (N_Ordinary_Fixed_Point_Definition, Delta_Loc);

         --  Range is required in ordinary fixed point case

         if Token /= Tok_Range then
            Error_Msg_AP ("range must be given for fixed-point type");
            T_Range;
         end if;
      end if;

      Set_Delta_Expression (Def_Node, Delta_Node);
      Set_Real_Range_Specification (Def_Node, P_Real_Range_Specification_Opt);
      return Def_Node;
   end P_Fixed_Point_Definition;

   --------------------------------------------
   -- 3.5.9  Ordinary Fixed Point Definition --
   --------------------------------------------

   --  Parsed by P_Fixed_Point_Definition (3.5.9)

   -------------------------------------------
   -- 3.5.9  Decimal Fixed Point Definition --
   -------------------------------------------

   --  Parsed by P_Decimal_Point_Definition (3.5.9)

   ------------------------------
   -- 3.5.9  Digits Constraint --
   ------------------------------

   --  DIGITS_CONSTRAINT ::=
   --    digits static_EXPRESSION [RANGE_CONSTRAINT]

   --  Note: in Ada 83, the EXPRESSION must be a SIMPLE_EXPRESSION

   --  The caller has checked that the initial token is DIGITS

   function P_Digits_Constraint return Node_Id is
      Constraint_Node : Node_Id;
      Expr_Node : Node_Id;

   begin
      Constraint_Node := New_Node (N_Digits_Constraint, Token_Ptr);
      Scan; -- past DIGITS
      Expr_Node := P_Expression;
      Check_Simple_Expression_In_Ada_83 (Expr_Node);
      Set_Digits_Expression (Constraint_Node, Expr_Node);

      if Token = Tok_Range then
         Set_Range_Constraint (Constraint_Node, P_Range_Constraint);
      end if;

      return Constraint_Node;
   end P_Digits_Constraint;

   -----------------------------
   -- 3.5.9  Delta Constraint --
   -----------------------------

   --  DELTA CONSTRAINT ::= DELTA STATIC_EXPRESSION [RANGE_CONSTRAINT]

   --  Note: this is an obsolescent feature in Ada 95 (I.3)

   --  Note: in Ada 83, the EXPRESSION must be a SIMPLE_EXPRESSION
   --  (also true in formal modes).

   --  The caller has checked that the initial token is DELTA

   --  Error recovery: cannot raise Error_Resync

   function P_Delta_Constraint return Node_Id is
      Constraint_Node : Node_Id;
      Expr_Node : Node_Id;

   begin
      Constraint_Node := New_Node (N_Delta_Constraint, Token_Ptr);
      Scan; -- past DELTA
      Expr_Node := P_Expression;
      Check_Simple_Expression_In_Ada_83 (Expr_Node);

      Set_Delta_Expression (Constraint_Node, Expr_Node);

      if Token = Tok_Range then
         Set_Range_Constraint (Constraint_Node, P_Range_Constraint);
      end if;

      return Constraint_Node;
   end P_Delta_Constraint;

   --------------------------------
   -- 3.6  Array Type Definition --
   --------------------------------

   --  ARRAY_TYPE_DEFINITION ::=
   --    UNCONSTRAINED_ARRAY_DEFINITION | CONSTRAINED_ARRAY_DEFINITION

   --  UNCONSTRAINED_ARRAY_DEFINITION ::=
   --    array (INDEX_SUBTYPE_DEFINITION {, INDEX_SUBTYPE_DEFINITION}) of
   --      COMPONENT_DEFINITION

   --  INDEX_SUBTYPE_DEFINITION ::= SUBTYPE_MARK range <>

   --  CONSTRAINED_ARRAY_DEFINITION ::=
   --    array (DISCRETE_SUBTYPE_DEFINITION {, DISCRETE_SUBTYPE_DEFINITION}) of
   --      COMPONENT_DEFINITION

   --  DISCRETE_SUBTYPE_DEFINITION ::=
   --    DISCRETE_SUBTYPE_INDICATION | RANGE

   --  COMPONENT_DEFINITION ::=
   --    [aliased] [NULL_EXCLUSION] SUBTYPE_INDICATION | ACCESS_DEFINITION

   --  The caller has checked that the initial token is ARRAY

   --  Error recovery: can raise Error_Resync

   function P_Array_Type_Definition return Node_Id is
      Array_Loc        : Source_Ptr;
      CompDef_Node     : Node_Id;
      Def_Node         : Node_Id;
      Not_Null_Present : Boolean := False;
      Subs_List        : List_Id;
      Scan_State       : Saved_Scan_State;
      Aliased_Present  : Boolean := False;

      procedure P_Index_Subtype_Def_With_Fixed_Lower_Bound
        (Subtype_Mark : Node_Id);
      --  Parse an unconstrained index range with a fixed lower bound:
      --    subtype_mark range <expression> .. <>
      --  This procedure creates a subtype_indication node for the index.

      --------------------------------------------
      --  P_Index_Range_With_Fixed_Lower_Bound  --
      --------------------------------------------

      procedure P_Index_Subtype_Def_With_Fixed_Lower_Bound
        (Subtype_Mark : Node_Id)
      is
         Low_Expr_Node  : constant Node_Id := P_Expression;
         High_Expr_Node : Node_Id;
         Indic_Node     : Node_Id;
         Constr_Node    : Node_Id;
         Range_Node     : Node_Id;

      begin
         T_Dot_Dot;  -- Error if no ..

         --  A box is required at this point, and we'll set the upper bound to
         --  the same expression as the lower bound (see further below), to
         --  avoid problems with trying to analyze an Empty node. Analysis can
         --  still tell that this is a fixed-lower-bound range because the
         --  index is represented by a subtype_indication in an unconstrained
         --  array type definition.

         if Token = Tok_Box then
            Scan;
            High_Expr_Node := Low_Expr_Node;

         --  Error if no <> was found, and try to parse an expression since
         --  it's likely one was given in place of the <>.

         else
            Error_Msg_AP -- CODEFIX
              ("missing ""'<'>""");

            High_Expr_Node := P_Expression;
         end if;

         Constr_Node := New_Node (N_Range_Constraint, Token_Ptr);
         Range_Node  := New_Node (N_Range, Token_Ptr);
         Set_Range_Expression (Constr_Node, Range_Node);

         Check_Simple_Expression (Low_Expr_Node);

         Set_Low_Bound (Range_Node, Low_Expr_Node);
         Set_High_Bound (Range_Node, High_Expr_Node);

         Indic_Node :=
           New_Node (N_Subtype_Indication, Sloc (Subtype_Mark));
         Set_Subtype_Mark (Indic_Node, Check_Subtype_Mark (Subtype_Mark));
         Set_Constraint (Indic_Node, Constr_Node);

         Append (Indic_Node, Subs_List);
      end P_Index_Subtype_Def_With_Fixed_Lower_Bound;

      --  Local variables

      Is_Constrained_Array_Def : Boolean := True;
      Subtype_Mark_Node        : Node_Id;

   --  Start of processing for P_Array_Type_Definition

   begin
      Array_Loc := Token_Ptr;
      Scan; -- past ARRAY
      Subs_List := New_List;
      T_Left_Paren;

      --  It's quite tricky to disentangle these two possibilities, so we do
      --  a prescan to determine which case we have and then reset the scan.
      --  The prescan skips past possible subtype mark tokens.

      Save_Scan_State (Scan_State); -- just after paren

      while Token in Token_Class_Desig or else
            Token = Tok_Dot or else
            Token = Tok_Apostrophe -- because of 'BASE, 'CLASS
      loop
         Scan;
      end loop;

      --  If we end up on RANGE <> then we have the unconstrained case. We
      --  will also allow the RANGE to be omitted, just to improve error
      --  handling for a case like array (integer <>) of integer;

      Scan; -- past possible RANGE or <>

      if (Prev_Token = Tok_Range and then Token = Tok_Box) or else
         Prev_Token = Tok_Box
      then
         Def_Node := New_Node (N_Unconstrained_Array_Definition, Array_Loc);
         Restore_Scan_State (Scan_State); -- to first subtype mark

         Is_Constrained_Array_Def := False;

         --  Now parse a sequence of indexes where each is either of form:
         --    <subtype_mark> range <>
         --  or
         --    <subtype_mark> range <expr> .. <>
         --
         --  The latter syntax indicates an index with a fixed lower bound,
         --  and only applies when extensions are enabled (-gnatX).

         loop
            Subtype_Mark_Node := P_Subtype_Mark_Resync;

            T_Range;

            --  Normal "subtype_mark range <>" form, so simply append
            --  the subtype reference.

            if Token = Tok_Box then
               Append (Subtype_Mark_Node, Subs_List);
               Scan;

            --  Fixed-lower-bound form ("subtype_mark range <expr> .. <>")

            else
               P_Index_Subtype_Def_With_Fixed_Lower_Bound (Subtype_Mark_Node);

               if not Extensions_Allowed then
                  Error_Msg_N
                    ("fixed-lower-bound array is an extension feature; "
                       & "use -gnatX",
                     Token_Node);
               end if;
            end if;

            exit when Token = Tok_Right_Paren or else Token = Tok_Of;
            T_Comma;
         end loop;

         Set_Subtype_Marks (Def_Node, Subs_List);

      --  If we don't have "range <>", then "range" will be followed by an
      --  expression, for either a normal range or a fixed-lower-bound range
      --  ("<exp> .. <>"), and we have to know which, in order to determine
      --  whether to parse the indexes for an unconstrained or constrained
      --  array definition. So we look ahead to see if "<>" follows the "..".
      --  If not, then this must be a discrete_subtype_indication for a
      --  constrained_array_definition, which will be processed further below.

      elsif Prev_Token = Tok_Range
        and then Token /= Tok_Right_Paren and then Token /= Tok_Comma
      then
         --  If we have an expression followed by "..", then scan farther
         --  and check for "<>" to see if we have a fixed-lower-bound range.

         if P_Expression_Or_Range_Attribute /= Error
           and then Expr_Form /= EF_Range_Attr
           and then Token = Tok_Dot_Dot
         then
            Scan;

            --  If there's a "<>", then we know we have a fixed-lower-bound
            --  index, so we can proceed with parsing an unconstrained array
            --  definition.

            if Token = Tok_Box then
               Is_Constrained_Array_Def := False;

               Def_Node :=
                 New_Node (N_Unconstrained_Array_Definition, Array_Loc);

               Restore_Scan_State (Scan_State); -- to first subtype mark

               --  Now parse a sequence of indexes where each is either of
               --  form:
               --     <subtype_mark> range <>
               --  or
               --     <subtype_mark> range <expr> .. <>
               --
               --  The latter indicates an index with a fixed lower bound,
               --  and only applies when extensions are enabled (-gnatX).

               loop
                  Subtype_Mark_Node := P_Subtype_Mark_Resync;

                  T_Range;

                  --  Normal "subtype_mark range <>" form, so simply append
                  --  the subtype reference.

                  if Token = Tok_Box then
                     Append (Subtype_Mark_Node, Subs_List);
                     Scan;

                  --  This must be an index of form:
                  --    <subtype_mark> range <expr> .. <>"

                  else
                     P_Index_Subtype_Def_With_Fixed_Lower_Bound
                       (Subtype_Mark_Node);

                     if not Extensions_Allowed then
                        Error_Msg_N
                          ("fixed-lower-bound array is an extension feature; "
                             & "use -gnatX",
                           Token_Node);
                     end if;
                  end if;

                  exit when Token = Tok_Right_Paren or else Token = Tok_Of;
                  T_Comma;
               end loop;

               Set_Subtype_Marks (Def_Node, Subs_List);
            end if;
         end if;
      end if;

      if Is_Constrained_Array_Def then
         Def_Node := New_Node (N_Constrained_Array_Definition, Array_Loc);
         Restore_Scan_State (Scan_State); -- to first discrete range

         loop
            Append (P_Discrete_Subtype_Definition, Subs_List);
            exit when not Comma_Present;
         end loop;

         Set_Discrete_Subtype_Definitions (Def_Node, Subs_List);
      end if;

      T_Right_Paren;
      T_Of;

      CompDef_Node := New_Node (N_Component_Definition, Token_Ptr);

      if Token_Name = Name_Aliased then
         Check_95_Keyword (Tok_Aliased, Tok_Identifier);
      end if;

      if Token = Tok_Aliased then
         Aliased_Present := True;
         Scan; -- past ALIASED
      end if;

      Not_Null_Present := P_Null_Exclusion; --  Ada 2005 (AI-231/AI-254)

      --  Ada 2005 (AI-230): Access Definition case

      if Token = Tok_Access then
         Error_Msg_Ada_2005_Extension
           ("generalized use of anonymous access types");

         --  AI95-406 makes "aliased" legal (and useless) in this context so
         --  followintg code which used to be needed is commented out.

         --  if Aliased_Present then
         --     Error_Msg_SP ("ALIASED not allowed here");
         --  end if;

         Set_Subtype_Indication     (CompDef_Node, Empty);
         Set_Aliased_Present        (CompDef_Node, Aliased_Present);
         Set_Access_Definition      (CompDef_Node,
           P_Access_Definition (Not_Null_Present));
      else

         Set_Access_Definition      (CompDef_Node, Empty);
         Set_Aliased_Present        (CompDef_Node, Aliased_Present);
         Set_Null_Exclusion_Present (CompDef_Node, Not_Null_Present);
         Set_Subtype_Indication     (CompDef_Node,
           P_Subtype_Indication (Not_Null_Present));
      end if;

      Set_Component_Definition (Def_Node, CompDef_Node);

      return Def_Node;
   end P_Array_Type_Definition;

   -----------------------------------------
   -- 3.6  Unconstrained Array Definition --
   -----------------------------------------

   --  Parsed by P_Array_Type_Definition (3.6)

   ---------------------------------------
   -- 3.6  Constrained Array Definition --
   ---------------------------------------

   --  Parsed by P_Array_Type_Definition (3.6)

   --------------------------------------
   -- 3.6  Discrete Subtype Definition --
   --------------------------------------

   --  DISCRETE_SUBTYPE_DEFINITION ::=
   --    discrete_SUBTYPE_INDICATION | RANGE

   --  Note: the discrete subtype definition appearing in a constrained
   --  array definition is parsed by P_Array_Type_Definition (3.6)

   --  Error recovery: cannot raise Error_Resync

   function P_Discrete_Subtype_Definition return Node_Id is
   begin
      --  The syntax of a discrete subtype definition is identical to that
      --  of a discrete range, so we simply share the same parsing code.

      return P_Discrete_Range;
   end P_Discrete_Subtype_Definition;

   -------------------------------
   -- 3.6  Component Definition --
   -------------------------------

   --  For the array case, parsed by P_Array_Type_Definition (3.6)
   --  For the record case, parsed by P_Component_Declaration (3.8)

   -----------------------------
   -- 3.6.1  Index Constraint --
   -----------------------------

   --  Parsed by P_Index_Or_Discriminant_Constraint (3.7.1)

   ---------------------------
   -- 3.6.1  Discrete Range --
   ---------------------------

   --  DISCRETE_RANGE ::= discrete_SUBTYPE_INDICATION | RANGE

   --  The possible forms for a discrete range are:

      --   Subtype_Mark                           (SUBTYPE_INDICATION, 3.2.2)
      --   Subtype_Mark range Range               (SUBTYPE_INDICATION, 3.2.2)
      --   Range_Attribute                        (RANGE, 3.5)
      --   Simple_Expression .. Simple_Expression (RANGE, 3.5)

   --  Error recovery: cannot raise Error_Resync

   function P_Discrete_Range return Node_Id is
      Expr_Node  : Node_Id;
      Range_Node : Node_Id;

   begin
      Expr_Node := P_Simple_Expression_Or_Range_Attribute;

      if Expr_Form = EF_Range_Attr then
         return Expr_Node;

      elsif Token = Tok_Range then
         if Expr_Form /= EF_Simple_Name then
            Error_Msg_SC ("range must be preceded by subtype mark");
         end if;

         return P_Subtype_Indication (Expr_Node);

      --  Check Expression .. Expression case

      elsif Token = Tok_Dot_Dot then
         Range_Node := New_Node (N_Range, Token_Ptr);
         Set_Low_Bound (Range_Node, Expr_Node);
         Scan; -- past ..
         Expr_Node := P_Expression;
         Check_Simple_Expression (Expr_Node);
         Set_High_Bound (Range_Node, Expr_Node);
         return Range_Node;

      --  Otherwise we must have a subtype mark, or an Ada 2012 iterator

      elsif Expr_Form = EF_Simple_Name then
         return Expr_Node;

      --  The domain of iteration must be a name. Semantics will determine that
      --  the expression has the proper form.

      elsif Ada_Version >= Ada_2012 then
         return Expr_Node;

      --  If incorrect, complain that we expect ..

      else
         T_Dot_Dot;
         return Expr_Node;
      end if;
   end P_Discrete_Range;

   ----------------------------
   -- 3.7  Discriminant Part --
   ----------------------------

   --  DISCRIMINANT_PART ::=
   --    UNKNOWN_DISCRIMINANT_PART
   --  | KNOWN_DISCRIMINANT_PART

   --  A discriminant part is parsed by P_Known_Discriminant_Part_Opt (3.7)
   --  or P_Unknown_Discriminant_Part (3.7), since we know which we want.

   ------------------------------------
   -- 3.7  Unknown Discriminant Part --
   ------------------------------------

   --  UNKNOWN_DISCRIMINANT_PART ::= (<>)

   --  If no unknown discriminant part is present, then False is returned,
   --  otherwise the unknown discriminant is scanned out and True is returned.

   --  Error recovery: cannot raise Error_Resync

   function P_Unknown_Discriminant_Part_Opt return Boolean is
      Scan_State : Saved_Scan_State;

   begin
      --  If <> right now, then this is missing left paren

      if Token = Tok_Box then
         U_Left_Paren;

      --  If not <> or left paren, then definitely no box

      elsif Token /= Tok_Left_Paren then
         return False;

      --  Left paren, so might be a box after it

      else
         Save_Scan_State (Scan_State);
         Scan; -- past the left paren

         if Token /= Tok_Box then
            Restore_Scan_State (Scan_State);
            return False;
         end if;
      end if;

      --  We are now pointing to the box

      if Ada_Version = Ada_83 then
         Error_Msg_SC ("(Ada 83) unknown discriminant not allowed!");
      end if;

      Scan; -- past the box
      U_Right_Paren; -- must be followed by right paren
      return True;
   end P_Unknown_Discriminant_Part_Opt;

   ----------------------------------
   -- 3.7  Known Discriminant Part --
   ----------------------------------

   --  KNOWN_DISCRIMINANT_PART ::=
   --    (DISCRIMINANT_SPECIFICATION {; DISCRIMINANT_SPECIFICATION})

   --  DISCRIMINANT_SPECIFICATION ::=
   --    DEFINING_IDENTIFIER_LIST : [NULL_EXCLUSION] SUBTYPE_MARK
   --      [:= DEFAULT_EXPRESSION] [ASPECT_SPECIFICATION]
   --  | DEFINING_IDENTIFIER_LIST : ACCESS_DEFINITION
   --      [:= DEFAULT_EXPRESSION] [ASPECT_SPECIFICATION]

   --  If no known discriminant part is present, then No_List is returned

   --  Error recovery: cannot raise Error_Resync

   function P_Known_Discriminant_Part_Opt return List_Id is
      Specification_Node : Node_Id;
      Specification_List : List_Id;
      Ident_Sloc         : Source_Ptr;
      Scan_State         : Saved_Scan_State;
      Num_Idents         : Nat;
      Not_Null_Present   : Boolean;
      Ident              : Nat;

      Idents : array (Int range 1 .. 4096) of Entity_Id;
      --  This array holds the list of defining identifiers. The upper bound
      --  of 4096 is intended to be essentially infinite, and we do not even
      --  bother to check for it being exceeded.

   begin
      if Token = Tok_Left_Paren then
         Specification_List := New_List;
         Scan; -- past (
         P_Pragmas_Misplaced;

         Specification_Loop : loop

            Ident_Sloc := Token_Ptr;
            Idents (1) := P_Defining_Identifier (C_Comma_Colon);
            Num_Idents := 1;

            while Comma_Present loop
               Num_Idents := Num_Idents + 1;
               Idents (Num_Idents) := P_Defining_Identifier (C_Comma_Colon);
            end loop;

            --  If there are multiple identifiers, we repeatedly scan the
            --  type and initialization expression information by resetting
            --  the scan pointer (so that we get completely separate trees
            --  for each occurrence).

            if Num_Idents > 1 then
               Save_Scan_State (Scan_State);
            end if;

            T_Colon;

            --  Loop through defining identifiers in list

            Ident := 1;
            Ident_Loop : loop
               Specification_Node :=
                 New_Node (N_Discriminant_Specification, Ident_Sloc);
               Set_Defining_Identifier (Specification_Node, Idents (Ident));
               Not_Null_Present :=  --  Ada 2005 (AI-231, AI-447)
                 P_Null_Exclusion (Allow_Anonymous_In_95 => True);

               if Token = Tok_Access then
                  if Ada_Version = Ada_83 then
                     Error_Msg_SC
                       ("(Ada 83) access discriminant not allowed!");
                  end if;

                  Set_Discriminant_Type
                    (Specification_Node,
                     P_Access_Definition (Not_Null_Present));

               --  Catch ouf-of-order keywords

               elsif Token = Tok_Constant then
                  Scan;

                  if Token = Tok_Access then
                     Error_Msg_SC ("CONSTANT must appear after ACCESS");
                     Set_Discriminant_Type
                       (Specification_Node,
                        P_Access_Definition (Not_Null_Present));

                  else
                     Error_Msg_SC ("misplaced CONSTANT");
                  end if;

               else
                  Set_Discriminant_Type
                    (Specification_Node, P_Subtype_Mark);
                  No_Constraint;
                  Set_Null_Exclusion_Present  -- Ada 2005 (AI-231)
                    (Specification_Node, Not_Null_Present);
               end if;

               Set_Expression
                 (Specification_Node, Init_Expr_Opt (True));

               if Token = Tok_With then
                  P_Aspect_Specifications (Specification_Node, False);
               end if;

               if Ident > 1 then
                  Set_Prev_Ids (Specification_Node, True);
               end if;

               if Ident < Num_Idents then
                  Set_More_Ids (Specification_Node, True);
               end if;

               Append (Specification_Node, Specification_List);
               exit Ident_Loop when Ident = Num_Idents;
               Ident := Ident + 1;
               Restore_Scan_State (Scan_State);
               T_Colon;
            end loop Ident_Loop;

            exit Specification_Loop when Token /= Tok_Semicolon;
            Scan; -- past ;
            P_Pragmas_Misplaced;
         end loop Specification_Loop;

         T_Right_Paren;
         return Specification_List;

      else
         return No_List;
      end if;
   end P_Known_Discriminant_Part_Opt;

   -------------------------------------
   -- 3.7  Discriminant Specification --
   -------------------------------------

   --  Parsed by P_Known_Discriminant_Part_Opt (3.7)

   -----------------------------
   -- 3.7  Default Expression --
   -----------------------------

   --  Always parsed (simply as an Expression) by the parent construct

   ------------------------------------
   -- 3.7.1  Discriminant Constraint --
   ------------------------------------

   --  Parsed by P_Index_Or_Discriminant_Constraint (3.7.1)

   --------------------------------------------------------
   -- 3.7.1  Index or Discriminant Constraint (also 3.6) --
   --------------------------------------------------------

   --  DISCRIMINANT_CONSTRAINT ::=
   --    (DISCRIMINANT_ASSOCIATION {, DISCRIMINANT_ASSOCIATION})

   --  DISCRIMINANT_ASSOCIATION ::=
   --    [discriminant_SELECTOR_NAME {| discriminant_SELECTOR_NAME} =>]
   --      EXPRESSION

   --  This routine parses either an index or a discriminant constraint. As
   --  is clear from the above grammar, it is often possible to clearly
   --  determine which of the two possibilities we have, but there are
   --  cases (those in which we have a series of expressions of the same
   --  syntactic form as subtype indications), where we cannot tell. Since
   --  this means that in any case the semantic phase has to distinguish
   --  between the two, there is not much point in the parser trying to
   --  distinguish even those cases where the difference is clear. In any
   --  case, if we have a situation like:

   --     (A => 123, 235 .. 500)

   --  it is not clear which of the two items is the wrong one, better to
   --  let the semantic phase give a clear message. Consequently, this
   --  routine in general returns a list of items which can be either
   --  discrete ranges or discriminant associations.

   --  The caller has checked that the initial token is a left paren

   --  Error recovery: can raise Error_Resync

   function P_Index_Or_Discriminant_Constraint return Node_Id is
      Scan_State  : Saved_Scan_State;
      Constr_Node : Node_Id;
      Constr_List : List_Id;
      Expr_Node   : Node_Id;
      Result_Node : Node_Id;

   begin
      Result_Node := New_Node (N_Index_Or_Discriminant_Constraint, Token_Ptr);
      Scan; -- past (
      Constr_List := New_List;
      Set_Constraints (Result_Node, Constr_List);

      --  The two syntactic forms are a little mixed up, so what we are doing
      --  here is looking at the first entry to determine which case we have

      --  A discriminant constraint is a list of discriminant associations,
      --  which have one of the following possible forms:

      --    Expression
      --    Id => Expression
      --    Id | Id | .. | Id => Expression

      --  An index constraint is a list of discrete ranges which have one
      --  of the following possible forms:

      --    Subtype_Mark
      --    Subtype_Mark range Range
      --    Range_Attribute
      --    Simple_Expression .. Simple_Expression

      --  Loop through discriminants in list

      loop
         --  Check cases of Id => Expression or Id | Id => Expression

         if Token = Tok_Identifier then
            Save_Scan_State (Scan_State); -- at Id
            Scan; -- past Id

            if Token = Tok_Arrow or else Token = Tok_Vertical_Bar then
               Restore_Scan_State (Scan_State); -- to Id
               Append (P_Discriminant_Association, Constr_List);
               goto Loop_Continue;
            else
               Restore_Scan_State (Scan_State); -- to Id
            end if;
         end if;

         --  Otherwise scan out an expression and see what we have got

         Expr_Node := P_Expression_Or_Range_Attribute;

         if Expr_Form = EF_Range_Attr then
            Append (Expr_Node, Constr_List);

         elsif Token = Tok_Range then
            if Expr_Form /= EF_Simple_Name then
               Error_Msg_SC ("subtype mark required before RANGE");
            end if;

            Append (P_Subtype_Indication (Expr_Node), Constr_List);
            goto Loop_Continue;

         --  Check Simple_Expression .. Simple_Expression case

         elsif Token = Tok_Dot_Dot then
            Check_Simple_Expression (Expr_Node);
            Constr_Node := New_Node (N_Range, Token_Ptr);
            Set_Low_Bound (Constr_Node, Expr_Node);
            Scan; -- past ..

            --  If the upper bound is given by "<>", this is an index for
            --  a fixed-lower-bound subtype, so set the expression to Empty
            --  for now (it will be set to the ranges maximum upper bound
            --  later during analysis), and scan to the next token.

            if Token = Tok_Box then
               if not Extensions_Allowed then
                  Error_Msg_N
                    ("fixed-lower-bound array is an extension feature; "
                       & "use -gnatX",
                     Expr_Node);
               end if;

               Expr_Node := Empty;
               Scan;

            --  Otherwise parse the range's upper bound expression

            else
               Expr_Node := P_Expression;
               Check_Simple_Expression (Expr_Node);
            end if;

            Set_High_Bound (Constr_Node, Expr_Node);
            Append (Constr_Node, Constr_List);
            goto Loop_Continue;

         --  Case of an expression which could be either form

         else
            Append (Expr_Node, Constr_List);
            goto Loop_Continue;
         end if;

         --  Here with a single entry scanned

         <<Loop_Continue>>
            exit when not Comma_Present;

      end loop;

      T_Right_Paren;
      return Result_Node;
   end P_Index_Or_Discriminant_Constraint;

   -------------------------------------
   -- 3.7.1  Discriminant Association --
   -------------------------------------

   --  DISCRIMINANT_ASSOCIATION ::=
   --    [discriminant_SELECTOR_NAME {| discriminant_SELECTOR_NAME} =>]
   --      EXPRESSION

   --  This routine is used only when the name list is present and the caller
   --  has already checked this (by scanning ahead and repositioning the
   --  scan).

   --  Error_Recovery: cannot raise Error_Resync;

   function P_Discriminant_Association return Node_Id is
      Discr_Node : Node_Id;
      Names_List : List_Id;
      Ident_Sloc : Source_Ptr;

   begin
      Ident_Sloc := Token_Ptr;
      Names_List := New_List;

      loop
         Append (P_Identifier (C_Vertical_Bar_Arrow), Names_List);
         exit when Token /= Tok_Vertical_Bar;
         Scan; -- past |
      end loop;

      Discr_Node := New_Node (N_Discriminant_Association, Ident_Sloc);
      Set_Selector_Names (Discr_Node, Names_List);
      TF_Arrow;
      Set_Expression (Discr_Node, P_Expression);
      return Discr_Node;
   end P_Discriminant_Association;

   ---------------------------------
   -- 3.8  Record Type Definition --
   ---------------------------------

   --  RECORD_TYPE_DEFINITION ::=
   --    [[abstract] tagged] [limited] RECORD_DEFINITION

   --  There is no node in the tree for a record type definition. Instead
   --  a record definition node appears, with possible Abstract_Present,
   --  Tagged_Present, and Limited_Present flags set appropriately.

   ----------------------------
   -- 3.8  Record Definition --
   ----------------------------

   --  RECORD_DEFINITION ::=
   --    record
   --      COMPONENT_LIST
   --    end record
   --  | null record

   --  Note: in the case where a record definition node is used to represent
   --  a record type definition, the caller sets the Tagged_Present and
   --  Limited_Present flags in the resulting N_Record_Definition node as
   --  required.

   --  Note that the RECORD token at the start may be missing in certain
   --  error situations, so this function is expected to post the error

   --  Error recovery: can raise Error_Resync

   function P_Record_Definition return Node_Id is
      Rec_Node : Node_Id;

   begin
      Inside_Record_Definition := True;
      Rec_Node := New_Node (N_Record_Definition, Token_Ptr);

      --  Null record case

      if Token = Tok_Null then
         Scan; -- past NULL
         T_Record;
         Set_Null_Present (Rec_Node, True);

      --  Catch incomplete declaration to prevent cascaded errors, see
      --  ACATS B393002 for an example.

      elsif Token = Tok_Semicolon then
         Error_Msg_AP ("missing record definition");

      --  Case starting with RECORD keyword. Build scope stack entry. For the
      --  column, we use the first non-blank character on the line, to deal
      --  with situations such as:

      --    type X is record
      --      ...
      --    end record;

      --  which is not official RM indentation, but is not uncommon usage, and
      --  in particular is standard GNAT coding style, so handle it nicely.

      else
         Push_Scope_Stack;
         Scopes (Scope.Last).Etyp := E_Record;
         Scopes (Scope.Last).Ecol := Start_Column;
         Scopes (Scope.Last).Sloc := Token_Ptr;
         Scopes (Scope.Last).Labl := Error;
         Scopes (Scope.Last).Junk := (Token /= Tok_Record);

         T_Record;

         Set_Component_List (Rec_Node, P_Component_List);

         loop
            exit when Check_End;
            Discard_Junk_Node (P_Component_List);
         end loop;
      end if;

      Inside_Record_Definition := False;
      return Rec_Node;
   end P_Record_Definition;

   -------------------------
   -- 3.8  Component List --
   -------------------------

   --  COMPONENT_LIST ::=
   --    COMPONENT_ITEM {COMPONENT_ITEM}
   --  | {COMPONENT_ITEM} VARIANT_PART
   --  | null;

   --  Error recovery: cannot raise Error_Resync

   function P_Component_List return Node_Id is
      Component_List_Node : Node_Id;
      Decls_List          : List_Id;
      Scan_State          : Saved_Scan_State;
      Null_Loc            : Source_Ptr;

   begin
      Component_List_Node := New_Node (N_Component_List, Token_Ptr);
      Decls_List := New_List;

      --  Handle null

      if Token = Tok_Null then
         Null_Loc := Token_Ptr;
         Scan; -- past NULL
         TF_Semicolon;
         P_Pragmas_Opt (Decls_List);

         --  If we have an END or WHEN now, everything is fine, otherwise we
         --  complain about the null, ignore it, and scan for more components.

         if Token = Tok_End or else Token = Tok_When then
            Set_Null_Present (Component_List_Node, True);
            return Component_List_Node;
         else
            Error_Msg ("NULL component only allowed in null record", Null_Loc);
         end if;
      end if;

      --  Scan components for non-null record

      P_Pragmas_Opt (Decls_List);

      if Token /= Tok_Case then
         Component_Scan_Loop : loop
            P_Component_Items (Decls_List);
            P_Pragmas_Opt (Decls_List);

            exit Component_Scan_Loop when Token = Tok_End
              or else Token = Tok_Case
              or else Token = Tok_When;

            --  We are done if we do not have an identifier. However, if we
            --  have a misspelled reserved identifier that is in a column to
            --  the right of the record definition, we will treat it as an
            --  identifier. It turns out to be too dangerous in practice to
            --  accept such a mis-spelled identifier which does not have this
            --  additional clue that confirms the incorrect spelling.

            if Token /= Tok_Identifier then
               if Start_Column > Scopes (Scope.Last).Ecol
                 and then Is_Reserved_Identifier
               then
                  Save_Scan_State (Scan_State); -- at reserved id
                  Scan; -- possible reserved id

                  if Token = Tok_Comma or else Token = Tok_Colon then
                     Restore_Scan_State (Scan_State);
                     Scan_Reserved_Identifier (Force_Msg => True);

                     --  Note reserved identifier used as field name after all
                     --  because not followed by colon or comma.

                  else
                     Restore_Scan_State (Scan_State);
                     exit Component_Scan_Loop;
                  end if;

                  --  Non-identifier that definitely was not reserved id

               else
                  exit Component_Scan_Loop;
               end if;
            end if;
         end loop Component_Scan_Loop;
      end if;

      if Token = Tok_Case then
         Set_Variant_Part (Component_List_Node, P_Variant_Part);

         --  Check for junk after variant part

         if Token = Tok_Identifier then
            Save_Scan_State (Scan_State);
            Scan; -- past identifier

            if Token = Tok_Colon then
               Restore_Scan_State (Scan_State);
               Error_Msg_SC ("component may not follow variant part");
               Discard_Junk_Node (P_Component_List);

            elsif Token = Tok_Case then
               Restore_Scan_State (Scan_State);
               Error_Msg_SC ("only one variant part allowed in a record");
               Discard_Junk_Node (P_Component_List);

            else
               Restore_Scan_State (Scan_State);
            end if;
         end if;
      end if;

      Set_Component_Items (Component_List_Node, Decls_List);
      return Component_List_Node;
   end P_Component_List;

   -------------------------
   -- 3.8  Component Item --
   -------------------------

   --  COMPONENT_ITEM ::= COMPONENT_DECLARATION | REPRESENTATION_CLAUSE

   --  COMPONENT_DECLARATION ::=
   --    DEFINING_IDENTIFIER_LIST : COMPONENT_DEFINITION
   --      [:= DEFAULT_EXPRESSION]
   --        [ASPECT_SPECIFICATIONS];

   --  COMPONENT_DEFINITION ::=
   --    [aliased] [NULL_EXCLUSION] SUBTYPE_INDICATION | ACCESS_DEFINITION

   --  Error recovery: cannot raise Error_Resync, if an error occurs,
   --  the scan is positioned past the following semicolon.

   --  Note: we do not yet allow representation clauses to appear as component
   --  items, do we need to add this capability sometime in the future ???

   procedure P_Component_Items (Decls : List_Id) is
      Aliased_Present  : Boolean := False;
      CompDef_Node     : Node_Id;
      Decl_Node        : Node_Id := Empty;  -- initialize to prevent warning
      Scan_State       : Saved_Scan_State;
      Not_Null_Present : Boolean := False;
      Num_Idents       : Nat;
      Ident            : Nat;
      Ident_Sloc       : Source_Ptr;

      Idents : array (Int range 1 .. 4096) of Entity_Id;
      --  This array holds the list of defining identifiers. The upper bound
      --  of 4096 is intended to be essentially infinite, and we do not even
      --  bother to check for it being exceeded.

   begin
      if Token /= Tok_Identifier then
         Error_Msg_SC ("component declaration expected");
         Resync_Past_Semicolon;
         return;
      end if;

      Ident_Sloc := Token_Ptr;
      Check_Bad_Layout;
      Idents (1) := P_Defining_Identifier (C_Comma_Colon);
      Num_Idents := 1;

      while Comma_Present loop
         Num_Idents := Num_Idents + 1;
         Idents (Num_Idents) := P_Defining_Identifier (C_Comma_Colon);
      end loop;

      --  If there are multiple identifiers, we repeatedly scan the
      --  type and initialization expression information by resetting
      --  the scan pointer (so that we get completely separate trees
      --  for each occurrence).

      if Num_Idents > 1 then
         Save_Scan_State (Scan_State);
      end if;

      T_Colon;

      --  Loop through defining identifiers in list

      Ident := 1;
      Ident_Loop : loop

         --  The following block is present to catch Error_Resync
         --  which causes the parse to be reset past the semicolon

         begin
            Decl_Node := New_Node (N_Component_Declaration, Ident_Sloc);
            Set_Defining_Identifier (Decl_Node, Idents (Ident));

            if Token = Tok_Constant then
               Error_Msg_SC ("constant component not permitted");
               Scan;
            end if;

            CompDef_Node := New_Node (N_Component_Definition, Token_Ptr);

            if Token_Name = Name_Aliased then
               Check_95_Keyword (Tok_Aliased, Tok_Identifier);
            end if;

            if Token = Tok_Aliased then
               Aliased_Present := True;
               Scan; -- past ALIASED
            end if;

            Not_Null_Present := P_Null_Exclusion; -- Ada 2005 (AI-231/AI-254)

            --  Ada 2005 (AI-230): Access Definition case

            if Token = Tok_Access then
               Error_Msg_Ada_2005_Extension
                 ("generalized use of anonymous access types");

               --  AI95-406 makes "aliased" legal (and useless) here, so the
               --  following code which used to be required is commented out.

               --  if Aliased_Present then
               --     Error_Msg_SP ("ALIASED not allowed here");
               --  end if;

               Set_Subtype_Indication (CompDef_Node, Empty);
               Set_Aliased_Present    (CompDef_Node, False);
               Set_Access_Definition  (CompDef_Node,
                 P_Access_Definition (Not_Null_Present));
            else

               Set_Access_Definition      (CompDef_Node, Empty);
               Set_Aliased_Present        (CompDef_Node, Aliased_Present);
               Set_Null_Exclusion_Present (CompDef_Node, Not_Null_Present);

               if Token = Tok_Array then
                  Error_Msg_SC ("anonymous array not allowed as component");
                  raise Error_Resync;
               end if;

               Set_Subtype_Indication (CompDef_Node,
                 P_Subtype_Indication (Not_Null_Present));
            end if;

            Set_Component_Definition (Decl_Node, CompDef_Node);
            Set_Expression           (Decl_Node, Init_Expr_Opt);

            if Ident > 1 then
               Set_Prev_Ids (Decl_Node, True);
            end if;

            if Ident < Num_Idents then
               Set_More_Ids (Decl_Node, True);
            end if;

            Append (Decl_Node, Decls);

         exception
            when Error_Resync =>
               if Token /= Tok_End then
                  Resync_Past_Semicolon;
               end if;
         end;

         exit Ident_Loop when Ident = Num_Idents;
         Ident := Ident + 1;
         Restore_Scan_State (Scan_State);
         T_Colon;
      end loop Ident_Loop;

      P_Aspect_Specifications (Decl_Node);
   end P_Component_Items;

   --------------------------------
   -- 3.8  Component Declaration --
   --------------------------------

   --  Parsed by P_Component_Items (3.8)

   -------------------------
   -- 3.8.1  Variant Part --
   -------------------------

   --  VARIANT_PART ::=
   --    case discriminant_DIRECT_NAME is
   --      VARIANT
   --      {VARIANT}
   --    end case;

   --  The caller has checked that the initial token is CASE

   --  Error recovery: cannot raise Error_Resync

   function P_Variant_Part return Node_Id is
      Variant_Part_Node : Node_Id;
      Variants_List     : List_Id;
      Case_Node         : Node_Id;

   begin
      Variant_Part_Node := New_Node (N_Variant_Part, Token_Ptr);
      Push_Scope_Stack;
      Scopes (Scope.Last).Etyp := E_Case;
      Scopes (Scope.Last).Sloc := Token_Ptr;
      Scopes (Scope.Last).Ecol := Start_Column;

      Scan; -- past CASE
      Case_Node := P_Expression;
      Set_Name (Variant_Part_Node, Case_Node);

      if Nkind (Case_Node) /= N_Identifier then
         Set_Name (Variant_Part_Node, Error);
         Error_Msg ("discriminant name expected", Sloc (Case_Node));

      elsif Paren_Count (Case_Node) /= 0 then
         Error_Msg
           ("|discriminant name may not be parenthesized",
                    Sloc (Case_Node));
         Set_Paren_Count (Case_Node, 0);
      end if;

      TF_Is;
      Variants_List := New_List;
      P_Pragmas_Opt (Variants_List);

      --  Test missing variant

      if Token = Tok_End then
         Error_Msg_BC ("WHEN expected (must have at least one variant)");
      else
         Append (P_Variant, Variants_List);
      end if;

      --  Loop through variants, note that we allow if in place of when,
      --  this error will be detected and handled in P_Variant.

      loop
         P_Pragmas_Opt (Variants_List);

         if Token /= Tok_When
           and then Token /= Tok_If
           and then Token /= Tok_Others
         then
            exit when Check_End;
         end if;

         Append (P_Variant, Variants_List);
      end loop;

      Set_Variants (Variant_Part_Node, Variants_List);
      return Variant_Part_Node;
   end P_Variant_Part;

   --------------------
   -- 3.8.1  Variant --
   --------------------

   --  VARIANT ::=
   --    when DISCRETE_CHOICE_LIST =>
   --      COMPONENT_LIST

   --  Error recovery: cannot raise Error_Resync

   --  The initial token on entry is either WHEN, IF or OTHERS

   function P_Variant return Node_Id is
      Variant_Node : Node_Id;

   begin
      --  Special check to recover nicely from use of IF in place of WHEN

      if Token = Tok_If then
         T_When;
         Scan; -- past IF
      else
         T_When;
      end if;

      Variant_Node := New_Node (N_Variant, Prev_Token_Ptr);
      Set_Discrete_Choices (Variant_Node, P_Discrete_Choice_List);
      TF_Arrow;
      Set_Component_List (Variant_Node, P_Component_List);
      return Variant_Node;
   end P_Variant;

   ---------------------------------
   -- 3.8.1  Discrete Choice List --
   ---------------------------------

   --  DISCRETE_CHOICE_LIST ::= DISCRETE_CHOICE {| DISCRETE_CHOICE}

   --  DISCRETE_CHOICE ::= EXPRESSION | DISCRETE_RANGE | others

   --  Note: in Ada 83, the expression must be a simple expression

   --  Error recovery: cannot raise Error_Resync

   function P_Discrete_Choice_List return List_Id is
      Choices     : List_Id;
      Expr_Node   : Node_Id := Empty;  -- initialize to prevent warning
      Choice_Node : Node_Id;

   begin
      Choices := New_List;
      loop
         if Token = Tok_Others then
            Append (New_Node (N_Others_Choice, Token_Ptr), Choices);
            Scan; -- past OTHERS

         else
            begin
               --  Scan out expression or range attribute

               Expr_Node := P_Expression_Or_Range_Attribute;
               Ignore (Tok_Right_Paren);

               if Token = Tok_Colon
                 and then Nkind (Expr_Node) = N_Identifier
               then
                  Error_Msg_SP ("label not permitted in this context");
                  Scan; -- past colon

               --  Range attribute

               elsif Expr_Form = EF_Range_Attr then
                  Append (Expr_Node, Choices);

               --  Explicit range

               elsif Token = Tok_Dot_Dot then
                  Check_Simple_Expression (Expr_Node);
                  Choice_Node := New_Node (N_Range, Token_Ptr);
                  Set_Low_Bound (Choice_Node, Expr_Node);
                  Scan; -- past ..
                  Expr_Node := P_Expression_No_Right_Paren;
                  Check_Simple_Expression (Expr_Node);
                  Set_High_Bound (Choice_Node, Expr_Node);
                  Append (Choice_Node, Choices);

               --  Simple name, must be subtype, so range allowed

               elsif Expr_Form = EF_Simple_Name then
                  if Token = Tok_Range then
                     Append (P_Subtype_Indication (Expr_Node), Choices);

                  elsif Token in Token_Class_Consk then
                     Error_Msg_SC
                       ("the only constraint allowed here " &
                        "is a range constraint");
                     Discard_Junk_Node (P_Constraint_Opt);
                     Append (Expr_Node, Choices);

                  else
                     Append (Expr_Node, Choices);
                  end if;

               --  Expression

               else
                  --  In Ada 2012 mode, the expression must be a simple
                  --  expression. The reason for this restriction (i.e. going
                  --  back to the Ada 83 rule) is to avoid ambiguities when set
                  --  membership operations are allowed, consider the
                  --  following:

                  --     when A in 1 .. 10 | 12 =>

                  --  This is ambiguous without parentheses, so we require one
                  --  of the following two parenthesized forms to disambiguate:

                  --  one of the following:

                  --     when (A in 1 .. 10 | 12) =>
                  --     when (A in 1 .. 10) | 12 =>

                  --  To solve this, in Ada 2012 mode, we disallow the use of
                  --  membership operations in expressions in choices.

                  --  Technically in the grammar, the expression must match the
                  --  grammar for restricted expression.

                  if Ada_Version >= Ada_2012 then
                     Check_Restricted_Expression (Expr_Node);

                  --  In Ada 83 mode, the syntax required a simple expression

                  else
                     Check_Simple_Expression_In_Ada_83 (Expr_Node);
                  end if;

                  Append (Expr_Node, Choices);
               end if;

            exception
               when Error_Resync =>
                  Resync_Choice;
                  return Error_List;
            end;
         end if;

         if Token = Tok_Comma then
            if Nkind (Expr_Node) = N_Iterated_Component_Association then
               return Choices;
            end if;

            Scan; -- past comma

            if Token = Tok_Vertical_Bar then
               Error_Msg_SP -- CODEFIX
                 ("|extra "","" ignored");
               Scan; -- past |

            else
               Error_Msg_SP -- CODEFIX
                 (""","" should be ""'|""");
            end if;

         else
            exit when Token /= Tok_Vertical_Bar;
            Scan; -- past |
         end if;

      end loop;

      return Choices;
   end P_Discrete_Choice_List;

   ----------------------------
   -- 3.8.1  Discrete Choice --
   ----------------------------

   --  Parsed by P_Discrete_Choice_List (3.8.1)

   ----------------------------------
   -- 3.9.1  Record Extension Part --
   ----------------------------------

   --  RECORD_EXTENSION_PART ::= with RECORD_DEFINITION

   --  Parsed by P_Derived_Type_Def_Or_Private_Ext_Decl (3.4)

   --------------------------------------
   -- 3.9.4  Interface Type Definition --
   --------------------------------------

   --  INTERFACE_TYPE_DEFINITION ::=
   --    [limited | task | protected | synchronized] interface
   --      [and INTERFACE_LIST]

   --  Error recovery: cannot raise Error_Resync

   function P_Interface_Type_Definition
     (Abstract_Present : Boolean) return Node_Id
   is
      Typedef_Node : Node_Id;

   begin
      Error_Msg_Ada_2005_Extension ("abstract interface");

      if Abstract_Present then
         Error_Msg_SP
           ("ABSTRACT not allowed in interface type definition " &
            "(RM 3.9.4(2/2))");
      end if;

      Scan; -- past INTERFACE

      --  Ada 2005 (AI-345): In case of interfaces with a null list of
      --  interfaces we build a record_definition node.

      if Token = Tok_Semicolon or else Aspect_Specifications_Present then
         Typedef_Node := New_Node (N_Record_Definition, Token_Ptr);

         Set_Abstract_Present  (Typedef_Node);
         Set_Tagged_Present    (Typedef_Node);
         Set_Null_Present      (Typedef_Node);
         Set_Interface_Present (Typedef_Node);

      --  Ada 2005 (AI-251): In case of not-synchronized interfaces that have
      --  a list of interfaces we build a derived_type_definition node. This
      --  simplifies the semantic analysis (and hence further maintenance)

      else
         if Token /= Tok_And then
            Error_Msg_AP ("AND expected");
         else
            Scan; -- past AND
         end if;

         Typedef_Node := New_Node (N_Derived_Type_Definition, Token_Ptr);

         Set_Abstract_Present   (Typedef_Node);
         Set_Interface_Present  (Typedef_Node);
         Set_Subtype_Indication (Typedef_Node, P_Qualified_Simple_Name);

         Set_Record_Extension_Part (Typedef_Node,
           New_Node (N_Record_Definition, Token_Ptr));
         Set_Null_Present (Record_Extension_Part (Typedef_Node));

         if Token = Tok_And then
            Set_Interface_List (Typedef_Node, New_List);
            Scan; -- past AND

            loop
               Append (P_Qualified_Simple_Name,
                       Interface_List (Typedef_Node));
               exit when Token /= Tok_And;
               Scan; -- past AND
            end loop;
         end if;
      end if;

      return Typedef_Node;
   end P_Interface_Type_Definition;

   ----------------------------------
   -- 3.10  Access Type Definition --
   ----------------------------------

   --  ACCESS_TYPE_DEFINITION ::=
   --    ACCESS_TO_OBJECT_DEFINITION
   --  | ACCESS_TO_SUBPROGRAM_DEFINITION

   --  ACCESS_TO_OBJECT_DEFINITION ::=
   --    [NULL_EXCLUSION] access [GENERAL_ACCESS_MODIFIER] SUBTYPE_INDICATION

   --  GENERAL_ACCESS_MODIFIER ::= all | constant

   --  ACCESS_TO_SUBPROGRAM_DEFINITION
   --    [NULL_EXCLUSION] access [protected] procedure PARAMETER_PROFILE
   --  | [NULL_EXCLUSION] access [protected] function
   --    PARAMETER_AND_RESULT_PROFILE

   --  PARAMETER_PROFILE ::= [FORMAL_PART]

   --  PARAMETER_AND_RESULT_PROFILE ::= [FORMAL_PART] RETURN SUBTYPE_MARK

   --  Ada 2005 (AI-254): If Header_Already_Parsed then the caller has already
   --  parsed the null_exclusion part and has also removed the ACCESS token;
   --  otherwise the caller has just checked that the initial token is ACCESS

   --  Error recovery: can raise Error_Resync

   function P_Access_Type_Definition
     (Header_Already_Parsed : Boolean := False) return Node_Id
   is
      Access_Loc       : constant Source_Ptr := Token_Ptr;
      Prot_Flag        : Boolean;
      Not_Null_Present : Boolean := False;
      Not_Null_Subtype : Boolean := False;
      Type_Def_Node    : Node_Id;
      Result_Not_Null  : Boolean;
      Result_Node      : Node_Id;

      procedure Check_Junk_Subprogram_Name;
      --  Used in access to subprogram definition cases to check for an
      --  identifier or operator symbol that does not belong.

      --------------------------------
      -- Check_Junk_Subprogram_Name --
      --------------------------------

      procedure Check_Junk_Subprogram_Name is
         Saved_State : Saved_Scan_State;

      begin
         if Token = Tok_Identifier or else Token = Tok_Operator_Symbol then
            Save_Scan_State (Saved_State);
            Scan; -- past possible junk subprogram name

            if Token = Tok_Left_Paren or else Token = Tok_Semicolon then
               Error_Msg_SP ("unexpected subprogram name ignored");
               return;

            else
               Restore_Scan_State (Saved_State);
            end if;
         end if;
      end Check_Junk_Subprogram_Name;

   --  Start of processing for P_Access_Type_Definition

   begin
      if not Header_Already_Parsed then

         --  NOT NULL ACCESS .. is a common form of access definition.
         --  ACCESS NOT NULL ..  is certainly rare, but syntactically legal.
         --  NOT NULL ACCESS NOT NULL .. is rarer yet, and also legal.
         --  The last two cases are only meaningful if the following subtype
         --  indication denotes an access type (semantic check). The flag
         --  Not_Null_Subtype indicates that this second null exclusion is
         --  present in the access type definition.

         Not_Null_Present := P_Null_Exclusion;     --  Ada 2005 (AI-231)
         Scan; -- past ACCESS
         Not_Null_Subtype := P_Null_Exclusion;     --  Might also appear
      end if;

      if Token_Name = Name_Protected then
         Check_95_Keyword (Tok_Protected, Tok_Procedure);
         Check_95_Keyword (Tok_Protected, Tok_Function);
      end if;

      Prot_Flag := (Token = Tok_Protected);

      if Prot_Flag then
         Scan; -- past PROTECTED

         if Token /= Tok_Procedure and then Token /= Tok_Function then
            Error_Msg_SC -- CODEFIX
              ("FUNCTION or PROCEDURE expected");
         end if;
      end if;

      if Token = Tok_Procedure then
         if Ada_Version = Ada_83 then
            Error_Msg_SC ("(Ada 83) access to procedure not allowed!");
         end if;

         Type_Def_Node := New_Node (N_Access_Procedure_Definition, Access_Loc);
         Set_Null_Exclusion_Present (Type_Def_Node, Not_Null_Present);
         Scan; -- past PROCEDURE
         Check_Junk_Subprogram_Name;
         Set_Parameter_Specifications (Type_Def_Node, P_Parameter_Profile);
         Set_Protected_Present (Type_Def_Node, Prot_Flag);

      elsif Token = Tok_Function then
         if Ada_Version = Ada_83 then
            Error_Msg_SC ("(Ada 83) access to function not allowed!");
         end if;

         Type_Def_Node := New_Node (N_Access_Function_Definition, Access_Loc);
         Set_Null_Exclusion_Present (Type_Def_Node, Not_Null_Present);
         Scan; -- past FUNCTION
         Check_Junk_Subprogram_Name;
         Set_Parameter_Specifications (Type_Def_Node, P_Parameter_Profile);
         Set_Protected_Present (Type_Def_Node, Prot_Flag);
         TF_Return;

         Result_Not_Null := P_Null_Exclusion;     --  Ada 2005 (AI-231)

         --  Ada 2005 (AI-318-02)

         if Token = Tok_Access then
            Error_Msg_Ada_2005_Extension ("anonymous access result type");

            Result_Node := P_Access_Definition (Result_Not_Null);

         else
            Result_Node := P_Subtype_Mark;
            No_Constraint;

            --  A null exclusion on the result type must be recorded in a flag
            --  distinct from the one used for the access-to-subprogram type's
            --  null exclusion.

            Set_Null_Exclusion_In_Return_Present
              (Type_Def_Node, Result_Not_Null);
         end if;

         Set_Result_Definition (Type_Def_Node, Result_Node);

      else
         Type_Def_Node :=
           New_Node (N_Access_To_Object_Definition, Access_Loc);
         Set_Null_Exclusion_Present (Type_Def_Node, Not_Null_Present);
         Set_Null_Excluding_Subtype (Type_Def_Node, Not_Null_Subtype);

         if Token = Tok_All or else Token = Tok_Constant then
            if Ada_Version = Ada_83 then
               Error_Msg_SC ("(Ada 83) access modifier not allowed!");
            end if;

            if Token = Tok_All then
               Set_All_Present (Type_Def_Node, True);

            else
               Set_Constant_Present (Type_Def_Node, True);
            end if;

            Scan; -- past ALL or CONSTANT
         end if;

         Set_Subtype_Indication (Type_Def_Node,
            P_Subtype_Indication (Not_Null_Present));
      end if;

      return Type_Def_Node;
   end P_Access_Type_Definition;

   ---------------------------------------
   -- 3.10  Access To Object Definition --
   ---------------------------------------

   --  Parsed by P_Access_Type_Definition (3.10)

   -----------------------------------
   -- 3.10  General Access Modifier --
   -----------------------------------

   --  Parsed by P_Access_Type_Definition (3.10)

   -------------------------------------------
   -- 3.10  Access To Subprogram Definition --
   -------------------------------------------

   --  Parsed by P_Access_Type_Definition (3.10)

   -----------------------------
   -- 3.10  Access Definition --
   -----------------------------

   --  ACCESS_DEFINITION ::=
   --    [NULL_EXCLUSION] access [GENERAL_ACCESS_MODIFIER] SUBTYPE_MARK
   --  | ACCESS_TO_SUBPROGRAM_DEFINITION
   --
   --  ACCESS_TO_SUBPROGRAM_DEFINITION
   --    [NULL_EXCLUSION] access [protected] procedure PARAMETER_PROFILE
   --  | [NULL_EXCLUSION] access [protected] function
   --    PARAMETER_AND_RESULT_PROFILE

   --  The caller has parsed the null-exclusion part and it has also checked
   --  that the next token is ACCESS

   --  Error recovery: cannot raise Error_Resync

   function P_Access_Definition
     (Null_Exclusion_Present : Boolean) return Node_Id
   is
      Def_Node  : Node_Id;
      Subp_Node : Node_Id;

   begin
      Def_Node := New_Node (N_Access_Definition, Token_Ptr);
      Scan; -- past ACCESS

      --  Ada 2005 (AI-254): Access_To_Subprogram_Definition

      if Token = Tok_Protected
        or else Token = Tok_Procedure
        or else Token = Tok_Function
      then
         Error_Msg_Ada_2005_Extension ("access-to-subprogram");

         Subp_Node := P_Access_Type_Definition (Header_Already_Parsed => True);
         Set_Null_Exclusion_Present (Subp_Node, Null_Exclusion_Present);
         Set_Access_To_Subprogram_Definition (Def_Node, Subp_Node);

      --  Ada 2005 (AI-231)
      --  [NULL_EXCLUSION] access [GENERAL_ACCESS_MODIFIER] SUBTYPE_MARK

      else
         Set_Null_Exclusion_Present (Def_Node, Null_Exclusion_Present);

         if Token = Tok_All then
            if Ada_Version < Ada_2005 then
               Error_Msg_SP
                 ("ALL not permitted for anonymous access type");
            end if;

            Scan; -- past ALL
            Set_All_Present (Def_Node);

         elsif Token = Tok_Constant then
            Error_Msg_Ada_2005_Extension ("access-to-constant");

            Scan; -- past CONSTANT
            Set_Constant_Present (Def_Node);
         end if;

         Set_Subtype_Mark (Def_Node, P_Subtype_Mark);
         No_Constraint;
      end if;

      return Def_Node;
   end P_Access_Definition;

   -----------------------------------------
   -- 3.10.1  Incomplete Type Declaration --
   -----------------------------------------

   --  Parsed by P_Type_Declaration (3.2.1)

   ----------------------------
   -- 3.11  Declarative Part --
   ----------------------------

   --  DECLARATIVE_PART ::= {DECLARATIVE_ITEM}

   --  Error recovery: cannot raise Error_Resync (because P_Declarative_Items
   --  handles errors, and returns cleanly after an error has occurred)

   function P_Declarative_Part return List_Id is
      Decls : List_Id;
      Done  : Boolean;

   begin
      --  Indicate no bad declarations detected yet. This will be reset by
      --  P_Declarative_Items if a bad declaration is discovered.

      Missing_Begin_Msg := No_Error_Msg;

      --  Get rid of active SIS entry from outer scope. This means we will
      --  miss some nested cases, but it doesn't seem worth the effort. See
      --  discussion in Par for further details

      SIS_Entry_Active := False;
      Decls := New_List;

      --  Loop to scan out the declarations

      loop
         P_Declarative_Items
           (Decls, Done, Declare_Expression => False, In_Spec => False);
         exit when Done;
      end loop;

      --  Get rid of active SIS entry which is left set only if we scanned a
      --  procedure declaration and have not found the body. We could give
      --  an error message, but that really would be usurping the role of
      --  semantic analysis (this really is a missing body case).

      SIS_Entry_Active := False;
      return Decls;
   end P_Declarative_Part;

   ----------------------------
   -- 3.11  Declarative Item --
   ----------------------------

   --  DECLARATIVE_ITEM ::= BASIC_DECLARATIVE_ITEM | BODY

   --  Can return Error if a junk declaration is found, or Empty if no
   --  declaration is found (i.e. a token ending declarations, such as
   --  BEGIN or END is encountered).

   --  Error recovery: cannot raise Error_Resync. If an error resync occurs,
   --  then the scan is set past the next semicolon and Error is returned.

   procedure P_Declarative_Items
     (Decls              : List_Id;
      Done               : out Boolean;
      Declare_Expression : Boolean;
      In_Spec            : Boolean)
   is
      Scan_State : Saved_Scan_State;

   begin
      Done := False;

      --  In -gnatg mode, we don't want a "bad indentation" error inside a
      --  declare_expression.

      if Style_Check and not Declare_Expression then
         Style.Check_Indentation;
      end if;

      case Token is
         when Tok_Function
            | Tok_Not
            | Tok_Overriding
            | Tok_Procedure
         =>
            Check_Bad_Layout;
            Append (P_Subprogram (Pf_Decl_Gins_Pbod_Rnam_Stub_Pexp), Decls);

         when Tok_For =>
            Check_Bad_Layout;

            --  Check for loop (premature statement)

            Save_Scan_State (Scan_State);
            Scan; -- past FOR

            if Token = Tok_Identifier then
               Scan; -- past identifier

               if Token = Tok_In then
                  Restore_Scan_State (Scan_State);
                  Statement_When_Declaration_Expected (Decls, Done, In_Spec);
                  return;
               end if;
            end if;

            --  Not a loop, so must be rep clause

            Restore_Scan_State (Scan_State);
            Append (P_Representation_Clause, Decls);

         when Tok_Generic =>
            Check_Bad_Layout;
            Append (P_Generic, Decls);

         when Tok_Identifier =>
            Check_Bad_Layout;

            --  Special check for misuse of overriding not in Ada 2005 mode

            if Token_Name = Name_Overriding
              and then not Next_Token_Is (Tok_Colon)
            then
               Error_Msg_SC ("overriding indicator is an Ada 2005 extension");
               Error_Msg_SC ("\unit must be compiled with -gnat05 switch");

               Token := Tok_Overriding;
               Append (P_Subprogram (Pf_Decl_Gins_Pbod_Rnam_Stub_Pexp), Decls);

            --  Normal case, no overriding, or overriding followed by colon

            else
               P_Identifier_Declarations (Decls, Done, In_Spec);
            end if;

         when Tok_Package =>
            Check_Bad_Layout;
            Append (P_Package (Pf_Decl_Gins_Pbod_Rnam_Stub_Pexp), Decls);

         when Tok_Pragma =>
            Append (P_Pragma, Decls);

         when Tok_Protected =>
            Check_Bad_Layout;
            Scan; -- past PROTECTED
            Append (P_Protected, Decls);

         when Tok_Subtype =>
            Check_Bad_Layout;
            Append (P_Subtype_Declaration, Decls);

         when Tok_Task =>
            Check_Bad_Layout;
            Scan; -- past TASK
            Append (P_Task, Decls);

         when Tok_Type =>
            Check_Bad_Layout;
            Append (P_Type_Declaration, Decls);

         when Tok_Use =>
            Check_Bad_Layout;
            P_Use_Clause (Decls);

         when Tok_With =>
            Check_Bad_Layout;

            if Aspect_Specifications_Present then

               --  If we are after a semicolon, complain that it was ignored.
               --  But we don't really ignore it, since we dump the aspects,
               --  so we make the error message a normal fatal message which
               --  will inhibit semantic analysis anyway).

               if Prev_Token = Tok_Semicolon then
                  Error_Msg_SP -- CODEFIX
                    ("extra "";"" ignored");

               --  If not just past semicolon, just complain that aspects are
               --  not allowed at this point.

               else
                  Error_Msg_SC ("aspect specifications not allowed here");
               end if;

               --  Assume that this is a misplaced aspect specification within
               --  a declarative list. After discarding the misplaced aspects
               --  we can continue the scan.

               declare
                  Dummy_Node : constant Node_Id :=
                                 New_Node (N_Package_Specification, Token_Ptr);
                  pragma Warnings (Off, Dummy_Node);
                  --  Dummy node to attach aspect specifications to. We will
                  --  then throw them away.

               begin
                  P_Aspect_Specifications (Dummy_Node, Semicolon => True);
               end;

            --  Here if not aspect specifications case

            else
               Error_Msg_SC ("WITH can only appear in context clause");
               raise Error_Resync;
            end if;

         --  BEGIN terminates the scan of a sequence of declarations unless
         --  there is a missing subprogram body, see section on handling
         --  semicolon in place of IS. We only treat the begin as satisfying
         --  the subprogram declaration if it falls in the expected column
         --  or to its right.

         when Tok_Begin =>
            if SIS_Entry_Active and then Start_Column >= SIS_Ecol then

               --  Here we have the case where a BEGIN is encountered during
               --  declarations in a declarative part, or at the outer level,
               --  and there is a subprogram declaration outstanding for which
               --  no body has been supplied. This is the case where we assume
               --  that the semicolon in the subprogram declaration should
               --  really have been is. The active SIS entry describes the
               --  subprogram declaration. On return the declaration has been
               --  modified to become a body.

               declare
                  Specification_Node : Node_Id;
                  Decl_Node          : Node_Id;
                  Body_Node          : Node_Id;

               begin
                  --  First issue the error message. If we had a missing
                  --  semicolon in the declaration, then change the message
                  --  to <missing "is">

                  if SIS_Missing_Semicolon_Message /= No_Error_Msg then
                     Change_Error_Text     -- Replace: "missing "";"" "
                       (SIS_Missing_Semicolon_Message, "missing ""is""");

                  --  Otherwise we saved the semicolon position, so complain

                  else
                     Error_Msg -- CODEFIX
                       ("|"";"" should be IS", SIS_Semicolon_Sloc);
                  end if;

                  --  The next job is to fix up any declarations that occurred
                  --  between the procedure header and the BEGIN. These got
                  --  chained to the outer declarative region (immediately
                  --  after the procedure declaration) and they should be
                  --  chained to the subprogram itself, which is a body
                  --  rather than a spec.

                  Specification_Node := Specification (SIS_Declaration_Node);
                  Change_Node (SIS_Declaration_Node, N_Subprogram_Body);
                  Body_Node := SIS_Declaration_Node;
                  Set_Specification (Body_Node, Specification_Node);
                  Set_Declarations (Body_Node, New_List);

                  loop
                     Decl_Node := Remove_Next (Body_Node);
                     exit when Decl_Node = Empty;
                     Append (Decl_Node, Declarations (Body_Node));
                  end loop;

                  --  Now make the scope table entry for the Begin-End and
                  --  scan it out

                  Push_Scope_Stack;
                  Scopes (Scope.Last).Sloc := SIS_Sloc;
                  Scopes (Scope.Last).Etyp := E_Name;
                  Scopes (Scope.Last).Ecol := SIS_Ecol;
                  Scopes (Scope.Last).Labl := SIS_Labl;
                  Scopes (Scope.Last).Lreq := False;
                  SIS_Entry_Active := False;
                  Scan; -- past BEGIN
                  Set_Handled_Statement_Sequence (Body_Node,
                    P_Handled_Sequence_Of_Statements);
                  End_Statements (Handled_Statement_Sequence (Body_Node));
               end;

            else
               Done := True;
            end if;

         --  Normally an END terminates the scan for basic declarative items.
         --  The one exception is END RECORD, which is probably left over from
         --  some other junk.

         when Tok_End =>
            Save_Scan_State (Scan_State); -- at END
            Scan; -- past END

            if Token = Tok_Record then
               Error_Msg_SP ("no RECORD for this `end record`!");
               Scan; -- past RECORD
               TF_Semicolon;

               --  This might happen because of misplaced aspect specification.
               --  After discarding the misplaced aspects we can continue the
               --  scan.

            else
               Restore_Scan_State (Scan_State); -- to END
               Done := True;
            end if;

         --  The following tokens which can only be the start of a statement
         --  are considered to end a declarative part (i.e. we have a missing
         --  BEGIN situation). We are fairly conservative in making this
         --  judgment, because it is a real mess to go into statement mode
         --  prematurely in response to a junk declaration.

         when Tok_Abort
            | Tok_Accept
            | Tok_Declare
            | Tok_Delay
            | Tok_Exit
            | Tok_Goto
            | Tok_If
            | Tok_Loop
            | Tok_Null
            | Tok_Requeue
            | Tok_Select
            | Tok_While
         =>
            --  But before we decide that it's a statement, let's check for
            --  a reserved word misused as an identifier.

            if Is_Reserved_Identifier then
               Save_Scan_State (Scan_State);
               Scan; -- past the token

               --  If reserved identifier not followed by colon or comma, then
               --  this is most likely an assignment statement to the bad id.

               if Token /= Tok_Colon and then Token /= Tok_Comma then
                  Restore_Scan_State (Scan_State);
                  Statement_When_Declaration_Expected (Decls, Done, In_Spec);
                  return;

               --  Otherwise we have a declaration of the bad id

               else
                  Restore_Scan_State (Scan_State);
                  Scan_Reserved_Identifier (Force_Msg => True);
                  P_Identifier_Declarations (Decls, Done, In_Spec);
               end if;

            --  If not reserved identifier, then it's definitely a statement

            else
               Statement_When_Declaration_Expected (Decls, Done, In_Spec);
               return;
            end if;

         --  The token RETURN may well also signal a missing BEGIN situation,
         --  however, we never let it end the declarative part, because it may
         --  also be part of a half-baked function declaration.

         when Tok_Return =>
            Error_Msg_SC ("misplaced RETURN statement");
            raise Error_Resync;

         --  PRIVATE definitely terminates the declarations in a spec,
         --  and is an error in a body.

         when Tok_Private =>
            if In_Spec then
               Done := True;
            else
               Error_Msg_SC ("PRIVATE not allowed in body");
               Scan; -- past PRIVATE
            end if;

         --  An end of file definitely terminates the declarations

         when Tok_EOF =>
            Done := True;

         --  The remaining tokens do not end the scan, but cannot start a
         --  valid declaration, so we signal an error and resynchronize.
         --  But first check for misuse of a reserved identifier.

         when others =>

            --  Here we check for a reserved identifier

            if Is_Reserved_Identifier then
               Save_Scan_State (Scan_State);
               Scan; -- past the token

               if Token /= Tok_Colon and then Token /= Tok_Comma then
                  Restore_Scan_State (Scan_State);
                  Set_Declaration_Expected;
                  raise Error_Resync;
               else
                  Restore_Scan_State (Scan_State);
                  Scan_Reserved_Identifier (Force_Msg => True);
                  Check_Bad_Layout;
                  P_Identifier_Declarations (Decls, Done, In_Spec);
               end if;

            else
               Set_Declaration_Expected;
               raise Error_Resync;
            end if;
      end case;

   --  To resynchronize after an error, we scan to the next semicolon and
   --  return with Done = False, indicating that there may still be more
   --  valid declarations to come.

   exception
      when Error_Resync =>
         Resync_Past_Semicolon;
   end P_Declarative_Items;

   ----------------------------------
   -- 3.11  Basic Declarative Item --
   ----------------------------------

   --  BASIC_DECLARATIVE_ITEM ::=
   --    BASIC_DECLARATION | REPRESENTATION_CLAUSE | USE_CLAUSE

   --  Scan zero or more basic declarative items

   --  Error recovery: cannot raise Error_Resync. If an error is detected, then
   --  the scan pointer is repositioned past the next semicolon, and the scan
   --  for declarative items continues.

   function P_Basic_Declarative_Items
     (Declare_Expression : Boolean) return List_Id
   is
      Decl  : Node_Id;
      Decls : List_Id;
      Kind  : Node_Kind;
      Done  : Boolean;

   begin
      --  Indicate no bad declarations detected yet in the current context:
      --  visible or private declarations of a package spec.

      Missing_Begin_Msg := No_Error_Msg;

      --  Get rid of active SIS entry from outer scope. This means we will
      --  miss some nested cases, but it doesn't seem worth the effort. See
      --  discussion in Par for further details

      SIS_Entry_Active := False;

      --  Loop to scan out declarations

      Decls := New_List;

      loop
         P_Declarative_Items
           (Decls, Done, Declare_Expression, In_Spec => True);
         exit when Done;
      end loop;

      --  Get rid of active SIS entry. This is set only if we have scanned a
      --  procedure declaration and have not found the body. We could give
      --  an error message, but that really would be usurping the role of
      --  semantic analysis (this really is a case of a missing body).

      SIS_Entry_Active := False;

      --  Test for assorted illegal declarations not diagnosed elsewhere

      Decl := First (Decls);

      while Present (Decl) loop
         Kind := Nkind (Decl);

         --  Test for body scanned, not acceptable as basic decl item

         if Kind = N_Subprogram_Body or else
            Kind = N_Package_Body    or else
            Kind = N_Task_Body       or else
            Kind = N_Protected_Body
         then
            if Declare_Expression then
               Error_Msg
                 ("proper body not allowed in declare_expression",
                  Sloc (Decl));
            else
               Error_Msg
                 ("proper body not allowed in package spec",
                  Sloc (Decl));
            end if;

            --  Complete declaration of mangled subprogram body, for better
            --  recovery if analysis is attempted.

            if Nkind (Decl) in N_Subprogram_Body | N_Package_Body | N_Task_Body
              and then No (Handled_Statement_Sequence (Decl))
            then
               Set_Handled_Statement_Sequence (Decl,
                 Make_Handled_Sequence_Of_Statements (Sloc (Decl),
                   Statements => New_List));
            end if;

         --  Test for body stub scanned, not acceptable as basic decl item

         elsif Kind in N_Body_Stub then
            Error_Msg ("body stub not allowed in package spec", Sloc (Decl));

         elsif Kind = N_Assignment_Statement then
            Error_Msg
              ("assignment statement not allowed in package spec",
               Sloc (Decl));
         end if;

         Next (Decl);
      end loop;

      return Decls;
   end P_Basic_Declarative_Items;

   ----------------
   -- 3.11  Body --
   ----------------

   --  For proper body, see below
   --  For body stub, see 10.1.3

   -----------------------
   -- 3.11  Proper Body --
   -----------------------

   --  Subprogram body is parsed by P_Subprogram (6.1)
   --  Package body is parsed by P_Package (7.1)
   --  Task body is parsed by P_Task (9.1)
   --  Protected body is parsed by P_Protected (9.4)

   ------------------------------
   -- Set_Declaration_Expected --
   ------------------------------

   procedure Set_Declaration_Expected is
   begin
      Error_Msg_SC ("declaration expected");

      if Missing_Begin_Msg = No_Error_Msg then
         Missing_Begin_Msg := Get_Msg_Id;
      end if;
   end Set_Declaration_Expected;

   ----------------------
   -- Skip_Declaration --
   ----------------------

   procedure Skip_Declaration (S : List_Id) is
      Dummy_Done : Boolean;
      pragma Warnings (Off, Dummy_Done);
   begin
      P_Declarative_Items
        (S, Dummy_Done, Declare_Expression => False, In_Spec => False);
   end Skip_Declaration;

   -----------------------------------------
   -- Statement_When_Declaration_Expected --
   -----------------------------------------

   procedure Statement_When_Declaration_Expected
     (Decls   : List_Id;
      Done    : out Boolean;
      In_Spec : Boolean)
   is
   begin
      --  Case of second occurrence of statement in one declaration sequence

      if Missing_Begin_Msg /= No_Error_Msg then

         --  In the procedure spec case, just ignore it, we only give one
         --  message for the first occurrence, since otherwise we may get
         --  horrible cascading if BODY was missing in the header line.

         if In_Spec then
            null;

         --  Just ignore it if we are in -gnatd.2 (allow statements to appear
         --  in declaration sequences) mode.

         elsif Debug_Flag_Dot_2 then
            null;

         --  In the declarative part case, take a second statement as a sure
         --  sign that we really have a missing BEGIN, and end the declarative
         --  part now. Note that the caller will fix up the first message to
         --  say "missing BEGIN" so that's how the error will be signalled.

         else
            Done := True;
            return;
         end if;

      --  Case of first occurrence of unexpected statement

      else
         --  Do not give error message if we are operating in -gnatd.2 mode
         --  (alllow statements to appear in declarative parts).

         if not Debug_Flag_Dot_2 then

            --  If we are in a package spec, then give message of statement
            --  not allowed in package spec. This message never gets changed.

            if In_Spec then
               Error_Msg_SC ("statement not allowed in package spec");

            --  If in declarative part, then we give the message complaining
            --  about finding a statement when a declaration is expected. This
            --  gets changed to a complaint about a missing BEGIN if we later
            --  find that no BEGIN is present.

            else
               Error_Msg_SC ("statement not allowed in declarative part");
            end if;

            --  Capture message Id. This is used for two purposes, first to
            --  stop multiple messages, see test above, and second, to allow
            --  the replacement of the message in the declarative part case.

            Missing_Begin_Msg := Get_Msg_Id;
         end if;
      end if;

      --  In all cases except the case in which we decided to terminate the
      --  declaration sequence on a second error, we scan out the statement
      --  and append it to the list of declarations (note that the semantics
      --  can handle statements in a declaration list so if we proceed to
      --  call the semantic phase, all will be (reasonably) well.

      Append_List_To (Decls, P_Sequence_Of_Statements (SS_Unco));

      --  Done is set to False, since we want to continue the scan of
      --  declarations, hoping that this statement was a temporary glitch.
      --  If we indeed are now in the statement part (i.e. this was a missing
      --  BEGIN, then it's not terrible, we will simply keep calling this
      --  procedure to process the statements one by one, and then finally
      --  hit the missing BEGIN, which will clean up the error message.

      Done := False;
   end Statement_When_Declaration_Expected;

end Ch3;
