Mercurial > hg > CbC > CbC_gcc
comparison gcc/ada/checks.adb @ 145:1830386684a0
gcc-9.2.0
author | anatofuz |
---|---|
date | Thu, 13 Feb 2020 11:34:05 +0900 |
parents | 84e7813d76e9 |
children |
comparison
equal
deleted
inserted
replaced
131:84e7813d76e9 | 145:1830386684a0 |
---|---|
4 -- -- | 4 -- -- |
5 -- C H E C K S -- | 5 -- C H E C K S -- |
6 -- -- | 6 -- -- |
7 -- B o d y -- | 7 -- B o d y -- |
8 -- -- | 8 -- -- |
9 -- Copyright (C) 1992-2018, Free Software Foundation, Inc. -- | 9 -- Copyright (C) 1992-2019, Free Software Foundation, Inc. -- |
10 -- -- | 10 -- -- |
11 -- GNAT is free software; you can redistribute it and/or modify it under -- | 11 -- GNAT is free software; you can redistribute it and/or modify it under -- |
12 -- terms of the GNU General Public License as published by the Free Soft- -- | 12 -- terms of the GNU General Public License as published by the Free Soft- -- |
13 -- ware Foundation; either version 3, or (at your option) any later ver- -- | 13 -- ware Foundation; either version 3, or (at your option) any later ver- -- |
14 -- sion. GNAT is distributed in the hope that it will be useful, but WITH- -- | 14 -- sion. GNAT is distributed in the hope that it will be useful, but WITH- -- |
48 with Sem_Aux; use Sem_Aux; | 48 with Sem_Aux; use Sem_Aux; |
49 with Sem_Ch3; use Sem_Ch3; | 49 with Sem_Ch3; use Sem_Ch3; |
50 with Sem_Ch8; use Sem_Ch8; | 50 with Sem_Ch8; use Sem_Ch8; |
51 with Sem_Disp; use Sem_Disp; | 51 with Sem_Disp; use Sem_Disp; |
52 with Sem_Eval; use Sem_Eval; | 52 with Sem_Eval; use Sem_Eval; |
53 with Sem_Mech; use Sem_Mech; | |
53 with Sem_Res; use Sem_Res; | 54 with Sem_Res; use Sem_Res; |
54 with Sem_Util; use Sem_Util; | 55 with Sem_Util; use Sem_Util; |
55 with Sem_Warn; use Sem_Warn; | 56 with Sem_Warn; use Sem_Warn; |
56 with Sinfo; use Sinfo; | 57 with Sinfo; use Sinfo; |
57 with Sinput; use Sinput; | 58 with Sinput; use Sinput; |
432 end if; | 433 end if; |
433 end if; | 434 end if; |
434 | 435 |
435 -- Fall through for cases where we do set the flag | 436 -- Fall through for cases where we do set the flag |
436 | 437 |
437 Set_Do_Overflow_Check (N, True); | 438 Set_Do_Overflow_Check (N); |
438 Possible_Local_Raise (N, Standard_Constraint_Error); | 439 Possible_Local_Raise (N, Standard_Constraint_Error); |
439 end Activate_Overflow_Check; | 440 end Activate_Overflow_Check; |
440 | 441 |
441 -------------------------- | 442 -------------------------- |
442 -- Activate_Range_Check -- | 443 -- Activate_Range_Check -- |
443 -------------------------- | 444 -------------------------- |
444 | 445 |
445 procedure Activate_Range_Check (N : Node_Id) is | 446 procedure Activate_Range_Check (N : Node_Id) is |
446 begin | 447 begin |
447 Set_Do_Range_Check (N, True); | 448 Set_Do_Range_Check (N); |
448 Possible_Local_Raise (N, Standard_Constraint_Error); | 449 Possible_Local_Raise (N, Standard_Constraint_Error); |
449 end Activate_Range_Check; | 450 end Activate_Range_Check; |
450 | 451 |
451 --------------------------------- | 452 --------------------------------- |
452 -- Alignment_Checks_Suppressed -- | 453 -- Alignment_Checks_Suppressed -- |
574 procedure Apply_Accessibility_Check | 575 procedure Apply_Accessibility_Check |
575 (N : Node_Id; | 576 (N : Node_Id; |
576 Typ : Entity_Id; | 577 Typ : Entity_Id; |
577 Insert_Node : Node_Id) | 578 Insert_Node : Node_Id) |
578 is | 579 is |
579 Loc : constant Source_Ptr := Sloc (N); | 580 Loc : constant Source_Ptr := Sloc (N); |
580 Param_Ent : Entity_Id := Param_Entity (N); | 581 |
582 Check_Cond : Node_Id; | |
583 Param_Ent : Entity_Id := Param_Entity (N); | |
581 Param_Level : Node_Id; | 584 Param_Level : Node_Id; |
582 Type_Level : Node_Id; | 585 Type_Level : Node_Id; |
583 | 586 |
584 begin | 587 begin |
585 if Ada_Version >= Ada_2012 | 588 if Ada_Version >= Ada_2012 |
614 and then not Accessibility_Checks_Suppressed (Typ) | 617 and then not Accessibility_Checks_Suppressed (Typ) |
615 then | 618 then |
616 Param_Level := | 619 Param_Level := |
617 New_Occurrence_Of (Extra_Accessibility (Param_Ent), Loc); | 620 New_Occurrence_Of (Extra_Accessibility (Param_Ent), Loc); |
618 | 621 |
619 Type_Level := | 622 -- Use the dynamic accessibility parameter for the function's result |
620 Make_Integer_Literal (Loc, Deepest_Type_Access_Level (Typ)); | 623 -- when one has been created instead of statically referring to the |
624 -- deepest type level so as to appropriatly handle the rules for | |
625 -- RM 3.10.2 (10.1/3). | |
626 | |
627 if Ekind_In (Scope (Param_Ent), E_Function, | |
628 E_Operator, | |
629 E_Subprogram_Type) | |
630 and then Present (Extra_Accessibility_Of_Result (Scope (Param_Ent))) | |
631 then | |
632 Type_Level := | |
633 New_Occurrence_Of | |
634 (Extra_Accessibility_Of_Result (Scope (Param_Ent)), Loc); | |
635 else | |
636 Type_Level := | |
637 Make_Integer_Literal (Loc, Deepest_Type_Access_Level (Typ)); | |
638 end if; | |
621 | 639 |
622 -- Raise Program_Error if the accessibility level of the access | 640 -- Raise Program_Error if the accessibility level of the access |
623 -- parameter is deeper than the level of the target access type. | 641 -- parameter is deeper than the level of the target access type. |
624 | 642 |
643 Check_Cond := | |
644 Make_Op_Gt (Loc, | |
645 Left_Opnd => Param_Level, | |
646 Right_Opnd => Type_Level); | |
647 | |
625 Insert_Action (Insert_Node, | 648 Insert_Action (Insert_Node, |
626 Make_Raise_Program_Error (Loc, | 649 Make_Raise_Program_Error (Loc, |
627 Condition => | 650 Condition => Check_Cond, |
628 Make_Op_Gt (Loc, | 651 Reason => PE_Accessibility_Check_Failed)); |
629 Left_Opnd => Param_Level, | |
630 Right_Opnd => Type_Level), | |
631 Reason => PE_Accessibility_Check_Failed)); | |
632 | 652 |
633 Analyze_And_Resolve (N); | 653 Analyze_And_Resolve (N); |
654 | |
655 -- If constant folding has happened on the condition for the | |
656 -- generated error, then warn about it being unconditional. | |
657 | |
658 if Nkind (Check_Cond) = N_Identifier | |
659 and then Entity (Check_Cond) = Standard_True | |
660 then | |
661 Error_Msg_Warn := SPARK_Mode /= On; | |
662 Error_Msg_N ("accessibility check fails<<", N); | |
663 Error_Msg_N ("\Program_Error [<<", N); | |
664 end if; | |
634 end if; | 665 end if; |
635 end Apply_Accessibility_Check; | 666 end Apply_Accessibility_Check; |
636 | 667 |
637 -------------------------------- | 668 -------------------------------- |
638 -- Apply_Address_Clause_Check -- | 669 -- Apply_Address_Clause_Check -- |
720 return; | 751 return; |
721 | 752 |
722 -- Generate a check to raise PE if alignment may be inappropriate | 753 -- Generate a check to raise PE if alignment may be inappropriate |
723 | 754 |
724 else | 755 else |
725 -- If the original expression is a non-static constant, use the name | 756 -- If the original expression is a nonstatic constant, use the name |
726 -- of the constant itself rather than duplicating its initialization | 757 -- of the constant itself rather than duplicating its initialization |
727 -- expression, which was extracted above. | 758 -- expression, which was extracted above. |
728 | 759 |
729 -- Note: Expr is empty if the address-clause is applied to in-mode | 760 -- Note: Expr is empty if the address-clause is applied to in-mode |
730 -- actuals (allowed by 13.1(22)). | 761 -- actuals (allowed by 13.1(22)). |
775 -- exception will be raised or not, and if not, we don't need | 806 -- exception will be raised or not, and if not, we don't need |
776 -- the warning so we will kill the warning later on. | 807 -- the warning so we will kill the warning later on. |
777 | 808 |
778 if Compile_Time_Known_Value (Expr) then | 809 if Compile_Time_Known_Value (Expr) then |
779 Alignment_Warnings.Append | 810 Alignment_Warnings.Append |
780 ((E => E, A => Expr_Value (Expr), W => Warning_Msg)); | 811 ((E => E, |
812 A => Expr_Value (Expr), | |
813 P => Empty, | |
814 W => Warning_Msg)); | |
815 | |
816 -- Likewise if the expression is of the form X'Address | |
817 | |
818 elsif Nkind (Expr) = N_Attribute_Reference | |
819 and then Attribute_Name (Expr) = Name_Address | |
820 then | |
821 Alignment_Warnings.Append | |
822 ((E => E, | |
823 A => No_Uint, | |
824 P => Prefix (Expr), | |
825 W => Warning_Msg)); | |
781 | 826 |
782 -- Add explanation of the warning generated by the check | 827 -- Add explanation of the warning generated by the check |
783 | 828 |
784 else | 829 else |
785 Error_Msg_N | 830 Error_Msg_N |
1998 | 2043 |
1999 if not Expander_Active then | 2044 if not Expander_Active then |
2000 return; | 2045 return; |
2001 end if; | 2046 end if; |
2002 | 2047 |
2048 -- Here we will generate an explicit range check, so we don't want to | |
2049 -- set the Do_Range check flag, since the range check is taken care of | |
2050 -- by the code we will generate. | |
2051 | |
2052 Set_Do_Range_Check (Ck_Node, False); | |
2053 | |
2003 if not Compile_Time_Known_Value (LB) | 2054 if not Compile_Time_Known_Value (LB) |
2004 or not Compile_Time_Known_Value (HB) | 2055 or not Compile_Time_Known_Value (HB) |
2005 then | 2056 then |
2006 declare | 2057 declare |
2007 -- First check that the value falls in the range of the base type, | 2058 -- First check that the value falls in the range of the base type, |
2014 | 2065 |
2015 begin | 2066 begin |
2016 Apply_Float_Conversion_Check (Ck_Node, Target_Base); | 2067 Apply_Float_Conversion_Check (Ck_Node, Target_Base); |
2017 Set_Etype (Temp, Target_Base); | 2068 Set_Etype (Temp, Target_Base); |
2018 | 2069 |
2019 Insert_Action (Parent (Par), | 2070 -- Note: Previously the declaration was inserted above the parent |
2071 -- of the conversion, apparently as a small optimization for the | |
2072 -- subequent traversal in Insert_Actions. Unfortunately a similar | |
2073 -- optimization takes place in Insert_Actions, assuming that the | |
2074 -- insertion point must be above the expression that creates | |
2075 -- actions. This is not correct in the presence of conditional | |
2076 -- expressions, where the insertion must be in the list of actions | |
2077 -- attached to the current alternative. | |
2078 | |
2079 Insert_Action (Par, | |
2020 Make_Object_Declaration (Loc, | 2080 Make_Object_Declaration (Loc, |
2021 Defining_Identifier => Temp, | 2081 Defining_Identifier => Temp, |
2022 Object_Definition => New_Occurrence_Of (Target_Typ, Loc), | 2082 Object_Definition => New_Occurrence_Of (Target_Typ, Loc), |
2023 Expression => New_Copy_Tree (Par)), | 2083 Expression => New_Copy_Tree (Par)), |
2024 Suppress => All_Checks); | 2084 Suppress => All_Checks); |
2046 -- an integer type statically. The range checks are unchanged. | 2106 -- an integer type statically. The range checks are unchanged. |
2047 | 2107 |
2048 if Nkind (Ck_Node) = N_Real_Literal | 2108 if Nkind (Ck_Node) = N_Real_Literal |
2049 and then Etype (Ck_Node) = Universal_Real | 2109 and then Etype (Ck_Node) = Universal_Real |
2050 and then Is_Integer_Type (Target_Typ) | 2110 and then Is_Integer_Type (Target_Typ) |
2051 and then Nkind (Parent (Ck_Node)) = N_Type_Conversion | |
2052 then | 2111 then |
2053 declare | 2112 declare |
2054 Int_Val : constant Uint := UR_To_Uint (Realval (Ck_Node)); | 2113 Int_Val : constant Uint := UR_To_Uint (Realval (Ck_Node)); |
2055 | 2114 |
2056 begin | 2115 begin |
2433 | 2492 |
2434 procedure Add_Validity_Check | 2493 procedure Add_Validity_Check |
2435 (Formal : Entity_Id; | 2494 (Formal : Entity_Id; |
2436 Prag_Nam : Name_Id; | 2495 Prag_Nam : Name_Id; |
2437 For_Result : Boolean := False); | 2496 For_Result : Boolean := False); |
2438 -- Add a single 'Valid[_Scalar] check which verifies the initialization | 2497 -- Add a single 'Valid[_Scalars] check which verifies the initialization |
2439 -- of Formal. Prag_Nam denotes the pre or post condition pragma name. | 2498 -- of Formal. Prag_Nam denotes the pre or post condition pragma name. |
2440 -- Set flag For_Result when to verify the result of a function. | 2499 -- Set flag For_Result when to verify the result of a function. |
2441 | 2500 |
2442 ------------------------ | 2501 ------------------------ |
2443 -- Add_Validity_Check -- | 2502 -- Add_Validity_Check -- |
2704 Reason => SE_Infinite_Recursion)); | 2763 Reason => SE_Infinite_Recursion)); |
2705 | 2764 |
2706 -- Here for normal case of predicate active | 2765 -- Here for normal case of predicate active |
2707 | 2766 |
2708 else | 2767 else |
2768 -- If the expression is an IN parameter, the predicate will have | |
2769 -- been applied at the point of call. An additional check would | |
2770 -- be redundant, or will lead to out-of-scope references if the | |
2771 -- call appears within an aspect specification for a precondition. | |
2772 | |
2773 -- However, if the reference is within the body of the subprogram | |
2774 -- that declares the formal, the predicate can safely be applied, | |
2775 -- which may be necessary for a nested call whose formal has a | |
2776 -- different predicate. | |
2777 | |
2778 if Is_Entity_Name (N) | |
2779 and then Ekind (Entity (N)) = E_In_Parameter | |
2780 then | |
2781 declare | |
2782 In_Body : Boolean := False; | |
2783 P : Node_Id := Parent (N); | |
2784 | |
2785 begin | |
2786 while Present (P) loop | |
2787 if Nkind (P) = N_Subprogram_Body | |
2788 and then Corresponding_Spec (P) = Scope (Entity (N)) | |
2789 then | |
2790 In_Body := True; | |
2791 exit; | |
2792 end if; | |
2793 | |
2794 P := Parent (P); | |
2795 end loop; | |
2796 | |
2797 if not In_Body then | |
2798 return; | |
2799 end if; | |
2800 end; | |
2801 end if; | |
2802 | |
2709 -- If the type has a static predicate and the expression is known | 2803 -- If the type has a static predicate and the expression is known |
2710 -- at compile time, see if the expression satisfies the predicate. | 2804 -- at compile time, see if the expression satisfies the predicate. |
2711 | 2805 |
2712 Check_Expression_Against_Static_Predicate (N, Typ); | 2806 Check_Expression_Against_Static_Predicate (N, Typ); |
2713 | 2807 |
3550 Apply_Float_Conversion_Check (Expr, Target_Type); | 3644 Apply_Float_Conversion_Check (Expr, Target_Type); |
3551 | 3645 |
3552 else | 3646 else |
3553 -- Conversions involving fixed-point types are expanded | 3647 -- Conversions involving fixed-point types are expanded |
3554 -- separately, and do not need a Range_Check flag, except | 3648 -- separately, and do not need a Range_Check flag, except |
3555 -- in SPARK_Mode, where the explicit constraint check will | 3649 -- in GNATprove_Mode, where the explicit constraint check |
3556 -- not be generated. | 3650 -- will not be generated. |
3557 | 3651 |
3558 if GNATprove_Mode | 3652 if GNATprove_Mode |
3559 or else not Is_Fixed_Point_Type (Expr_Type) | 3653 or else (not Is_Fixed_Point_Type (Expr_Type) |
3654 and then not Is_Fixed_Point_Type (Target_Type)) | |
3560 then | 3655 then |
3561 Apply_Scalar_Range_Check | 3656 Apply_Scalar_Range_Check |
3562 (Expr, Target_Type, Fixed_Int => Conv_OK); | 3657 (Expr, Target_Type, Fixed_Int => Conv_OK); |
3563 | 3658 |
3564 else | 3659 else |
3565 Set_Do_Range_Check (Expression (N), False); | 3660 Set_Do_Range_Check (Expr, False); |
3566 end if; | 3661 end if; |
3567 | 3662 |
3568 -- If the target type has predicates, we need to indicate | 3663 -- If the target type has predicates, we need to indicate |
3569 -- the need for a check, even if Determine_Range finds that | 3664 -- the need for a check, even if Determine_Range finds that |
3570 -- the value is within bounds. This may be the case e.g for | 3665 -- the value is within bounds. This may be the case e.g for |
4561 | 4656 |
4562 if (Is_Entity_Name (N) and then Is_Known_Valid (Entity (N))) | 4657 if (Is_Entity_Name (N) and then Is_Known_Valid (Entity (N))) |
4563 or else Assume_No_Invalid_Values | 4658 or else Assume_No_Invalid_Values |
4564 or else Assume_Valid | 4659 or else Assume_Valid |
4565 then | 4660 then |
4566 null; | 4661 -- If this is a known valid constant with a nonstatic value, it may |
4662 -- have inherited a narrower subtype from its initial value; use this | |
4663 -- saved subtype (see sem_ch3.adb). | |
4664 | |
4665 if Is_Entity_Name (N) | |
4666 and then Ekind (Entity (N)) = E_Constant | |
4667 and then Present (Actual_Subtype (Entity (N))) | |
4668 then | |
4669 Typ := Actual_Subtype (Entity (N)); | |
4670 end if; | |
4671 | |
4567 else | 4672 else |
4568 Typ := Underlying_Type (Base_Type (Typ)); | 4673 Typ := Underlying_Type (Base_Type (Typ)); |
4569 end if; | 4674 end if; |
4570 | 4675 |
4571 -- Retrieve the base type. Handle the case where the base type is a | 4676 -- Retrieve the base type. Handle the case where the base type is a |
6059 Ensure_Valid (Expression (Expr)); | 6164 Ensure_Valid (Expression (Expr)); |
6060 return; | 6165 return; |
6061 | 6166 |
6062 -- An annoying special case. If this is an out parameter of a scalar | 6167 -- An annoying special case. If this is an out parameter of a scalar |
6063 -- type, then the value is not going to be accessed, therefore it is | 6168 -- type, then the value is not going to be accessed, therefore it is |
6064 -- inappropriate to do any validity check at the call site. | 6169 -- inappropriate to do any validity check at the call site. Likewise |
6170 -- if the parameter is passed by reference. | |
6065 | 6171 |
6066 else | 6172 else |
6067 -- Only need to worry about scalar types | 6173 -- Only need to worry about scalar types |
6068 | 6174 |
6069 if Is_Scalar_Type (Typ) then | 6175 if Is_Scalar_Type (Typ) then |
6085 if Nkind (P) = N_Parameter_Association then | 6191 if Nkind (P) = N_Parameter_Association then |
6086 N := P; | 6192 N := P; |
6087 P := Parent (N); | 6193 P := Parent (N); |
6088 end if; | 6194 end if; |
6089 | 6195 |
6090 -- Only need to worry if we are argument of a procedure call | 6196 -- If this is an indirect or dispatching call, get signature |
6091 -- since functions don't have out parameters. If this is an | 6197 -- from the subprogram type. |
6092 -- indirect or dispatching call, get signature from the | 6198 |
6093 -- subprogram type. | 6199 if Nkind_In (P, N_Entry_Call_Statement, |
6094 | 6200 N_Function_Call, |
6095 if Nkind (P) = N_Procedure_Call_Statement then | 6201 N_Procedure_Call_Statement) |
6202 then | |
6203 E := Get_Called_Entity (P); | |
6096 L := Parameter_Associations (P); | 6204 L := Parameter_Associations (P); |
6097 | 6205 |
6098 if Is_Entity_Name (Name (P)) then | |
6099 E := Entity (Name (P)); | |
6100 else | |
6101 pragma Assert (Nkind (Name (P)) = N_Explicit_Dereference); | |
6102 E := Etype (Name (P)); | |
6103 end if; | |
6104 | |
6105 -- Only need to worry if there are indeed actuals, and if | 6206 -- Only need to worry if there are indeed actuals, and if |
6106 -- this could be a procedure call, otherwise we cannot get a | 6207 -- this could be a subprogram call, otherwise we cannot get |
6107 -- match (either we are not an argument, or the mode of the | 6208 -- a match (either we are not an argument, or the mode of |
6108 -- formal is not OUT). This test also filters out the | 6209 -- the formal is not OUT). This test also filters out the |
6109 -- generic case. | 6210 -- generic case. |
6110 | 6211 |
6111 if Is_Non_Empty_List (L) and then Is_Subprogram (E) then | 6212 if Is_Non_Empty_List (L) and then Is_Subprogram (E) then |
6112 | 6213 |
6113 -- This is the loop through parameters, looking for an | 6214 -- This is the loop through parameters, looking for an |
6114 -- OUT parameter for which we are the argument. | 6215 -- OUT parameter for which we are the argument. |
6115 | 6216 |
6116 F := First_Formal (E); | 6217 F := First_Formal (E); |
6117 A := First (L); | 6218 A := First (L); |
6118 while Present (F) loop | 6219 while Present (F) loop |
6119 if Ekind (F) = E_Out_Parameter and then A = N then | 6220 if A = N |
6221 and then (Ekind (F) = E_Out_Parameter | |
6222 or else Mechanism (F) = By_Reference) | |
6223 then | |
6120 return; | 6224 return; |
6121 end if; | 6225 end if; |
6122 | 6226 |
6123 Next_Formal (F); | 6227 Next_Formal (F); |
6124 Next (A); | 6228 Next (A); |
6763 Loc : constant Source_Ptr := Sloc (N); | 6867 Loc : constant Source_Ptr := Sloc (N); |
6764 Source_Type : constant Entity_Id := Etype (N); | 6868 Source_Type : constant Entity_Id := Etype (N); |
6765 Source_Base_Type : constant Entity_Id := Base_Type (Source_Type); | 6869 Source_Base_Type : constant Entity_Id := Base_Type (Source_Type); |
6766 Target_Base_Type : constant Entity_Id := Base_Type (Target_Type); | 6870 Target_Base_Type : constant Entity_Id := Base_Type (Target_Type); |
6767 | 6871 |
6768 procedure Convert_And_Check_Range; | 6872 procedure Convert_And_Check_Range (Suppress : Check_Id); |
6769 -- Convert the conversion operand to the target base type and save in | 6873 -- Convert N to the target base type and save the result in a temporary. |
6770 -- a temporary. Then check the converted value against the range of the | 6874 -- The action is analyzed using the default checks as modified by the |
6771 -- target subtype. | 6875 -- given Suppress argument. Then check the converted value against the |
6876 -- range of the target subtype. | |
6772 | 6877 |
6773 ----------------------------- | 6878 ----------------------------- |
6774 -- Convert_And_Check_Range -- | 6879 -- Convert_And_Check_Range -- |
6775 ----------------------------- | 6880 ----------------------------- |
6776 | 6881 |
6777 procedure Convert_And_Check_Range is | 6882 procedure Convert_And_Check_Range (Suppress : Check_Id) is |
6778 Tnn : constant Entity_Id := Make_Temporary (Loc, 'T', N); | 6883 Tnn : constant Entity_Id := Make_Temporary (Loc, 'T', N); |
6779 Conv_Node : Node_Id; | 6884 Conv_N : Node_Id; |
6780 | 6885 |
6781 begin | 6886 begin |
6782 -- For enumeration types with non-standard representation this is a | 6887 -- For enumeration types with non-standard representation this is a |
6783 -- direct conversion from the enumeration type to the target integer | 6888 -- direct conversion from the enumeration type to the target integer |
6784 -- type, which is treated by the back end as a normal integer type | 6889 -- type, which is treated by the back end as a normal integer type |
6789 | 6894 |
6790 if Is_Enumeration_Type (Source_Base_Type) | 6895 if Is_Enumeration_Type (Source_Base_Type) |
6791 and then Present (Enum_Pos_To_Rep (Source_Base_Type)) | 6896 and then Present (Enum_Pos_To_Rep (Source_Base_Type)) |
6792 and then Is_Integer_Type (Target_Base_Type) | 6897 and then Is_Integer_Type (Target_Base_Type) |
6793 then | 6898 then |
6794 Conv_Node := | 6899 Conv_N := OK_Convert_To (Target_Base_Type, Duplicate_Subexpr (N)); |
6795 OK_Convert_To | |
6796 (Typ => Target_Base_Type, | |
6797 Expr => Duplicate_Subexpr (N)); | |
6798 | |
6799 -- Common case | |
6800 | |
6801 else | 6900 else |
6802 Conv_Node := | 6901 Conv_N := Convert_To (Target_Base_Type, Duplicate_Subexpr (N)); |
6803 Make_Type_Conversion (Loc, | 6902 end if; |
6804 Subtype_Mark => New_Occurrence_Of (Target_Base_Type, Loc), | 6903 |
6805 Expression => Duplicate_Subexpr (N)); | 6904 -- We make a temporary to hold the value of the conversion to the |
6806 end if; | 6905 -- target base type, and then do the test against this temporary. |
6807 | 6906 -- N itself is replaced by an occurrence of Tnn and followed by |
6808 -- We make a temporary to hold the value of the converted value | 6907 -- the explicit range check. |
6809 -- (converted to the base type), and then do the test against this | |
6810 -- temporary. The conversion itself is replaced by an occurrence of | |
6811 -- Tnn and followed by the explicit range check. Note that checks | |
6812 -- are suppressed for this code, since we don't want a recursive | |
6813 -- range check popping up. | |
6814 | 6908 |
6815 -- Tnn : constant Target_Base_Type := Target_Base_Type (N); | 6909 -- Tnn : constant Target_Base_Type := Target_Base_Type (N); |
6816 -- [constraint_error when Tnn not in Target_Type] | 6910 -- [constraint_error when Tnn not in Target_Type] |
6911 -- Tnn | |
6817 | 6912 |
6818 Insert_Actions (N, New_List ( | 6913 Insert_Actions (N, New_List ( |
6819 Make_Object_Declaration (Loc, | 6914 Make_Object_Declaration (Loc, |
6820 Defining_Identifier => Tnn, | 6915 Defining_Identifier => Tnn, |
6821 Object_Definition => New_Occurrence_Of (Target_Base_Type, Loc), | 6916 Object_Definition => New_Occurrence_Of (Target_Base_Type, Loc), |
6822 Constant_Present => True, | 6917 Constant_Present => True, |
6823 Expression => Conv_Node), | 6918 Expression => Conv_N), |
6824 | 6919 |
6825 Make_Raise_Constraint_Error (Loc, | 6920 Make_Raise_Constraint_Error (Loc, |
6826 Condition => | 6921 Condition => |
6827 Make_Not_In (Loc, | 6922 Make_Not_In (Loc, |
6828 Left_Opnd => New_Occurrence_Of (Tnn, Loc), | 6923 Left_Opnd => New_Occurrence_Of (Tnn, Loc), |
6829 Right_Opnd => New_Occurrence_Of (Target_Type, Loc)), | 6924 Right_Opnd => New_Occurrence_Of (Target_Type, Loc)), |
6830 Reason => Reason)), | 6925 Reason => Reason)), |
6831 Suppress => All_Checks); | 6926 Suppress => Suppress); |
6832 | 6927 |
6833 Rewrite (N, New_Occurrence_Of (Tnn, Loc)); | 6928 Rewrite (N, New_Occurrence_Of (Tnn, Loc)); |
6834 | 6929 |
6835 -- Set the type of N, because the declaration for Tnn might not | 6930 -- Set the type of N, because the declaration for Tnn might not |
6836 -- be analyzed yet, as is the case if N appears within a record | 6931 -- be analyzed yet, as is the case if N appears within a record |
6843 | 6938 |
6844 begin | 6939 begin |
6845 -- First special case, if the source type is already within the range | 6940 -- First special case, if the source type is already within the range |
6846 -- of the target type, then no check is needed (probably we should have | 6941 -- of the target type, then no check is needed (probably we should have |
6847 -- stopped Do_Range_Check from being set in the first place, but better | 6942 -- stopped Do_Range_Check from being set in the first place, but better |
6848 -- late than never in preventing junk code and junk flag settings. | 6943 -- late than never in preventing junk code and junk flag settings). |
6849 | 6944 |
6850 if In_Subrange_Of (Source_Type, Target_Type) | 6945 if In_Subrange_Of (Source_Type, Target_Type) |
6851 | 6946 |
6852 -- We do NOT apply this if the source node is a literal, since in this | 6947 -- We do NOT apply this if the source node is a literal, since in this |
6853 -- case the literal has already been labeled as having the subtype of | 6948 -- case the literal has already been labeled as having the subtype of |
6867 -- in GNATProve mode, then simply set the Do_Range_Check flag and we | 6962 -- in GNATProve mode, then simply set the Do_Range_Check flag and we |
6868 -- are done. In both these cases, we just want to see the range check | 6963 -- are done. In both these cases, we just want to see the range check |
6869 -- flag set, we do not want to generate the explicit range check code. | 6964 -- flag set, we do not want to generate the explicit range check code. |
6870 | 6965 |
6871 if GNATprove_Mode or else not Expander_Active then | 6966 if GNATprove_Mode or else not Expander_Active then |
6872 Set_Do_Range_Check (N, True); | 6967 Set_Do_Range_Check (N); |
6873 return; | 6968 return; |
6874 end if; | 6969 end if; |
6875 | 6970 |
6876 -- Here we will generate an explicit range check, so we don't want to | 6971 -- Here we will generate an explicit range check, so we don't want to |
6877 -- set the Do_Range check flag, since the range check is taken care of | 6972 -- set the Do_Range check flag, since the range check is taken care of |
6920 Reason => Reason), | 7015 Reason => Reason), |
6921 Suppress => All_Checks); | 7016 Suppress => All_Checks); |
6922 | 7017 |
6923 -- Next test for the case where the target type is within the bounds | 7018 -- Next test for the case where the target type is within the bounds |
6924 -- of the base type of the source type, since in this case we can | 7019 -- of the base type of the source type, since in this case we can |
6925 -- simply convert these bounds to the base type of T to do the test. | 7020 -- simply convert the bounds of the target type to this base type |
7021 -- to do the test. | |
6926 | 7022 |
6927 -- [constraint_error when N not in | 7023 -- [constraint_error when N not in |
6928 -- Source_Base_Type (Target_Type'First) | 7024 -- Source_Base_Type (Target_Type'First) |
6929 -- .. | 7025 -- .. |
6930 -- Source_Base_Type(Target_Type'Last))] | 7026 -- Source_Base_Type(Target_Type'Last))] |
6969 Attribute_Name => Name_Last)))), | 7065 Attribute_Name => Name_Last)))), |
6970 Reason => Reason), | 7066 Reason => Reason), |
6971 Suppress => All_Checks); | 7067 Suppress => All_Checks); |
6972 | 7068 |
6973 -- For conversions involving at least one type that is not discrete, | 7069 -- For conversions involving at least one type that is not discrete, |
6974 -- first convert to target type and then generate the range check. | 7070 -- first convert to the target base type and then generate the range |
6975 -- This avoids problems with values that are close to a bound of the | 7071 -- check. This avoids problems with values that are close to a bound |
6976 -- target type that would fail a range check when done in a larger | 7072 -- of the target type that would fail a range check when done in a |
6977 -- source type before converting but would pass if converted with | 7073 -- larger source type before converting but pass if converted with |
6978 -- rounding and then checked (such as in float-to-float conversions). | 7074 -- rounding and then checked (such as in float-to-float conversions). |
6979 | 7075 |
7076 -- Note that overflow checks are not suppressed for this code because | |
7077 -- we do not know whether the source type is in range of the target | |
7078 -- base type (unlike in the next case below). | |
7079 | |
6980 else | 7080 else |
6981 Convert_And_Check_Range; | 7081 Convert_And_Check_Range (Suppress => Range_Check); |
6982 end if; | 7082 end if; |
6983 | 7083 |
6984 -- Note that at this stage we now that the Target_Base_Type is not in | 7084 -- Note that at this stage we know that the Target_Base_Type is not in |
6985 -- the range of the Source_Base_Type (since even the Target_Type itself | 7085 -- the range of the Source_Base_Type (since even the Target_Type itself |
6986 -- is not in this range). It could still be the case that Source_Type is | 7086 -- is not in this range). It could still be the case that Source_Type is |
6987 -- in range of the target base type since we have not checked that case. | 7087 -- in range of the target base type since we have not checked that case. |
6988 | 7088 |
6989 -- If that is the case, we can freely convert the source to the target, | 7089 -- If that is the case, we can freely convert the source to the target, |
6990 -- and then test the target result against the bounds. | 7090 -- and then test the target result against the bounds. Note that checks |
7091 -- are suppressed for this code, since we don't want a recursive range | |
7092 -- check popping up. | |
6991 | 7093 |
6992 elsif In_Subrange_Of (Source_Type, Target_Base_Type) then | 7094 elsif In_Subrange_Of (Source_Type, Target_Base_Type) then |
6993 Convert_And_Check_Range; | 7095 Convert_And_Check_Range (Suppress => All_Checks); |
6994 | 7096 |
6995 -- At this stage, we know that we have two scalar types, which are | 7097 -- At this stage, we know that we have two scalar types, which are |
6996 -- directly convertible, and where neither scalar type has a base | 7098 -- directly convertible, and where neither scalar type has a base |
6997 -- range that is in the range of the other scalar type. | 7099 -- range that is in the range of the other scalar type. |
6998 | 7100 |
7417 | 7519 |
7418 elsif Inside_A_Generic then | 7520 elsif Inside_A_Generic then |
7419 return; | 7521 return; |
7420 end if; | 7522 end if; |
7421 | 7523 |
7524 -- Entities declared in Lock_free protected types must be treated as | |
7525 -- volatile, and we must inhibit validity checks to prevent improper | |
7526 -- constant folding. | |
7527 | |
7528 if Is_Entity_Name (Expr) | |
7529 and then Is_Subprogram (Scope (Entity (Expr))) | |
7530 and then Present (Protected_Subprogram (Scope (Entity (Expr)))) | |
7531 and then Uses_Lock_Free | |
7532 (Scope (Protected_Subprogram (Scope (Entity (Expr))))) | |
7533 then | |
7534 return; | |
7535 end if; | |
7536 | |
7422 -- If we have a checked conversion, then validity check applies to | 7537 -- If we have a checked conversion, then validity check applies to |
7423 -- the expression inside the conversion, not the result, since if | 7538 -- the expression inside the conversion, not the result, since if |
7424 -- the expression inside is valid, then so is the conversion result. | 7539 -- the expression inside is valid, then so is the conversion result. |
7425 | 7540 |
7426 Exp := Expr; | 7541 Exp := Expr; |
7494 Object_Definition => New_Occurrence_Of (Typ, Loc), | 7609 Object_Definition => New_Occurrence_Of (Typ, Loc), |
7495 Expression => New_Copy_Tree (Exp)), | 7610 Expression => New_Copy_Tree (Exp)), |
7496 Suppress => Validity_Check); | 7611 Suppress => Validity_Check); |
7497 | 7612 |
7498 Set_Validated_Object (Var_Id, New_Copy_Tree (Exp)); | 7613 Set_Validated_Object (Var_Id, New_Copy_Tree (Exp)); |
7614 | |
7499 Rewrite (Exp, New_Occurrence_Of (Var_Id, Loc)); | 7615 Rewrite (Exp, New_Occurrence_Of (Var_Id, Loc)); |
7616 | |
7617 -- Move the Do_Range_Check flag over to the new Exp so it doesn't | |
7618 -- get lost and doesn't leak elsewhere. | |
7619 | |
7620 if Do_Range_Check (Validated_Object (Var_Id)) then | |
7621 Set_Do_Range_Check (Exp); | |
7622 Set_Do_Range_Check (Validated_Object (Var_Id), False); | |
7623 end if; | |
7624 | |
7500 PV := New_Occurrence_Of (Var_Id, Loc); | 7625 PV := New_Occurrence_Of (Var_Id, Loc); |
7501 | |
7502 -- Copy the Do_Range_Check flag over to the new Exp, so it doesn't | |
7503 -- get lost. Floating point types are handled elsewhere. | |
7504 | |
7505 if not Is_Floating_Point_Type (Typ) then | |
7506 Set_Do_Range_Check (Exp, Do_Range_Check (Original_Node (Exp))); | |
7507 end if; | |
7508 | 7626 |
7509 -- Otherwise the expression does not denote a variable. Force its | 7627 -- Otherwise the expression does not denote a variable. Force its |
7510 -- evaluation by capturing its value in a constant. Generate: | 7628 -- evaluation by capturing its value in a constant. Generate: |
7511 | 7629 |
7512 -- Temp : constant ... := Exp; | 7630 -- Temp : constant ... := Exp; |
7867 and then Is_RTE (Entity (Prefix (Name (N))), RE_Get_Current_Excep) | 7985 and then Is_RTE (Entity (Prefix (Name (N))), RE_Get_Current_Excep) |
7868 then | 7986 then |
7869 return; | 7987 return; |
7870 end if; | 7988 end if; |
7871 | 7989 |
7990 -- In GNATprove mode, we do not apply the check | |
7991 | |
7992 if GNATprove_Mode then | |
7993 return; | |
7994 end if; | |
7995 | |
7872 -- Otherwise install access check | 7996 -- Otherwise install access check |
7873 | 7997 |
7874 Insert_Action (N, | 7998 Insert_Action (N, |
7875 Make_Raise_Constraint_Error (Loc, | 7999 Make_Raise_Constraint_Error (Loc, |
7876 Condition => | 8000 Condition => |
7956 return; | 8080 return; |
7957 | 8081 |
7958 -- Do not generate an elaboration check if such code is not desirable | 8082 -- Do not generate an elaboration check if such code is not desirable |
7959 | 8083 |
7960 elsif Restriction_Active (No_Elaboration_Code) then | 8084 elsif Restriction_Active (No_Elaboration_Code) then |
8085 return; | |
8086 | |
8087 -- Do not generate an elaboration check if exceptions cannot be used, | |
8088 -- caught, or propagated. | |
8089 | |
8090 elsif not Exceptions_OK then | |
7961 return; | 8091 return; |
7962 | 8092 |
7963 -- Do not consider subprograms which act as compilation units, because | 8093 -- Do not consider subprograms which act as compilation units, because |
7964 -- they cannot be the target of a dispatching call. | 8094 -- they cannot be the target of a dispatching call. |
7965 | 8095 |
9439 Typ : Entity_Id; | 9569 Typ : Entity_Id; |
9440 Indx : Nat) return Node_Id; | 9570 Indx : Nat) return Node_Id; |
9441 -- Returns expression to compute: | 9571 -- Returns expression to compute: |
9442 -- Typ'Length /= Expr'Length | 9572 -- Typ'Length /= Expr'Length |
9443 | 9573 |
9574 function Length_Mismatch_Info_Message | |
9575 (Left_Element_Count : Uint; | |
9576 Right_Element_Count : Uint) return String; | |
9577 -- Returns a message indicating how many elements were expected | |
9578 -- (Left_Element_Count) and how many were found (Right_Element_Count). | |
9579 | |
9444 --------------- | 9580 --------------- |
9445 -- Add_Check -- | 9581 -- Add_Check -- |
9446 --------------- | 9582 --------------- |
9447 | 9583 |
9448 procedure Add_Check (N : Node_Id) is | 9584 procedure Add_Check (N : Node_Id) is |
9626 Make_Op_Ne (Loc, | 9762 Make_Op_Ne (Loc, |
9627 Left_Opnd => Get_E_Length (Typ, Indx), | 9763 Left_Opnd => Get_E_Length (Typ, Indx), |
9628 Right_Opnd => Get_N_Length (Expr, Indx)); | 9764 Right_Opnd => Get_N_Length (Expr, Indx)); |
9629 end Length_N_Cond; | 9765 end Length_N_Cond; |
9630 | 9766 |
9767 ---------------------------------- | |
9768 -- Length_Mismatch_Info_Message -- | |
9769 ---------------------------------- | |
9770 | |
9771 function Length_Mismatch_Info_Message | |
9772 (Left_Element_Count : Uint; | |
9773 Right_Element_Count : Uint) return String | |
9774 is | |
9775 | |
9776 function Plural_Vs_Singular_Ending (Count : Uint) return String; | |
9777 -- Returns an empty string if Count is 1; otherwise returns "s" | |
9778 | |
9779 function Plural_Vs_Singular_Ending (Count : Uint) return String is | |
9780 begin | |
9781 if Count = 1 then | |
9782 return ""; | |
9783 else | |
9784 return "s"; | |
9785 end if; | |
9786 end Plural_Vs_Singular_Ending; | |
9787 | |
9788 begin | |
9789 return "expected " & UI_Image (Left_Element_Count) | |
9790 & " element" | |
9791 & Plural_Vs_Singular_Ending (Left_Element_Count) | |
9792 & "; found " & UI_Image (Right_Element_Count) | |
9793 & " element" | |
9794 & Plural_Vs_Singular_Ending (Right_Element_Count); | |
9795 end Length_Mismatch_Info_Message; | |
9796 | |
9631 ----------------- | 9797 ----------------- |
9632 -- Same_Bounds -- | 9798 -- Same_Bounds -- |
9633 ----------------- | 9799 ----------------- |
9634 | 9800 |
9635 function Same_Bounds (L : Node_Id; R : Node_Id) return Boolean is | 9801 function Same_Bounds (L : Node_Id; R : Node_Id) return Boolean is |
9820 end if; | 9986 end if; |
9821 | 9987 |
9822 if L_Length > R_Length then | 9988 if L_Length > R_Length then |
9823 Add_Check | 9989 Add_Check |
9824 (Compile_Time_Constraint_Error | 9990 (Compile_Time_Constraint_Error |
9825 (Wnode, "too few elements for}??", T_Typ)); | 9991 (Wnode, "too few elements for}??", T_Typ, |
9992 Extra_Msg => Length_Mismatch_Info_Message | |
9993 (L_Length, R_Length))); | |
9826 | 9994 |
9827 elsif L_Length < R_Length then | 9995 elsif L_Length < R_Length then |
9828 Add_Check | 9996 Add_Check |
9829 (Compile_Time_Constraint_Error | 9997 (Compile_Time_Constraint_Error |
9830 (Wnode, "too many elements for}??", T_Typ)); | 9998 (Wnode, "too many elements for}??", T_Typ, |
9999 Extra_Msg => Length_Mismatch_Info_Message | |
10000 (L_Length, R_Length))); | |
9831 end if; | 10001 end if; |
9832 | 10002 |
9833 -- The comparison for an individual index subtype | 10003 -- The comparison for an individual index subtype |
9834 -- is omitted if the corresponding index subtypes | 10004 -- is omitted if the corresponding index subtypes |
9835 -- statically match, since the result is known to | 10005 -- statically match, since the result is known to |
10776 declare | 10946 declare |
10777 AWR : Alignment_Warnings_Record | 10947 AWR : Alignment_Warnings_Record |
10778 renames Alignment_Warnings.Table (J); | 10948 renames Alignment_Warnings.Table (J); |
10779 begin | 10949 begin |
10780 if Known_Alignment (AWR.E) | 10950 if Known_Alignment (AWR.E) |
10781 and then AWR.A mod Alignment (AWR.E) = 0 | 10951 and then ((AWR.A /= No_Uint |
10952 and then AWR.A mod Alignment (AWR.E) = 0) | |
10953 or else (Present (AWR.P) | |
10954 and then Has_Compatible_Alignment | |
10955 (AWR.E, AWR.P, True) = | |
10956 Known_Compatible)) | |
10782 then | 10957 then |
10783 Delete_Warning_And_Continuations (AWR.W); | 10958 Delete_Warning_And_Continuations (AWR.W); |
10784 end if; | 10959 end if; |
10785 end; | 10960 end; |
10786 end loop; | 10961 end loop; |