stor-layout.c (finish_bitfield_representative): Fallback to conservative maximum size if the padding up to the next field...
2012-03-20 Richard Guenther <rguenther@suse.de> * stor-layout.c (finish_bitfield_representative): Fallback to conservative maximum size if the padding up to the next field cannot be computed as a constant. (finish_bitfield_layout): If we cannot compute the distance between the start of the bitfield representative and the bitfield member start a new representative. * expr.c (get_bit_range): The distance between the start of the bitfield representative and the bitfield member is zero if the field offsets are not constants. * gnat.dg/pack16.adb: New testcase. * gnat.dg/pack16_pkg.ads: Likewise. * gnat.dg/specs/pack8.ads: Likewise. * gnat.dg/specs/pack8_pkg.ads: Likewise. From-SVN: r185563
This commit is contained in:
parent
9b96cf92a4
commit
7ebf9677e5
@ -1,3 +1,15 @@
|
||||
2012-03-20 Richard Guenther <rguenther@suse.de>
|
||||
|
||||
* stor-layout.c (finish_bitfield_representative): Fallback
|
||||
to conservative maximum size if the padding up to the next
|
||||
field cannot be computed as a constant.
|
||||
(finish_bitfield_layout): If we cannot compute the distance
|
||||
between the start of the bitfield representative and the
|
||||
bitfield member start a new representative.
|
||||
* expr.c (get_bit_range): The distance between the start of
|
||||
the bitfield representative and the bitfield member is zero
|
||||
if the field offsets are not constants.
|
||||
|
||||
2012-03-20 Tristan Gingold <gingold@adacore.com>
|
||||
|
||||
* tree.h (enum size_type_kind): Add stk_ prefix to constants,
|
||||
|
19
gcc/expr.c
19
gcc/expr.c
@ -4452,7 +4452,7 @@ get_bit_range (unsigned HOST_WIDE_INT *bitstart,
|
||||
HOST_WIDE_INT bitpos)
|
||||
{
|
||||
unsigned HOST_WIDE_INT bitoffset;
|
||||
tree field, repr, offset;
|
||||
tree field, repr;
|
||||
|
||||
gcc_assert (TREE_CODE (exp) == COMPONENT_REF);
|
||||
|
||||
@ -4467,12 +4467,17 @@ get_bit_range (unsigned HOST_WIDE_INT *bitstart,
|
||||
}
|
||||
|
||||
/* Compute the adjustment to bitpos from the offset of the field
|
||||
relative to the representative. */
|
||||
offset = size_diffop (DECL_FIELD_OFFSET (field),
|
||||
DECL_FIELD_OFFSET (repr));
|
||||
bitoffset = (tree_low_cst (offset, 1) * BITS_PER_UNIT
|
||||
+ tree_low_cst (DECL_FIELD_BIT_OFFSET (field), 1)
|
||||
- tree_low_cst (DECL_FIELD_BIT_OFFSET (repr), 1));
|
||||
relative to the representative. DECL_FIELD_OFFSET of field and
|
||||
repr are the same by construction if they are not constants,
|
||||
see finish_bitfield_layout. */
|
||||
if (host_integerp (DECL_FIELD_OFFSET (field), 1)
|
||||
&& host_integerp (DECL_FIELD_OFFSET (repr), 1))
|
||||
bitoffset = (tree_low_cst (DECL_FIELD_OFFSET (field), 1)
|
||||
- tree_low_cst (DECL_FIELD_OFFSET (repr), 1)) * BITS_PER_UNIT;
|
||||
else
|
||||
bitoffset = 0;
|
||||
bitoffset += (tree_low_cst (DECL_FIELD_BIT_OFFSET (field), 1)
|
||||
- tree_low_cst (DECL_FIELD_BIT_OFFSET (repr), 1));
|
||||
|
||||
*bitstart = bitpos - bitoffset;
|
||||
*bitend = *bitstart + tree_low_cst (DECL_SIZE (repr), 1) - 1;
|
||||
|
@ -1781,10 +1781,17 @@ finish_bitfield_representative (tree repr, tree field)
|
||||
return;
|
||||
maxsize = size_diffop (DECL_FIELD_OFFSET (nextf),
|
||||
DECL_FIELD_OFFSET (repr));
|
||||
gcc_assert (host_integerp (maxsize, 1));
|
||||
maxbitsize = (tree_low_cst (maxsize, 1) * BITS_PER_UNIT
|
||||
+ tree_low_cst (DECL_FIELD_BIT_OFFSET (nextf), 1)
|
||||
- tree_low_cst (DECL_FIELD_BIT_OFFSET (repr), 1));
|
||||
if (host_integerp (maxsize, 1))
|
||||
{
|
||||
maxbitsize = (tree_low_cst (maxsize, 1) * BITS_PER_UNIT
|
||||
+ tree_low_cst (DECL_FIELD_BIT_OFFSET (nextf), 1)
|
||||
- tree_low_cst (DECL_FIELD_BIT_OFFSET (repr), 1));
|
||||
/* If the group ends within a bitfield nextf does not need to be
|
||||
aligned to BITS_PER_UNIT. Thus round up. */
|
||||
maxbitsize = (maxbitsize + BITS_PER_UNIT - 1) & ~(BITS_PER_UNIT - 1);
|
||||
}
|
||||
else
|
||||
maxbitsize = bitsize;
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -1888,6 +1895,8 @@ finish_bitfield_layout (record_layout_info rli)
|
||||
}
|
||||
else if (DECL_BIT_FIELD_TYPE (field))
|
||||
{
|
||||
gcc_assert (repr != NULL_TREE);
|
||||
|
||||
/* Zero-size bitfields finish off a representative and
|
||||
do not have a representative themselves. This is
|
||||
required by the C++ memory model. */
|
||||
@ -1896,6 +1905,24 @@ finish_bitfield_layout (record_layout_info rli)
|
||||
finish_bitfield_representative (repr, prev);
|
||||
repr = NULL_TREE;
|
||||
}
|
||||
|
||||
/* We assume that either DECL_FIELD_OFFSET of the representative
|
||||
and each bitfield member is a constant or they are equal.
|
||||
This is because we need to be able to compute the bit-offset
|
||||
of each field relative to the representative in get_bit_range
|
||||
during RTL expansion.
|
||||
If these constraints are not met, simply force a new
|
||||
representative to be generated. That will at most
|
||||
generate worse code but still maintain correctness with
|
||||
respect to the C++ memory model. */
|
||||
else if (!((host_integerp (DECL_FIELD_OFFSET (repr), 1)
|
||||
&& host_integerp (DECL_FIELD_OFFSET (field), 1))
|
||||
|| operand_equal_p (DECL_FIELD_OFFSET (repr),
|
||||
DECL_FIELD_OFFSET (field), 0)))
|
||||
{
|
||||
finish_bitfield_representative (repr, prev);
|
||||
repr = start_bitfield_representative (field);
|
||||
}
|
||||
}
|
||||
else
|
||||
continue;
|
||||
|
@ -1,3 +1,10 @@
|
||||
2012-03-20 Richard Guenther <rguenther@suse.de>
|
||||
|
||||
* gnat.dg/pack16.adb: New testcase.
|
||||
* gnat.dg/pack16_pkg.ads: Likewise.
|
||||
* gnat.dg/specs/pack8.ads: Likewise.
|
||||
* gnat.dg/specs/pack8_pkg.ads: Likewise.
|
||||
|
||||
2012-03-19 Paolo Carlini <paolo.carlini@oracle.com>
|
||||
|
||||
* g++.dg/warn/Wuseless-cast.C: Extend.
|
||||
|
26
gcc/testsuite/gnat.dg/pack16.adb
Normal file
26
gcc/testsuite/gnat.dg/pack16.adb
Normal file
@ -0,0 +1,26 @@
|
||||
-- { dg-do compile }
|
||||
-- { dg-options "-gnatws" }
|
||||
|
||||
with Pack16_Pkg; use Pack16_Pkg;
|
||||
|
||||
procedure Pack16 is
|
||||
|
||||
type Sample_Table_T is array (1 .. N) of Integer;
|
||||
|
||||
type Clock_T is record
|
||||
N_Ticks : Integer := 0;
|
||||
end record;
|
||||
|
||||
type Sampling_Descriptor_T is record
|
||||
Values : Sample_Table_T;
|
||||
Valid : Boolean;
|
||||
Tstamp : Clock_T;
|
||||
end record;
|
||||
|
||||
pragma Pack (Sampling_Descriptor_T);
|
||||
|
||||
Sampling_Data : Sampling_Descriptor_T;
|
||||
|
||||
begin
|
||||
null;
|
||||
end;
|
5
gcc/testsuite/gnat.dg/pack16_pkg.ads
Normal file
5
gcc/testsuite/gnat.dg/pack16_pkg.ads
Normal file
@ -0,0 +1,5 @@
|
||||
package Pack16_Pkg is
|
||||
|
||||
N : Natural := 16;
|
||||
|
||||
end Pack16_Pkg;
|
19
gcc/testsuite/gnat.dg/specs/pack8.ads
Normal file
19
gcc/testsuite/gnat.dg/specs/pack8.ads
Normal file
@ -0,0 +1,19 @@
|
||||
with Pack8_Pkg;
|
||||
|
||||
package Pack8 is
|
||||
|
||||
subtype Index_Type is Integer range 1 .. Pack8_Pkg.N;
|
||||
|
||||
subtype Str is String( Index_Type);
|
||||
|
||||
subtype Str2 is String (1 .. 11);
|
||||
|
||||
type Rec is record
|
||||
S1 : Str;
|
||||
S2 : Str;
|
||||
B : Boolean;
|
||||
S3 : Str2;
|
||||
end record;
|
||||
pragma Pack (Rec);
|
||||
|
||||
end Pack8;
|
5
gcc/testsuite/gnat.dg/specs/pack8_pkg.ads
Normal file
5
gcc/testsuite/gnat.dg/specs/pack8_pkg.ads
Normal file
@ -0,0 +1,5 @@
|
||||
package Pack8_Pkg is
|
||||
|
||||
N : Natural := 1;
|
||||
|
||||
end Pack8_Pkg;
|
Loading…
Reference in New Issue
Block a user