]> granicus.if.org Git - clang/commitdiff
Recommited:
authorStepan Dyatkovskiy <stpworld@narod.ru>
Wed, 18 Sep 2013 09:08:52 +0000 (09:08 +0000)
committerStepan Dyatkovskiy <stpworld@narod.ru>
Wed, 18 Sep 2013 09:08:52 +0000 (09:08 +0000)
Fix for PR16752. Second commit.

PR16752: 'mode' attribute for unusual targets doesn't work properly
Description:
Troubles could be happened due to some assumptions in handleModeAttr function (see SemaDeclAttr.cpp).
For example, it assumes that 32 bit integer is 'int', while it could be 16 bit only.
Instead of asking target: 'which type do you want to use for int32_t ?' it just hardcodes general opinion. That doesn't looks pretty correct.
Please consider the next solution:
1. In Basic/TargetInfo add getIntTypeByWidth and getRealTypeByWidth methods. Methods asks target for proper type for given bit width.
2. Fix handleModeAttr according to new methods in TargetInfo.

Fixes:
1st Commit (Done): Add new methods for TargetInfo:
     getRealTypeByWidth and getIntTypeByWidth
  for ASTContext names are almost same(invokes new methods from TargetInfo):
     getIntTypeForBitwidth and getRealTypeForBitwidth

2nd Commit (Current): Fix SemaDeclAttr, handleModeAttr function.

Also test/Sema/attr-mode.c was fixed. 'XC' mode test was disabled for PPC64 machines.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@190926 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Sema/SemaDeclAttr.cpp
test/Sema/attr-mode.c

index 756d56ad16868f59165560427d7de203ede8532e..10ff4b8b942edc2a9956d8f81d8a265030424004 100644 (file)
@@ -3460,77 +3460,24 @@ static void handleModeAttr(Sema &S, Decl *D, const AttributeList &Attr) {
 
   // FIXME: Sync this with InitializePredefinedMacros; we need to match int8_t
   // and friends, at least with glibc.
-  // FIXME: Make sure 32/64-bit integers don't get defined to types of the wrong
-  // width on unusual platforms.
   // FIXME: Make sure floating-point mappings are accurate
   // FIXME: Support XF and TF types
-  QualType NewTy;
-  switch (DestWidth) {
-  case 0:
+  if (!DestWidth) {
     S.Diag(Attr.getLoc(), diag::err_unknown_machine_mode) << Name;
     return;
-  default:
+  }
+
+  QualType NewTy;
+
+  if (IntegerMode)
+    NewTy = S.Context.getIntTypeForBitwidth(DestWidth,
+                                            OldTy->isSignedIntegerType());
+  else
+    NewTy = S.Context.getRealTypeForBitwidth(DestWidth);
+
+  if (NewTy.isNull()) {
     S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name;
     return;
-  case 8:
-    if (!IntegerMode) {
-      S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name;
-      return;
-    }
-    if (OldTy->isSignedIntegerType())
-      NewTy = S.Context.SignedCharTy;
-    else
-      NewTy = S.Context.UnsignedCharTy;
-    break;
-  case 16:
-    if (!IntegerMode) {
-      S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name;
-      return;
-    }
-    if (OldTy->isSignedIntegerType())
-      NewTy = S.Context.ShortTy;
-    else
-      NewTy = S.Context.UnsignedShortTy;
-    break;
-  case 32:
-    if (!IntegerMode)
-      NewTy = S.Context.FloatTy;
-    else if (OldTy->isSignedIntegerType())
-      NewTy = S.Context.IntTy;
-    else
-      NewTy = S.Context.UnsignedIntTy;
-    break;
-  case 64:
-    if (!IntegerMode)
-      NewTy = S.Context.DoubleTy;
-    else if (OldTy->isSignedIntegerType())
-      if (S.Context.getTargetInfo().getLongWidth() == 64)
-        NewTy = S.Context.LongTy;
-      else
-        NewTy = S.Context.LongLongTy;
-    else
-      if (S.Context.getTargetInfo().getLongWidth() == 64)
-        NewTy = S.Context.UnsignedLongTy;
-      else
-        NewTy = S.Context.UnsignedLongLongTy;
-    break;
-  case 96:
-    NewTy = S.Context.LongDoubleTy;
-    break;
-  case 128:
-    if (!IntegerMode && &S.Context.getTargetInfo().getLongDoubleFormat() !=
-        &llvm::APFloat::PPCDoubleDouble) {
-      S.Diag(Attr.getLoc(), diag::err_unsupported_machine_mode) << Name;
-      return;
-    }
-    if (IntegerMode) {
-      if (OldTy->isSignedIntegerType())
-        NewTy = S.Context.Int128Ty;
-      else
-        NewTy = S.Context.UnsignedInt128Ty;
-    } else
-      NewTy = S.Context.LongDoubleTy;
-    break;
   }
 
   if (ComplexMode) {
index f74916db94eb32779b835f980786f82bebac5408..49e41d210d035c865016706c1605a1140e9ab7f9 100644 (file)
@@ -27,7 +27,10 @@ int **__attribute((mode(QI)))* i32;  // expected-error{{mode attribute}}
 typedef _Complex double c32 __attribute((mode(SC)));
 int c32_test[sizeof(c32) == 8 ? 1 : -1];
 typedef _Complex float c64 __attribute((mode(DC)));
+
+#ifndef TEST_64BIT_PPC64 // Note, 'XC' mode is illegal for PPC64 machines.
 typedef _Complex float c80 __attribute((mode(XC)));
+#endif
 
 // PR6108: Correctly select 'long' built in type on 64-bit platforms for 64 bit
 // modes. Also test other mode-based conversions.