[cfe-commits] r128159 - in /cfe/trunk: include/clang/Sema/Overload.h lib/Sema/SemaExprCXX.cpp lib/Sema/SemaOverload.cpp test/Sema/overloaded-func-transparent-union.c

Fariborz Jahanian fjahanian at apple.com
Wed Mar 23 12:50:54 PDT 2011


Author: fjahanian
Date: Wed Mar 23 14:50:54 2011
New Revision: 128159

URL: http://llvm.org/viewvc/llvm-project?rev=128159&view=rev
Log:
Support for Transparent unions used as overloadable
function parameter. // rdar:// 9129552
and PR9406.

Added:
    cfe/trunk/test/Sema/overloaded-func-transparent-union.c
Modified:
    cfe/trunk/include/clang/Sema/Overload.h
    cfe/trunk/lib/Sema/SemaExprCXX.cpp
    cfe/trunk/lib/Sema/SemaOverload.cpp

Modified: cfe/trunk/include/clang/Sema/Overload.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Sema/Overload.h?rev=128159&r1=128158&r2=128159&view=diff
==============================================================================
--- cfe/trunk/include/clang/Sema/Overload.h (original)
+++ cfe/trunk/include/clang/Sema/Overload.h Wed Mar 23 14:50:54 2011
@@ -76,6 +76,7 @@
     ICK_Vector_Splat,          ///< A vector splat from an arithmetic type
     ICK_Complex_Real,          ///< Complex-real conversions (C99 6.3.1.7)
     ICK_Block_Pointer_Conversion,    ///< Block Pointer conversions 
+    ICK_TransparentUnionConversion, /// Transparent Union Conversions
     ICK_Num_Conversion_Kinds   ///< The number of conversion kinds
   };
 

Modified: cfe/trunk/lib/Sema/SemaExprCXX.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExprCXX.cpp?rev=128159&r1=128158&r2=128159&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaExprCXX.cpp (original)
+++ cfe/trunk/lib/Sema/SemaExprCXX.cpp Wed Mar 23 14:50:54 2011
@@ -2277,6 +2277,15 @@
       break;
     }
       
+  case ICK_TransparentUnionConversion: {
+    Sema::AssignConvertType ConvTy =
+      CheckTransparentUnionArgumentConstraints(ToType, From);
+    assert ((ConvTy == Sema::Compatible) &&
+            "Improper transparent union conversion");
+    (void)ConvTy;
+    break;
+  }
+
   case ICK_Lvalue_To_Rvalue:
   case ICK_Array_To_Pointer:
   case ICK_Function_To_Pointer:

Modified: cfe/trunk/lib/Sema/SemaOverload.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaOverload.cpp?rev=128159&r1=128158&r2=128159&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaOverload.cpp (original)
+++ cfe/trunk/lib/Sema/SemaOverload.cpp Wed Mar 23 14:50:54 2011
@@ -48,6 +48,12 @@
                                  bool InOverloadResolution,
                                  StandardConversionSequence &SCS,
                                  bool CStyle);
+  
+static bool IsTransparentUnionStandardConversion(Sema &S, Expr* From, 
+                                                 QualType &ToType,
+                                                 bool InOverloadResolution,
+                                                 StandardConversionSequence &SCS,
+                                                 bool CStyle);
 static OverloadingResult
 IsUserDefinedConversion(Sema &S, Expr *From, QualType ToType,
                         UserDefinedConversionSequence& User,
@@ -128,7 +134,9 @@
     ICR_Conversion,
     ICR_Conversion,
     ICR_Conversion,
-    ICR_Complex_Real_Conversion
+    ICR_Complex_Real_Conversion,
+    ICR_Conversion,
+    ICR_Conversion
   };
   return Rank[(int)Kind];
 }
@@ -157,7 +165,9 @@
     "Derived-to-base conversion",
     "Vector conversion",
     "Vector splat",
-    "Complex-real conversion"
+    "Complex-real conversion",
+    "Block Pointer conversion",
+    "Transparent Union Conversion"
   };
   return Name[Kind];
 }
@@ -1203,6 +1213,11 @@
   } else if (IsNoReturnConversion(S.Context, FromType, ToType, FromType)) {
     // Treat a conversion that strips "noreturn" as an identity conversion.
     SCS.Second = ICK_NoReturn_Adjustment;
+  } else if (IsTransparentUnionStandardConversion(S, From, ToType,
+                                             InOverloadResolution,
+                                             SCS, CStyle)) {
+    SCS.Second = ICK_TransparentUnionConversion;
+    FromType = ToType;
   } else {
     // No second conversion required.
     SCS.Second = ICK_Identity;
@@ -1244,6 +1259,30 @@
 
   return true;
 }
+  
+static bool
+IsTransparentUnionStandardConversion(Sema &S, Expr* From, 
+                                     QualType &ToType,
+                                     bool InOverloadResolution,
+                                     StandardConversionSequence &SCS,
+                                     bool CStyle) {
+    
+  const RecordType *UT = ToType->getAsUnionType();
+  if (!UT || !UT->getDecl()->hasAttr<TransparentUnionAttr>())
+    return false;
+  // The field to initialize within the transparent union.
+  RecordDecl *UD = UT->getDecl();
+  // It's compatible if the expression matches any of the fields.
+  for (RecordDecl::field_iterator it = UD->field_begin(),
+       itend = UD->field_end();
+       it != itend; ++it) {
+    if (IsStandardConversion(S, From, it->getType(), InOverloadResolution, SCS, CStyle)) {
+      ToType = it->getType();
+      return true;
+    }
+  }
+  return false;
+}
 
 /// IsIntegralPromotion - Determines whether the conversion from the
 /// expression From (whose potentially-adjusted type is FromType) to

Added: cfe/trunk/test/Sema/overloaded-func-transparent-union.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Sema/overloaded-func-transparent-union.c?rev=128159&view=auto
==============================================================================
--- cfe/trunk/test/Sema/overloaded-func-transparent-union.c (added)
+++ cfe/trunk/test/Sema/overloaded-func-transparent-union.c Wed Mar 23 14:50:54 2011
@@ -0,0 +1,28 @@
+// RUN: %clang_cc1 %s -fsyntax-only -verify
+// rdar:// 9129552
+// PR9406
+
+typedef struct {
+	char *str;
+	char *str2;
+} Class;
+
+typedef union {
+	Class *object;
+} Instance __attribute__((transparent_union));
+
+__attribute__((overloadable)) void Class_Init(Instance this, char *str, void *str2) {
+	this.object->str  = str;
+	this.object->str2 = str2;
+}
+
+__attribute__((overloadable)) void Class_Init(Instance this, char *str) {
+	this.object->str  = str;
+	this.object->str2 = str;
+}
+
+int main(void) {
+	Class obj;
+	Class_Init(&obj, "Hello ", " World");
+}
+





More information about the cfe-commits mailing list