<div dir="ltr">Hi,<div>Please find the patch for incorrect ABI in case we have a union argument passed by value.</div><div><br></div><div>Index: test/CodeGen/transparent-union.c<br></div><div><div>===================================================================</div>
<div>--- test/CodeGen/transparent-union.c<span class="" style="white-space:pre">        </span>(revision 188794)</div><div>+++ test/CodeGen/transparent-union.c<span class="" style="white-space:pre">      </span>(working copy)</div><div>
@@ -1,9 +1,7 @@</div><div> // RUN: %clang_cc1 -Werror -triple i386-unknown-unknown -emit-llvm -o %t %s</div><div> // RUN: FileCheck < %t %s</div><div>-//</div><div>-// FIXME: Note that we don't currently get the ABI right here. f0() should be</div>
<div>-// f0(i8*).</div><div> </div><div>+</div><div> typedef union {</div><div>   void *f0;</div><div> } transp_t0 __attribute__((transparent_union));</div><div>@@ -11,7 +9,7 @@</div><div> void f0(transp_t0 obj);</div><div>
 </div><div> // CHECK-LABEL: define void @f1_0(i32* %a0) </div><div>-// CHECK:  call void @f0(%union.transp_t0* byval align 4 %{{.*}})</div><div>+// CHECK:  call void @f0(i8* %{{.*}})</div><div> // CHECK:  call void %{{.*}}(i8* %{{[a-z0-9]*}})</div>
<div> // CHECK: }</div><div> void f1_0(int *a0) {</div><div>Index: lib/CodeGen/TargetInfo.cpp</div><div>===================================================================</div><div>--- lib/CodeGen/TargetInfo.cpp<span class="" style="white-space:pre">     </span>(revision 188794)</div>
<div>+++ lib/CodeGen/TargetInfo.cpp<span class="" style="white-space:pre">      </span>(working copy)</div><div>@@ -325,10 +325,11 @@</div><div>   //</div><div>   // FIXME: This needs to be generalized to handle classes as well.</div>
<div>   const RecordDecl *RD = RT->getDecl();</div><div>-  if (!RD->isStruct() || isa<CXXRecordDecl>(RD))</div><div>+  if (!(RD->isStruct() || RD->isUnion()) || isa<CXXRecordDecl>(RD))</div><div>     return false;</div>
<div> </div><div>   uint64_t Size = 0;</div><div>+  uint64_t CurrentElmtSize = 0;</div><div> </div><div>   for (RecordDecl::field_iterator i = RD->field_begin(), e = RD->field_end();</div><div>          i != e; ++i) {</div>
<div>@@ -343,7 +344,14 @@</div><div>     if (FD->isBitField())</div><div>       return false;</div><div> </div><div>+    if (!RD->isUnion())</div><div>     Size += Context.getTypeSize(FD->getType());</div><div>+    else {</div>
<div>+      //Size of union is size of it's largest element.</div><div>+      CurrentElmtSize = Context.getTypeSize(FD->getType());</div><div>+      if (CurrentElmtSize > Size)</div><div>+        Size = CurrentElmtSize;</div>
<div>+    }</div><div>   }</div><div> </div><div>   // Make sure there are not any holes in the struct.</div></div><div><br></div><div><br></div><div>Regards</div><div>Karthik Bhat</div>
</div>