diff options
author | Arnaud Charlet <charlet@gcc.gnu.org> | 2012-07-12 12:56:02 +0200 |
---|---|---|
committer | Arnaud Charlet <charlet@gcc.gnu.org> | 2012-07-12 12:56:02 +0200 |
commit | 759658521a6e6c4f1b426752ea568ad69806b8a2 (patch) | |
tree | 3f4ee2a3f34ece8b71fc886093da3456a5ae2ad1 /gcc/ada/exp_pakd.adb | |
parent | 727e7b1a870bdc057c4cb6d7d09ef1b56a84f222 (diff) | |
download | gcc-759658521a6e6c4f1b426752ea568ad69806b8a2.tar.gz |
[multiple changes]
2012-07-12 Vasiliy Fofanov <fofanov@adacore.com>
* vms_data.ads: Add VMS qualifiers for -gnatn1/2 switches.
2012-07-12 Thomas Quinot <quinot@adacore.com>
* exp_ch5.adb, exp_pakd.adb, rtsfind.ads, freeze.adb, sem_util.adb,
sem_util.ads, exp_aggr.adb
(Exp_Aggr.Packed_Array_Aggregate_Handled): Simplify processing
for reverse storage order aggregate.
(Exp_Pakd.Byte_Swap): New utility routine used by...
(Exp_Pakd.Expand_Bit_Packed_Element_Set,
Expand_Packed_Element_Reference): For the case of a free-standing
packed array with reverse storage order, perform byte swapping.
(Rtsfind): Make new entities RE_Bswap_{16,32,64} available.
(Freeze.Check_Component_Storage_Order): New utility routine
to enforce legality rules for nested composite types whose
enclosing composite has an explicitly defined Scalar_Storage_Order
attribute.
(Sem_Util.In_Reverse_Storage_Order_Object): Renamed from
Sem_Util.In_Reverse_Storage_Order_Record, as SSO now applies to
array types as well.
(Exp_Ch5.Expand_Assign_Array): Remove now unnecessary kludge
for change of scalar storage order in assignments. The Lhs and
Rhs now always have the same scalar storage order.
2012-07-12 Hristian Kirtchev <kirtchev@adacore.com>
* g-debpoo.adb (Allocate): Add local constant
No_Element. Initialize the allocated memory chunk to No_Element.
2012-07-12 Ed Schonberg <schonberg@adacore.com>
* sem_ch12.adb (Validate_Derived_Type_Instance): Handle properly
the case of an instance of a child unit where a formal derived
type DT is an extension of a type T declared in a parent unit,
and the actual in the instance of the child is the type T declared
in the parent instance, and that actual is not a derived type.
2012-07-12 Eric Botcazou <ebotcazou@adacore.com>
Tristan Gingold <gingold@adacore.com>
* system-hpux-ia64.ads: Enable ZCX by default.
* gcc-interface/Makefile.in: Use alternate stack on ia64-hpux.
Change soext to .so.
From-SVN: r189439
Diffstat (limited to 'gcc/ada/exp_pakd.adb')
-rw-r--r-- | gcc/ada/exp_pakd.adb | 73 |
1 files changed, 72 insertions, 1 deletions
diff --git a/gcc/ada/exp_pakd.adb b/gcc/ada/exp_pakd.adb index ee75cf732be..b958383f933 100644 --- a/gcc/ada/exp_pakd.adb +++ b/gcc/ada/exp_pakd.adb @@ -543,6 +543,42 @@ package body Exp_Pakd is -- array type on the fly). Such actions are inserted into the tree -- directly using Insert_Action. + function Byte_Swap (N : Node_Id) return Node_Id; + -- Wrap N in a call to a byte swapping function, with appropriate type + -- conversions. + + --------------- + -- Byte_Swap -- + --------------- + + function Byte_Swap (N : Node_Id) return Node_Id is + Loc : constant Source_Ptr := Sloc (N); + T : constant Entity_Id := Etype (N); + Swap_RE : RE_Id; + Swap_F : Entity_Id; + + begin + pragma Assert (Esize (T) > 8); + + if Esize (T) <= 16 then + Swap_RE := RE_Bswap_16; + elsif Esize (T) <= 32 then + Swap_RE := RE_Bswap_32; + else pragma Assert (Esize (T) <= 64); + Swap_RE := RE_Bswap_64; + end if; + + Swap_F := RTE (Swap_RE); + + return Unchecked_Convert_To + (T, + Make_Function_Call (Loc, + Name => + New_Occurrence_Of (Swap_F, Loc), + Parameter_Associations => + New_List (Unchecked_Convert_To (Etype (Swap_F), N)))); + end Byte_Swap; + ------------------------------ -- Compute_Linear_Subscript -- ------------------------------ @@ -1304,6 +1340,12 @@ package body Exp_Pakd is -- contains the value. Otherwise Rhs_Val_Known is set False, and -- the Rhs_Val is undefined. + Require_Byte_Swapping : Boolean := False; + -- True if byte swapping required, for the Reverse_Storage_Order case + -- when the packed array is a free-standing object. (If it is part + -- of a composite type, and therefore potentially not aligned on a byte + -- boundary, the swapping is done by the back-end). + function Get_Shift return Node_Id; -- Function used to get the value of Shift, making sure that it -- gets duplicated if the function is called more than once. @@ -1415,6 +1457,11 @@ package body Exp_Pakd is -- Obj := atyp!((Obj and Mask1) or (shift_left (rhs, Shift))) + -- or in the case of a freestanding Reverse_Storage_Order object, + + -- Obj := Swap (atyp!((Swap (Obj) and Mask1) + -- or (shift_left (rhs, Shift)))) + -- where Mask1 is obtained by shifting Cmask left Shift bits -- and then complementing the result. @@ -1485,6 +1532,14 @@ package body Exp_Pakd is Set_Etype (Obj, T); Set_Etype (New_Lhs, T); Set_Etype (New_Rhs, T); + + if Reverse_Storage_Order (Base_Type (Atyp)) + and then Esize (T) > 8 + and then not In_Reverse_Storage_Order_Object (Obj) + then + Require_Byte_Swapping := True; + New_Rhs := Byte_Swap (New_Rhs); + end if; end; -- First we deal with the "and" @@ -1615,6 +1670,11 @@ package body Exp_Pakd is end; end if; + if Require_Byte_Swapping then + Set_Etype (New_Rhs, Etype (Obj)); + New_Rhs := Byte_Swap (New_Rhs); + end if; + -- Now do the rewrite Rewrite (N, @@ -1977,6 +2037,17 @@ package body Exp_Pakd is Lit := Make_Integer_Literal (Loc, Cmask); Set_Print_In_Hex (Lit); + -- Byte swapping required for the Reverse_Storage_Order case, but + -- only for a free-standing object (see note on Require_Byte_Swapping + -- in Expand_Bit_Packed_Element_Set). + + if Reverse_Storage_Order (Atyp) + and then Esize (Atyp) > 8 + and then not In_Reverse_Storage_Order_Object (Obj) + then + Obj := Byte_Swap (Obj); + end if; + -- We generate a shift right to position the field, followed by a -- masking operation to extract the bit field, and we finally do an -- unchecked conversion to convert the result to the required target. @@ -2726,7 +2797,7 @@ package body Exp_Pakd is -- We also have to adjust if the storage order is reversed - if Bytes_Big_Endian xor In_Reverse_Storage_Order_Record (Obj) then + if Bytes_Big_Endian xor Reverse_Storage_Order (Base_Type (Atyp)) then Shift := Make_Op_Subtract (Loc, Left_Opnd => Make_Integer_Literal (Loc, Osiz - Csiz), |