<div dir="ltr">Hi Rafael,<div><br></div><div>This change causes a Clang crash when using LTO and building the test-suite tools, which completely breaks testing with LTO. Can you take a look?</div><div><br></div><div>--</div>
<div style>$ cd ~/llvm-test-suite/tools</div><div style><br></div><div style>$ clang-r180193-t20130424_085843-b4726/bin/clang -v<br></div><div>clang version 3.3 (trunk 180193)</div><div>Target: x86_64-apple-darwin10.7.0</div>
<div>Thread model: posix</div><div><div><br></div><div>$ env DYLD_LIBRARY_PATH=$(pwd)/clang-r180193-t20130424_085843-b4726/lib clang-r180193-t20130424_085843-b4726/bin/clang -flto -Os timeit.c Assertion failed: (isa<X>(Val) && "cast<Ty>() argument of incompatible type!"), function cast, file /Users/buildslave/zorg/buildbot/smooshlab/slave-0.8/build.clang-x86_64-darwin10-RA/llvm/include/llvm/Support/Casting.h, line 237.</div>
<div>Stack dump:</div><div>0.<span class="" style="white-space:pre">        </span>Running pass 'Merge Duplicate Global Constants' on module 'ld-temp.o'.</div><div>clang: error: unable to execute command: Illegal instruction</div>
<div>clang: error: linker command failed due to signal (use -v to see invocation)</div></div><div>--</div><div><br></div><div style> - Daniel</div><div style><br></div></div><div class="gmail_extra"><br><br><div class="gmail_quote">
On Mon, Apr 22, 2013 at 7:58 AM, Rafael Espindola <span dir="ltr"><<a href="mailto:rafael.espindola@gmail.com" target="_blank">rafael.espindola@gmail.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
Author: rafael<br>
Date: Mon Apr 22 09:58:02 2013<br>
New Revision: 180019<br>
<br>
URL: <a href="http://llvm.org/viewvc/llvm-project?rev=180019&view=rev" target="_blank">http://llvm.org/viewvc/llvm-project?rev=180019&view=rev</a><br>
Log:<br>
Clarify that llvm.used can contain aliases.<br>
<br>
Also add a check for llvm.used in the verifier and simplify clients now that<br>
they can assume they have a ConstantArray.<br>
<br>
Added:<br>
    llvm/trunk/test/Verifier/llvm.used-invalid-init.ll<br>
    llvm/trunk/test/Verifier/llvm.used-invalid-init2.ll<br>
    llvm/trunk/test/Verifier/llvm.used-invalid-type.ll<br>
    llvm/trunk/test/Verifier/llvm.used-invalid-type2.ll<br>
    llvm/trunk/test/Verifier/llvm.used-ptr-type.ll<br>
Modified:<br>
    llvm/trunk/docs/LangRef.rst<br>
    llvm/trunk/include/llvm/CodeGen/AsmPrinter.h<br>
    llvm/trunk/lib/CodeGen/AsmPrinter/AsmPrinter.cpp<br>
    llvm/trunk/lib/CodeGen/MachineModuleInfo.cpp<br>
    llvm/trunk/lib/IR/Verifier.cpp<br>
    llvm/trunk/lib/Transforms/IPO/ConstantMerge.cpp<br>
    llvm/trunk/lib/Transforms/IPO/StripSymbols.cpp<br>
    llvm/trunk/lib/Transforms/Scalar/GlobalMerge.cpp<br>
    llvm/trunk/test/Feature/aliases.ll<br>
<br>
Modified: llvm/trunk/docs/LangRef.rst<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/LangRef.rst?rev=180019&r1=180018&r2=180019&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/docs/LangRef.rst?rev=180019&r1=180018&r2=180019&view=diff</a><br>

==============================================================================<br>
--- llvm/trunk/docs/LangRef.rst (original)<br>
+++ llvm/trunk/docs/LangRef.rst Mon Apr 22 09:58:02 2013<br>
@@ -2868,9 +2868,9 @@ All globals of this sort should have a s<br>
 The '``llvm.used``' Global Variable<br>
 -----------------------------------<br>
<br>
-The ``@llvm.used`` global is an array with i8\* element type which has<br>
-:ref:`appending linkage <linkage_appending>`. This array contains a list of<br>
-pointers to global variables and functions which may optionally have a<br>
+The ``@llvm.used`` global is an array which has<br>
+ :ref:`appending linkage <linkage_appending>`. This array contains a list of<br>
+pointers to global variables, functions and aliases which may optionally have a<br>
 pointer cast formed of bitcast or getelementptr. For example, a legal<br>
 use of it is:<br>
<br>
@@ -2884,13 +2884,13 @@ use of it is:<br>
        i8* bitcast (i32* @Y to i8*)<br>
     ], section "llvm.metadata"<br>
<br>
-If a global variable appears in the ``@llvm.used`` list, then the<br>
-compiler, assembler, and linker are required to treat the symbol as if<br>
-there is a reference to the global that it cannot see. For example, if a<br>
-variable has internal linkage and no references other than that from the<br>
-``@llvm.used`` list, it cannot be deleted. This is commonly used to<br>
-represent references from inline asms and other things the compiler<br>
-cannot "see", and corresponds to "``attribute((used))``" in GNU C.<br>
+If a symbol appears in the ``@llvm.used`` list, then the compiler, assembler,<br>
+and linker are required to treat the symbol as if there is a reference to the<br>
+symbol that it cannot see. For example, if a variable has internal linkage and<br>
+no references other than that from the ``@llvm.used`` list, it cannot be<br>
+deleted. This is commonly used to represent references from inline asms and<br>
+other things the compiler cannot "see", and corresponds to<br>
+"``attribute((used))``" in GNU C.<br>
<br>
 On some targets, the code generator must emit a directive to the<br>
 assembler or object file to prevent the assembler and linker from<br>
<br>
Modified: llvm/trunk/include/llvm/CodeGen/AsmPrinter.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/CodeGen/AsmPrinter.h?rev=180019&r1=180018&r2=180019&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/CodeGen/AsmPrinter.h?rev=180019&r1=180018&r2=180019&view=diff</a><br>

==============================================================================<br>
--- llvm/trunk/include/llvm/CodeGen/AsmPrinter.h (original)<br>
+++ llvm/trunk/include/llvm/CodeGen/AsmPrinter.h Mon Apr 22 09:58:02 2013<br>
@@ -25,6 +25,7 @@ namespace llvm {<br>
   class BlockAddress;<br>
   class GCStrategy;<br>
   class Constant;<br>
+  class ConstantArray;<br>
   class GCMetadataPrinter;<br>
   class GlobalValue;<br>
   class GlobalVariable;<br>
@@ -480,7 +481,7 @@ namespace llvm {<br>
     void EmitJumpTableEntry(const MachineJumpTableInfo *MJTI,<br>
                             const MachineBasicBlock *MBB,<br>
                             unsigned uid) const;<br>
-    void EmitLLVMUsedList(const Constant *List);<br>
+    void EmitLLVMUsedList(const ConstantArray *InitList);<br>
     void EmitXXStructorList(const Constant *List, bool isCtor);<br>
     GCMetadataPrinter *GetOrCreateGCPrinter(GCStrategy *C);<br>
   };<br>
<br>
Modified: llvm/trunk/lib/CodeGen/AsmPrinter/AsmPrinter.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/AsmPrinter/AsmPrinter.cpp?rev=180019&r1=180018&r2=180019&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/AsmPrinter/AsmPrinter.cpp?rev=180019&r1=180018&r2=180019&view=diff</a><br>

==============================================================================<br>
--- llvm/trunk/lib/CodeGen/AsmPrinter/AsmPrinter.cpp (original)<br>
+++ llvm/trunk/lib/CodeGen/AsmPrinter/AsmPrinter.cpp Mon Apr 22 09:58:02 2013<br>
@@ -1213,7 +1213,7 @@ void AsmPrinter::EmitJumpTableEntry(cons<br>
 bool AsmPrinter::EmitSpecialLLVMGlobal(const GlobalVariable *GV) {<br>
   if (GV->getName() == "llvm.used") {<br>
     if (MAI->hasNoDeadStrip())    // No need to emit this at all.<br>
-      EmitLLVMUsedList(GV->getInitializer());<br>
+      EmitLLVMUsedList(cast<ConstantArray>(GV->getInitializer()));<br>
     return true;<br>
   }<br>
<br>
@@ -1256,11 +1256,8 @@ bool AsmPrinter::EmitSpecialLLVMGlobal(c<br>
 /// EmitLLVMUsedList - For targets that define a MAI::UsedDirective, mark each<br>
 /// global in the specified llvm.used list for which emitUsedDirectiveFor<br>
 /// is true, as being used with this directive.<br>
-void AsmPrinter::EmitLLVMUsedList(const Constant *List) {<br>
+void AsmPrinter::EmitLLVMUsedList(const ConstantArray *InitList) {<br>
   // Should be an array of 'i8*'.<br>
-  const ConstantArray *InitList = dyn_cast<ConstantArray>(List);<br>
-  if (InitList == 0) return;<br>
-<br>
   for (unsigned i = 0, e = InitList->getNumOperands(); i != e; ++i) {<br>
     const GlobalValue *GV =<br>
       dyn_cast<GlobalValue>(InitList->getOperand(i)->stripPointerCasts());<br>
<br>
Modified: llvm/trunk/lib/CodeGen/MachineModuleInfo.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/MachineModuleInfo.cpp?rev=180019&r1=180018&r2=180019&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/MachineModuleInfo.cpp?rev=180019&r1=180018&r2=180019&view=diff</a><br>

==============================================================================<br>
--- llvm/trunk/lib/CodeGen/MachineModuleInfo.cpp (original)<br>
+++ llvm/trunk/lib/CodeGen/MachineModuleInfo.cpp Mon Apr 22 09:58:02 2013<br>
@@ -326,8 +326,7 @@ void MachineModuleInfo::AnalyzeModule(co<br>
   if (!GV || !GV->hasInitializer()) return;<br>
<br>
   // Should be an array of 'i8*'.<br>
-  const ConstantArray *InitList = dyn_cast<ConstantArray>(GV->getInitializer());<br>
-  if (InitList == 0) return;<br>
+  const ConstantArray *InitList = cast<ConstantArray>(GV->getInitializer());<br>
<br>
   for (unsigned i = 0, e = InitList->getNumOperands(); i != e; ++i)<br>
     if (const Function *F =<br>
<br>
Modified: llvm/trunk/lib/IR/Verifier.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/IR/Verifier.cpp?rev=180019&r1=180018&r2=180019&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/IR/Verifier.cpp?rev=180019&r1=180018&r2=180019&view=diff</a><br>

==============================================================================<br>
--- llvm/trunk/lib/IR/Verifier.cpp (original)<br>
+++ llvm/trunk/lib/IR/Verifier.cpp Mon Apr 22 09:58:02 2013<br>
@@ -449,6 +449,29 @@ void Verifier::visitGlobalVariable(Globa<br>
     }<br>
   }<br>
<br>
+  if (GV.hasName() && (GV.getName() == "llvm.used")) {<br>
+    Assert1(!GV.hasInitializer() || GV.hasAppendingLinkage(),<br>
+            "invalid linkage for intrinsic global variable", &GV);<br>
+    Type *GVType = GV.getType()->getElementType();<br>
+    if (ArrayType *ATy = dyn_cast<ArrayType>(GVType)) {<br>
+      PointerType *PTy = dyn_cast<PointerType>(ATy->getElementType());<br>
+      Assert1(PTy, "wrong type for intrinsic global variable", &GV);<br>
+      if (GV.hasInitializer()) {<br>
+        Constant *Init = GV.getInitializer();<br>
+        ConstantArray *InitArray = dyn_cast<ConstantArray>(Init);<br>
+        Assert1(InitArray, "wrong initalizer for intrinsic global variable",<br>
+                Init);<br>
+        for (unsigned i = 0, e = InitArray->getNumOperands(); i != e; ++i) {<br>
+          Value *V = Init->getOperand(i)->stripPointerCasts();<br>
+          // stripPointerCasts strips aliases, so we only need to check for<br>
+          // variables and functions.<br>
+          Assert1(isa<GlobalVariable>(V) || isa<Function>(V),<br>
+                  "invalid llvm.used member", V);<br>
+        }<br>
+      }<br>
+    }<br>
+  }<br>
+<br>
   visitGlobalValue(GV);<br>
 }<br>
<br>
<br>
Modified: llvm/trunk/lib/Transforms/IPO/ConstantMerge.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/IPO/ConstantMerge.cpp?rev=180019&r1=180018&r2=180019&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/IPO/ConstantMerge.cpp?rev=180019&r1=180018&r2=180019&view=diff</a><br>

==============================================================================<br>
--- llvm/trunk/lib/Transforms/IPO/ConstantMerge.cpp (original)<br>
+++ llvm/trunk/lib/Transforms/IPO/ConstantMerge.cpp Mon Apr 22 09:58:02 2013<br>
@@ -66,9 +66,8 @@ ModulePass *llvm::createConstantMergePas<br>
 static void FindUsedValues(GlobalVariable *LLVMUsed,<br>
                            SmallPtrSet<const GlobalValue*, 8> &UsedValues) {<br>
   if (LLVMUsed == 0) return;<br>
-  ConstantArray *Inits = dyn_cast<ConstantArray>(LLVMUsed->getInitializer());<br>
-  if (Inits == 0) return;<br>
-<br>
+  ConstantArray *Inits = cast<ConstantArray>(LLVMUsed->getInitializer());<br>
+<br>
   for (unsigned i = 0, e = Inits->getNumOperands(); i != e; ++i)<br>
     if (GlobalValue *GV =<br>
         dyn_cast<GlobalValue>(Inits->getOperand(i)->stripPointerCasts()))<br>
<br>
Modified: llvm/trunk/lib/Transforms/IPO/StripSymbols.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/IPO/StripSymbols.cpp?rev=180019&r1=180018&r2=180019&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/IPO/StripSymbols.cpp?rev=180019&r1=180018&r2=180019&view=diff</a><br>

==============================================================================<br>
--- llvm/trunk/lib/Transforms/IPO/StripSymbols.cpp (original)<br>
+++ llvm/trunk/lib/Transforms/IPO/StripSymbols.cpp Mon Apr 22 09:58:02 2013<br>
@@ -195,10 +195,9 @@ static void findUsedValues(GlobalVariabl<br>
                            SmallPtrSet<const GlobalValue*, 8> &UsedValues) {<br>
   if (LLVMUsed == 0) return;<br>
   UsedValues.insert(LLVMUsed);<br>
-<br>
-  ConstantArray *Inits = dyn_cast<ConstantArray>(LLVMUsed->getInitializer());<br>
-  if (Inits == 0) return;<br>
-<br>
+<br>
+  ConstantArray *Inits = cast<ConstantArray>(LLVMUsed->getInitializer());<br>
+<br>
   for (unsigned i = 0, e = Inits->getNumOperands(); i != e; ++i)<br>
     if (GlobalValue *GV =<br>
           dyn_cast<GlobalValue>(Inits->getOperand(i)->stripPointerCasts()))<br>
<br>
Modified: llvm/trunk/lib/Transforms/Scalar/GlobalMerge.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/Scalar/GlobalMerge.cpp?rev=180019&r1=180018&r2=180019&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/Scalar/GlobalMerge.cpp?rev=180019&r1=180018&r2=180019&view=diff</a><br>

==============================================================================<br>
--- llvm/trunk/lib/Transforms/Scalar/GlobalMerge.cpp (original)<br>
+++ llvm/trunk/lib/Transforms/Scalar/GlobalMerge.cpp Mon Apr 22 09:58:02 2013<br>
@@ -200,9 +200,8 @@ void GlobalMerge::collectUsedGlobalVaria<br>
   if (!GV || !GV->hasInitializer()) return;<br>
<br>
   // Should be an array of 'i8*'.<br>
-  const ConstantArray *InitList = dyn_cast<ConstantArray>(GV->getInitializer());<br>
-  if (InitList == 0) return;<br>
-<br>
+  const ConstantArray *InitList = cast<ConstantArray>(GV->getInitializer());<br>
+<br>
   for (unsigned i = 0, e = InitList->getNumOperands(); i != e; ++i)<br>
     if (const GlobalVariable *G =<br>
         dyn_cast<GlobalVariable>(InitList->getOperand(i)->stripPointerCasts()))<br>
<br>
Modified: llvm/trunk/test/Feature/aliases.ll<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Feature/aliases.ll?rev=180019&r1=180018&r2=180019&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Feature/aliases.ll?rev=180019&r1=180018&r2=180019&view=diff</a><br>

==============================================================================<br>
--- llvm/trunk/test/Feature/aliases.ll (original)<br>
+++ llvm/trunk/test/Feature/aliases.ll Mon Apr 22 09:58:02 2013<br>
@@ -2,6 +2,8 @@<br>
 ; RUN: llvm-as %t1.ll -o - | llvm-dis > %t2.ll<br>
 ; RUN: diff %t1.ll %t2.ll<br>
<br>
+@llvm.used = appending global [1 x i8*] [i8* bitcast (i32* @foo1 to i8*)], section "llvm.metadata"<br>
+<br>
 @bar = external global i32<br>
 @foo1 = alias i32* @bar<br>
 @foo2 = alias i32* @bar<br>
<br>
Added: llvm/trunk/test/Verifier/llvm.used-invalid-init.ll<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Verifier/llvm.used-invalid-init.ll?rev=180019&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Verifier/llvm.used-invalid-init.ll?rev=180019&view=auto</a><br>

==============================================================================<br>
--- llvm/trunk/test/Verifier/llvm.used-invalid-init.ll (added)<br>
+++ llvm/trunk/test/Verifier/llvm.used-invalid-init.ll Mon Apr 22 09:58:02 2013<br>
@@ -0,0 +1,6 @@<br>
+; RUN: not llvm-as < %s -o /dev/null 2>&1 | FileCheck %s<br>
+<br>
+@llvm.used = appending global [1 x i8*] zeroinitializer, section "llvm.metadata"<br>
+<br>
+; CHECK: wrong initalizer for intrinsic global variable<br>
+; CHECK-NEXT: [1 x i8*] zeroinitializer<br>
<br>
Added: llvm/trunk/test/Verifier/llvm.used-invalid-init2.ll<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Verifier/llvm.used-invalid-init2.ll?rev=180019&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Verifier/llvm.used-invalid-init2.ll?rev=180019&view=auto</a><br>

==============================================================================<br>
--- llvm/trunk/test/Verifier/llvm.used-invalid-init2.ll (added)<br>
+++ llvm/trunk/test/Verifier/llvm.used-invalid-init2.ll Mon Apr 22 09:58:02 2013<br>
@@ -0,0 +1,7 @@<br>
+; RUN: not llvm-as < %s -o /dev/null 2>&1 | FileCheck %s<br>
+<br>
+@a = global i8 42<br>
+@llvm.used = appending global [2 x i8*] [i8* @a, i8* null], section "llvm.metadata"<br>
+<br>
+; CHECK: invalid llvm.used member<br>
+; CHECK-NEXT: i8* null<br>
<br>
Added: llvm/trunk/test/Verifier/llvm.used-invalid-type.ll<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Verifier/llvm.used-invalid-type.ll?rev=180019&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Verifier/llvm.used-invalid-type.ll?rev=180019&view=auto</a><br>

==============================================================================<br>
--- llvm/trunk/test/Verifier/llvm.used-invalid-type.ll (added)<br>
+++ llvm/trunk/test/Verifier/llvm.used-invalid-type.ll Mon Apr 22 09:58:02 2013<br>
@@ -0,0 +1,6 @@<br>
+; RUN: not llvm-as < %s -o /dev/null 2>&1 | FileCheck %s<br>
+<br>
+@llvm.used = appending global [1 x i32] [i32 0], section "llvm.metadata"<br>
+<br>
+; CHECK:       wrong type for intrinsic global variable<br>
+; CHECK-NEXT: [1 x i32]* @llvm.used<br>
<br>
Added: llvm/trunk/test/Verifier/llvm.used-invalid-type2.ll<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Verifier/llvm.used-invalid-type2.ll?rev=180019&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Verifier/llvm.used-invalid-type2.ll?rev=180019&view=auto</a><br>

==============================================================================<br>
--- llvm/trunk/test/Verifier/llvm.used-invalid-type2.ll (added)<br>
+++ llvm/trunk/test/Verifier/llvm.used-invalid-type2.ll Mon Apr 22 09:58:02 2013<br>
@@ -0,0 +1,5 @@<br>
+; RUN: not llvm-as < %s -o /dev/null 2>&1 | FileCheck %s<br>
+@llvm.used = appending global i32 0, section "llvm.metadata"<br>
+<br>
+; CHECK: Only global arrays can have appending linkage!<br>
+; CHEKC-NEXT: i32* @llvm.used<br>
<br>
Added: llvm/trunk/test/Verifier/llvm.used-ptr-type.ll<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Verifier/llvm.used-ptr-type.ll?rev=180019&view=auto" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Verifier/llvm.used-ptr-type.ll?rev=180019&view=auto</a><br>

==============================================================================<br>
--- llvm/trunk/test/Verifier/llvm.used-ptr-type.ll (added)<br>
+++ llvm/trunk/test/Verifier/llvm.used-ptr-type.ll Mon Apr 22 09:58:02 2013<br>
@@ -0,0 +1,4 @@<br>
+; RUN: llvm-as < %s -o /dev/null<br>
+<br>
+@a = global i32 42<br>
+@llvm.used = appending global [1 x i32*] [i32* @a], section "llvm.metadata"<br>
<br>
<br>
_______________________________________________<br>
llvm-commits mailing list<br>
<a href="mailto:llvm-commits@cs.uiuc.edu">llvm-commits@cs.uiuc.edu</a><br>
<a href="http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits" target="_blank">http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits</a><br>
</blockquote></div><br></div>