Commit 8133b9d1 by Ed Schonberg Committed by Arnaud Charlet

atree.ads, atree.adb (New_Copy_Tree): If hash table is being used and itype is visited...

2007-08-14  Ed Schonberg  <schonberg@adacore.com>
	    Robert Dewar  <dewar@adacore.com>

	* atree.ads, atree.adb (New_Copy_Tree): If hash table is being used and
	itype is visited, make an entry into table to link associated node and
	new itype.
	Add comments and correct harmless error in Build_NCT_Hash_Tables
	(Array_Aggr_Subtype): Associate each itype created for an index type to
	the corresponding range construct, and not to the aggregate itself. to
	maintain a one-to-one correspondence between itype and its associated
	node, to prevent errors when complex expression is copied.
	Fix mishandling of multiple levels of parens

	* sem_aggr.adb: Create a limited view of an incomplete type, to make
	treatment of limited views uniform for all visible declarations in a
	limited_withed package.
	(New_Copy_Tree): If hash table is being used and itype is visited,
	make an entry into table to link associated node and new itype.
	(Resolve_Record_Aggregate): Do not add an others box association for a
	discriminated record component that has only discriminants, when there
	is a box association for the component itself.

	* par-ch4.adb: Fix mishandling of multiple levels of parens

From-SVN: r127412
parent d766cee3
......@@ -94,12 +94,11 @@ package Atree is
-- Rewrite_Ins A flag set if a node is marked as a rewrite inserted
-- node as a result of a call to Mark_Rewrite_Insertion.
-- Paren_Count A 2-bit count used on expression nodes to indicate
-- the level of parentheses. Up to 3 levels can be
-- accomodated. Anything more than 3 levels is treated
-- as 3 levels (conformance tests that complain about
-- this are hereby deemed pathological!). Set to zero
-- for non-subexpression nodes.
-- Paren_Count A 2-bit count used in sub-expression nodes to indicate
-- the level of parentheses. The settings are 0,1,2 and
-- 3 for many. If the value is 3, then an auxiliary table
-- is used to indicate the real value. Set to zero for
-- non-subexpression nodes.
-- Comes_From_Source
-- This flag is present in all nodes. It is set if the
......@@ -203,10 +202,6 @@ package Atree is
-- Elist7-Elist28, Uint7-Uint28, Ureal7-Ureal28). Note that not all
-- these functions are defined, only the ones that are actually used.
type Paren_Count_Type is mod 4;
for Paren_Count_Type'Size use 2;
-- Type used for Paren_Count field
function Last_Node_Id return Node_Id;
pragma Inline (Last_Node_Id);
-- Returns Id of last allocated node Id
......@@ -548,7 +543,7 @@ package Atree is
-- The result returned by Traverse is Abandon if processing was terminated
-- by a call to Process returning Abandon, otherwise it is OK (meaning that
-- all calls to process returned either OK or Skip).
-- all calls to process returned either OK, OK_Orig, or Skip).
generic
with function Process (N : Node_Id) return Traverse_Result is <>;
......@@ -579,7 +574,7 @@ package Atree is
function Sloc (N : Node_Id) return Source_Ptr;
pragma Inline (Sloc);
function Paren_Count (N : Node_Id) return Paren_Count_Type;
function Paren_Count (N : Node_Id) return Nat;
pragma Inline (Paren_Count);
function Parent (N : Node_Id) return Node_Id;
......@@ -623,7 +618,7 @@ package Atree is
procedure Set_Sloc (N : Node_Id; Val : Source_Ptr);
pragma Inline (Set_Sloc);
procedure Set_Paren_Count (N : Node_Id; Val : Paren_Count_Type);
procedure Set_Paren_Count (N : Node_Id; Val : Nat);
pragma Inline (Set_Paren_Count);
procedure Set_Parent (N : Node_Id; Val : Node_Id);
......
......@@ -69,7 +69,7 @@ package body Ch4 is
procedure Bad_Range_Attribute (Loc : Source_Ptr) is
begin
Error_Msg ("range attribute cannot be used in expression", Loc);
Error_Msg ("range attribute cannot be used in expression!", Loc);
Resync_Expression;
end Bad_Range_Attribute;
......@@ -1267,18 +1267,14 @@ package body Ch4 is
then
Error_Msg
("|parentheses not allowed for range attribute", Lparen_Sloc);
Scan; -- past right paren
return Expr_Node;
end if;
-- Bump paren count of expression, note that if the paren count
-- is already at the maximum, then we leave it alone. This will
-- cause some failures in pathalogical conformance tests, which
-- we do not shed a tear over!
-- Bump paren count of expression
if Expr_Node /= Error then
if Paren_Count (Expr_Node) /= Paren_Count_Type'Last then
Set_Paren_Count (Expr_Node, Paren_Count (Expr_Node) + 1);
end if;
Set_Paren_Count (Expr_Node, Paren_Count (Expr_Node) + 1);
end if;
T_Right_Paren; -- past right paren (error message if none)
......@@ -1577,11 +1573,13 @@ package body Ch4 is
-- called in all contexts where a right parenthesis cannot legitimately
-- follow an expression.
-- Error recovery: can raise Error_Resync
-- Error recovery: can not raise Error_Resync
function P_Expression_No_Right_Paren return Node_Id is
Expr : constant Node_Id := P_Expression;
begin
return No_Right_Paren (P_Expression);
Check_No_Right_Paren;
return Expr;
end P_Expression_No_Right_Paren;
----------------------------------------
......@@ -1805,7 +1803,10 @@ package body Ch4 is
else
if Token = Tok_Double_Asterisk then
if Style_Check then Style.Check_Exponentiation_Operator; end if;
if Style_Check then
Style.Check_Exponentiation_Operator;
end if;
Node2 := New_Node (N_Op_Expon, Token_Ptr);
Scan; -- past **
Set_Left_Opnd (Node2, Node1);
......@@ -1818,7 +1819,11 @@ package body Ch4 is
exit when Token not in Token_Class_Mulop;
Tokptr := Token_Ptr;
Node2 := New_Node (P_Multiplying_Operator, Tokptr);
if Style_Check then Style.Check_Binary_Operator; end if;
if Style_Check then
Style.Check_Binary_Operator;
end if;
Scan; -- past operator
Set_Left_Opnd (Node2, Node1);
Set_Right_Opnd (Node2, P_Factor);
......@@ -1830,7 +1835,11 @@ package body Ch4 is
exit when Token not in Token_Class_Binary_Addop;
Tokptr := Token_Ptr;
Node2 := New_Node (P_Binary_Adding_Operator, Tokptr);
if Style_Check then Style.Check_Binary_Operator; end if;
if Style_Check then
Style.Check_Binary_Operator;
end if;
Scan; -- past operator
Set_Left_Opnd (Node2, Node1);
Set_Right_Opnd (Node2, P_Term);
......@@ -1849,7 +1858,11 @@ package body Ch4 is
if Token in Token_Class_Unary_Addop then
Tokptr := Token_Ptr;
Node1 := New_Node (P_Unary_Adding_Operator, Tokptr);
if Style_Check then Style.Check_Unary_Plus_Or_Minus; end if;
if Style_Check then
Style.Check_Unary_Plus_Or_Minus;
end if;
Scan; -- past operator
Set_Right_Opnd (Node1, P_Term);
Set_Op_Name (Node1);
......@@ -1951,6 +1964,39 @@ package body Ch4 is
Attr_Node : Node_Id;
begin
-- We don't just want to roar ahead and call P_Simple_Expression
-- here, since we want to handle the case of a parenthesized range
-- attribute cleanly.
if Token = Tok_Left_Paren then
declare
Lptr : constant Source_Ptr := Token_Ptr;
Scan_State : Saved_Scan_State;
begin
Save_Scan_State (Scan_State);
Scan; -- past left paren
Sexpr := P_Simple_Expression;
if Token = Tok_Apostrophe then
Attr_Node := P_Range_Attribute_Reference (Sexpr);
Expr_Form := EF_Range_Attr;
if Token = Tok_Right_Paren then
Scan; -- scan past right paren if present
end if;
Error_Msg ("parentheses not allowed for range attribute", Lptr);
return Attr_Node;
end if;
Restore_Scan_State (Scan_State);
end;
end if;
-- Here after dealing with parenthesized range attribute
Sexpr := P_Simple_Expression;
if Token = Tok_Apostrophe then
......@@ -2007,7 +2053,11 @@ package body Ch4 is
begin
if Token = Tok_Abs then
Node1 := New_Node (N_Op_Abs, Token_Ptr);
if Style_Check then Style.Check_Abs_Not; end if;
if Style_Check then
Style.Check_Abs_Not;
end if;
Scan; -- past ABS
Set_Right_Opnd (Node1, P_Primary);
Set_Op_Name (Node1);
......@@ -2015,7 +2065,11 @@ package body Ch4 is
elsif Token = Tok_Not then
Node1 := New_Node (N_Op_Not, Token_Ptr);
if Style_Check then Style.Check_Abs_Not; end if;
if Style_Check then
Style.Check_Abs_Not;
end if;
Scan; -- past NOT
Set_Right_Opnd (Node1, P_Primary);
Set_Op_Name (Node1);
......@@ -2116,7 +2170,18 @@ package body Ch4 is
-- Left paren, starts aggregate or parenthesized expression
when Tok_Left_Paren =>
return P_Aggregate_Or_Paren_Expr;
declare
Expr : constant Node_Id := P_Aggregate_Or_Paren_Expr;
begin
if Nkind (Expr) = N_Attribute_Reference
and then Attribute_Name (Expr) = Name_Range
then
Bad_Range_Attribute (Sloc (Expr));
end if;
return Expr;
end;
-- Allocator
......@@ -2174,7 +2239,10 @@ package body Ch4 is
function P_Logical_Operator return Node_Kind is
begin
if Token = Tok_And then
if Style_Check then Style.Check_Binary_Operator; end if;
if Style_Check then
Style.Check_Binary_Operator;
end if;
Scan; -- past AND
if Token = Tok_Then then
......@@ -2185,7 +2253,10 @@ package body Ch4 is
end if;
elsif Token = Tok_Or then
if Style_Check then Style.Check_Binary_Operator; end if;
if Style_Check then
Style.Check_Binary_Operator;
end if;
Scan; -- past OR
if Token = Tok_Else then
......@@ -2196,7 +2267,10 @@ package body Ch4 is
end if;
else -- Token = Tok_Xor
if Style_Check then Style.Check_Binary_Operator; end if;
if Style_Check then
Style.Check_Binary_Operator;
end if;
Scan; -- past XOR
return N_Op_Xor;
end if;
......@@ -2235,7 +2309,11 @@ package body Ch4 is
end if;
Op_Kind := Relop_Node (Token);
if Style_Check then Style.Check_Binary_Operator; end if;
if Style_Check then
Style.Check_Binary_Operator;
end if;
Scan; -- past operator token
if Prev_Token = Tok_Not then
......
......@@ -39,11 +39,9 @@ with Namet; use Namet;
with Nmake; use Nmake;
with Nlists; use Nlists;
with Opt; use Opt;
with Rtsfind; use Rtsfind;
with Sem; use Sem;
with Sem_Cat; use Sem_Cat;
with Sem_Ch3; use Sem_Ch3;
with Sem_Ch8; use Sem_Ch8;
with Sem_Ch13; use Sem_Ch13;
with Sem_Eval; use Sem_Eval;
with Sem_Res; use Sem_Res;
......@@ -88,7 +86,7 @@ package body Sem_Aggr is
-- E_Component/E_Discriminant entity in the record case, in which case the
-- type of the component will be used for the test. If Typ is any other
-- kind of entity, the call is ignored. Expr is the component node in the
-- aggregate which is an explicit occurrence of NULL. An error will be
-- aggregate which is known to have a null value. A warning message will be
-- issued if the component is null excluding.
--
-- It would be better to pass the proper type for Typ ???
......@@ -639,9 +637,11 @@ package body Sem_Aggr is
Index_Typ : Entity_Id;
begin
-- Construct the Index subtype
-- Construct the Index subtype, and associate it with the range
-- construct that generates it.
Index_Typ := Create_Itype (Subtype_Kind (Ekind (Index_Base)), N);
Index_Typ :=
Create_Itype (Subtype_Kind (Ekind (Index_Base)), Aggr_Range (J));
Set_Etype (Index_Typ, Index_Base);
......@@ -684,32 +684,15 @@ package body Sem_Aggr is
Set_Is_Internal (Itype, True);
Init_Size_Align (Itype);
-- Handle aggregate initializing statically allocated dispatch table
if Static_Dispatch_Tables
and then VM_Target = No_VM
and then RTU_Loaded (Ada_Tags)
-- Avoid circularity when rebuilding the compiler
and then Cunit_Entity (Get_Source_Unit (N)) /= RTU_Entity (Ada_Tags)
and then (Etype (N) = RTE (RE_Address_Array)
or else
Base_Type (Etype (N)) = RTE (RE_Tag_Table))
then
Set_Size_Known_At_Compile_Time (Itype);
-- A simple optimization: purely positional aggregates of static
-- components should be passed to gigi unexpanded whenever possible,
-- and regardless of the staticness of the bounds themselves. Subse-
-- quent checks in exp_aggr verify that type is not packed, etc.
else
Set_Size_Known_At_Compile_Time (Itype,
Is_Fully_Positional
and then Comes_From_Source (N)
and then Size_Known_At_Compile_Time (Component_Type (Typ)));
end if;
Set_Size_Known_At_Compile_Time (Itype,
Is_Fully_Positional
and then Comes_From_Source (N)
and then Size_Known_At_Compile_Time (Component_Type (Typ)));
-- We always need a freeze node for a packed array subtype, so that
-- we can build the Packed_Array_Type corresponding to the subtype.
......@@ -1022,7 +1005,7 @@ package body Sem_Aggr is
Pkind = N_Procedure_Call_Statement or else
Pkind = N_Generic_Association or else
Pkind = N_Formal_Object_Declaration or else
Pkind = N_Return_Statement or else
Pkind = N_Simple_Return_Statement or else
Pkind = N_Object_Declaration or else
Pkind = N_Component_Declaration or else
Pkind = N_Parameter_Specification or else
......@@ -1719,7 +1702,7 @@ package body Sem_Aggr is
-- Ada 2005 (AI-231)
if Ada_Version >= Ada_05
and then Nkind (Expression (Assoc)) = N_Null
and then Known_Null (Expression (Assoc))
then
Check_Can_Never_Be_Null (Etype (N), Expression (Assoc));
end if;
......@@ -1851,7 +1834,7 @@ package body Sem_Aggr is
-- Ada 2005 (AI-231)
if Ada_Version >= Ada_05
and then Nkind (Expr) = N_Null
and then Known_Null (Expr)
then
Check_Can_Never_Be_Null (Etype (N), Expr);
end if;
......@@ -1869,7 +1852,7 @@ package body Sem_Aggr is
-- Ada 2005 (AI-231)
if Ada_Version >= Ada_05
and then Nkind (Assoc) = N_Null
and then Known_Null (Assoc)
then
Check_Can_Never_Be_Null (Etype (N), Expression (Assoc));
end if;
......@@ -2401,7 +2384,7 @@ package body Sem_Aggr is
-- Ada 2005 (AI-231)
if Ada_Version >= Ada_05
and then Nkind (Expression (Assoc)) = N_Null
and then Known_Null (Expression (Assoc))
then
Check_Can_Never_Be_Null (Compon, Expression (Assoc));
end if;
......@@ -2731,7 +2714,7 @@ package body Sem_Aggr is
-- Ada 2005 (AI-231)
if Ada_Version >= Ada_05
and then Nkind (Positional_Expr) = N_Null
and then Known_Null (Positional_Expr)
then
Check_Can_Never_Be_Null (Discrim, Positional_Expr);
end if;
......@@ -2969,7 +2952,7 @@ package body Sem_Aggr is
-- Ada 2005 (AI-231)
if Ada_Version >= Ada_05
and then Nkind (Positional_Expr) = N_Null
and then Known_Null (Positional_Expr)
then
Check_Can_Never_Be_Null (Component, Positional_Expr);
end if;
......@@ -3052,7 +3035,7 @@ package body Sem_Aggr is
then
-- We build a partially initialized aggregate with the
-- values of the discriminants and box initialization
-- for the rest.
-- for the rest, if other components are present.
declare
Loc : constant Source_Ptr := Sloc (N);
......@@ -3085,13 +3068,29 @@ package body Sem_Aggr is
Next_Elmt (Discr_Elmt);
end loop;
Append
(Make_Component_Association (Loc,
Choices =>
New_List (Make_Others_Choice (Loc)),
Expression => Empty,
Box_Present => True),
Component_Associations (Expr));
declare
Comp : Entity_Id;
begin
-- Look for a component that is not a discriminant
-- before creating an others box association.
Comp := First_Component (Ctyp);
while Present (Comp) loop
if Ekind (Comp) = E_Component then
Append
(Make_Component_Association (Loc,
Choices =>
New_List (Make_Others_Choice (Loc)),
Expression => Empty,
Box_Present => True),
Component_Associations (Expr));
exit;
end if;
Next_Component (Comp);
end loop;
end;
Add_Association
(Component => Component,
......@@ -3271,7 +3270,7 @@ package body Sem_Aggr is
pragma Assert
(Ada_Version >= Ada_05
and then Present (Expr)
and then Nkind (Expr) = N_Null);
and then Known_Null (Expr));
case Ekind (Typ) is
when E_Array_Type =>
......@@ -3295,7 +3294,7 @@ package body Sem_Aggr is
Insert_Action
(Compile_Time_Constraint_Error
(Expr,
"(Ada 2005) NULL not allowed in null-excluding components?"),
"(Ada 2005) null not allowed in null-excluding component?"),
Make_Raise_Constraint_Error (Sloc (Expr),
Reason => CE_Access_Check_Failed));
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment