aboutsummaryrefslogtreecommitdiff
path: root/lib/CodeGen/TargetInfo.cpp
diff options
context:
space:
mode:
authorDaniel Dunbar <daniel@zuster.org>2010-01-29 03:22:29 +0000
committerDaniel Dunbar <daniel@zuster.org>2010-01-29 03:22:29 +0000
commit679855a6e14fbc6c6838c566aa74c32f52f4f946 (patch)
tree243bda8fdad7e2bbfe44cae47bbf2a2ccadb5e6a /lib/CodeGen/TargetInfo.cpp
parent808015a18bd97781ce437831a95a92fdfc8d5136 (diff)
ARM/APCS ABI: Fix some problems with bit-fields in structures. After rereading
the ABI spec, this turns out to simplify the code. We still have some annoying code which mismatches the spec with regard to empty structures. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@94796 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/CodeGen/TargetInfo.cpp')
-rw-r--r--lib/CodeGen/TargetInfo.cpp36
1 files changed, 18 insertions, 18 deletions
diff --git a/lib/CodeGen/TargetInfo.cpp b/lib/CodeGen/TargetInfo.cpp
index bc512e7a27..92ff312425 100644
--- a/lib/CodeGen/TargetInfo.cpp
+++ b/lib/CodeGen/TargetInfo.cpp
@@ -1611,30 +1611,30 @@ static bool isIntegerLikeType(QualType Ty,
i != e; ++i, ++idx) {
const FieldDecl *FD = *i;
- // Check if this field is at offset 0.
- uint64_t Offset = Layout.getFieldOffset(idx);
- if (Offset != 0) {
- // Allow padding bit-fields, but only if they are all at the end of the
- // structure (despite the wording above, this matches gcc).
- if (FD->isBitField() &&
- !FD->getBitWidth()->EvaluateAsInt(Context).getZExtValue()) {
- for (; i != e; ++i)
- if (!i->isBitField() ||
- i->getBitWidth()->EvaluateAsInt(Context).getZExtValue())
- return false;
-
- // All remaining fields are padding, allow this.
- return true;
- }
+ // Bit-fields are not addressable, we only need to verify they are "integer
+ // like". We still have to disallow a subsequent non-bitfield, for example:
+ // struct { int : 0; int x }
+ // is non-integer like according to gcc.
+ if (FD->isBitField()) {
+ if (!RD->isUnion())
+ HadField = true;
+
+ if (!isIntegerLikeType(FD->getType(), Context, VMContext))
+ return false;
- return false;
+ continue;
}
+ // Check if this field is at offset 0.
+ if (Layout.getFieldOffset(idx) != 0)
+ return false;
+
if (!isIntegerLikeType(FD->getType(), Context, VMContext))
return false;
- // Only allow at most one field in a structure. Again this doesn't match the
- // wording above, but follows gcc.
+ // Only allow at most one field in a structure. This doesn't match the
+ // wording above, but follows gcc in situations with a field following an
+ // empty structure.
if (!RD->isUnion()) {
if (HadField)
return false;