aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorMark Mitchell <mark@codesourcery.com>2003-02-18 19:17:29 +0000
committerMark Mitchell <mmitchel@gcc.gnu.org>2003-02-18 19:17:29 +0000
commit6b99d1c036cedd5d1e123ffca8201946fbcd2929 (patch)
tree6194e752687100426e32b0c55b5f09fae875b2d3 /gcc
parent2e120205b3fef4037f776cdeb3159365be01e300 (diff)
downloadgcc-6b99d1c036cedd5d1e123ffca8201946fbcd2929.zip
gcc-6b99d1c036cedd5d1e123ffca8201946fbcd2929.tar.gz
gcc-6b99d1c036cedd5d1e123ffca8201946fbcd2929.tar.bz2
re PR c++/9704 (miscompilation of classes with bit fields)
PR c++/9704 * class.c (layout_class_type): In the 3.2 ABI, take into account trailing bit fields when computing CLASSTYPE_SIZE_UNIT. PR c++/9704 * g++.dg/init/copy5.C: New test. From-SVN: r63055
Diffstat (limited to 'gcc')
-rw-r--r--gcc/cp/ChangeLog6
-rw-r--r--gcc/cp/class.c20
-rw-r--r--gcc/testsuite/ChangeLog5
3 files changed, 27 insertions, 4 deletions
diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog
index 73676fc..9071de0 100644
--- a/gcc/cp/ChangeLog
+++ b/gcc/cp/ChangeLog
@@ -1,3 +1,9 @@
+2003-02-18 Mark Mitchell <mark@codesourcery.com>
+
+ PR c++/9704
+ * class.c (layout_class_type): In the 3.2 ABI, take into account
+ trailing bit fields when computing CLASSTYPE_SIZE_UNIT.
+
2003-02-18 Matt Austern <austern@apple.com>
* cp/cp-lang.c: Change lang hooks so that final_write_globals does
diff --git a/gcc/cp/class.c b/gcc/cp/class.c
index 5e8b9fa..5ee67bc 100644
--- a/gcc/cp/class.c
+++ b/gcc/cp/class.c
@@ -5194,16 +5194,28 @@ layout_class_type (tree t, tree *virtuals_p)
}
else
{
+ tree eoc;
+
+ /* If the ABI version is not at least two, and the last
+ field was a bit-field, RLI may not be on a byte
+ boundary. In particular, rli_size_unit_so_far might
+ indicate the last complete byte, while rli_size_so_far
+ indicates the total number of bits used. Therefore,
+ rli_size_so_far, rather than rli_size_unit_so_far, is
+ used to compute TYPE_SIZE_UNIT. */
+ eoc = end_of_class (t, /*include_virtuals_p=*/0);
TYPE_SIZE_UNIT (base_t)
= size_binop (MAX_EXPR,
- rli_size_unit_so_far (rli),
- end_of_class (t, /*include_virtuals_p=*/0));
+ convert (sizetype,
+ size_binop (CEIL_DIV_EXPR,
+ rli_size_so_far (rli),
+ bitsize_int (BITS_PER_UNIT))),
+ eoc);
TYPE_SIZE (base_t)
= size_binop (MAX_EXPR,
rli_size_so_far (rli),
size_binop (MULT_EXPR,
- convert (bitsizetype,
- TYPE_SIZE_UNIT (base_t)),
+ convert (bitsizetype, eoc),
bitsize_int (BITS_PER_UNIT)));
}
TYPE_ALIGN (base_t) = rli->record_align;
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index 96d1b06..220c696 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2003-02-18 Mark Mitchell <mark@codesourcery.com>
+
+ PR c++/9704
+ * g++.dg/init/copy5.C: New test.
+
2003-02-18 Geoffrey Keating <geoffk@apple.com>
* gcc.dg/pch/pch.exp: Delete $bname.h before copying into it.