Eliminate the restriction that the array size in an alloca must be i32.
authorDan Gohman <gohman@apple.com>
Fri, 28 May 2010 01:14:11 +0000 (01:14 +0000)
committerDan Gohman <gohman@apple.com>
Fri, 28 May 2010 01:14:11 +0000 (01:14 +0000)
This will help reduce the amount of casting required on 64-bit targets.

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

docs/LangRef.html
lib/AsmParser/LLParser.cpp
lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp
lib/VMCore/Instructions.cpp
lib/VMCore/Verifier.cpp
test/CodeGen/X86/alloca-align-rounding-32.ll [new file with mode: 0644]
test/CodeGen/X86/alloca-align-rounding.ll

index 4b1919adf0348665b9d1067fd4db31afcaac3ec8..bfb4256973f2d4598b806465ba2a942432db1d44 100644 (file)
@@ -4239,7 +4239,7 @@ Instruction</a> </div>
 
 <h5>Syntax:</h5>
 <pre>
-  &lt;result&gt; = alloca &lt;type&gt;[, i32 &lt;NumElements&gt;][, align &lt;alignment&gt;]     <i>; yields {type*}:result</i>
+  &lt;result&gt; = alloca &lt;type&gt;[, &lt;ty&gt; &lt;NumElements&gt;][, align &lt;alignment&gt;]     <i>; yields {type*}:result</i>
 </pre>
 
 <h5>Overview:</h5>
index 226d8d3272987addf4425937b7a7ed60395bd25d..1cd66e536ea788c990114aec04698b0a54b182ed 100644 (file)
@@ -3791,8 +3791,8 @@ int LLParser::ParseAlloc(Instruction *&Inst, PerFunctionState &PFS,
     }
   }
 
-  if (Size && !Size->getType()->isIntegerTy(32))
-    return Error(SizeLoc, "element count must be i32");
+  if (Size && !Size->getType()->isIntegerTy())
+    return Error(SizeLoc, "element count must have integer type");
 
   if (isAlloca) {
     Inst = new AllocaInst(Ty, Size, Alignment);
@@ -3801,6 +3801,8 @@ int LLParser::ParseAlloc(Instruction *&Inst, PerFunctionState &PFS,
 
   // Autoupgrade old malloc instruction to malloc call.
   // FIXME: Remove in LLVM 3.0.
+  if (Size && !Size->getType()->isIntegerTy(32))
+    return Error(SizeLoc, "element count must be i32");
   const Type *IntPtrTy = Type::getInt32Ty(Context);
   Constant *AllocSize = ConstantExpr::getSizeOf(Ty);
   AllocSize = ConstantExpr::getTruncOrBitCast(AllocSize, IntPtrTy);
index fbe601f2db09ec338fea20dd9f305e3fb5a47525..90ad7f71f78f4d8515e3b79712ade651af2156dc 100644 (file)
@@ -2643,12 +2643,13 @@ void SelectionDAGBuilder::visitAlloca(const AllocaInst &I) {
 
   SDValue AllocSize = getValue(I.getArraySize());
 
-  AllocSize = DAG.getNode(ISD::MUL, getCurDebugLoc(), AllocSize.getValueType(),
-                          AllocSize,
-                          DAG.getConstant(TySize, AllocSize.getValueType()));
-
   EVT IntPtr = TLI.getPointerTy();
-  AllocSize = DAG.getZExtOrTrunc(AllocSize, getCurDebugLoc(), IntPtr);
+  if (AllocSize.getValueType() != IntPtr)
+    AllocSize = DAG.getZExtOrTrunc(AllocSize, getCurDebugLoc(), IntPtr);
+
+  AllocSize = DAG.getNode(ISD::MUL, getCurDebugLoc(), IntPtr,
+                          AllocSize,
+                          DAG.getConstant(TySize, IntPtr));
 
   // Handle alignment.  If the requested alignment is less than or equal to
   // the stack alignment, ignore it.  If the size is greater than or equal to
index f64b220c3fde3e733158d6abca458a22989158bd..3060a7601d00eec7d045ce300ab538213d88da34 100644 (file)
@@ -828,8 +828,8 @@ static Value *getAISize(LLVMContext &Context, Value *Amt) {
   else {
     assert(!isa<BasicBlock>(Amt) &&
            "Passed basic block into allocation size parameter! Use other ctor");
-    assert(Amt->getType()->isIntegerTy(32) &&
-           "Allocation array size is not a 32-bit integer!");
+    assert(Amt->getType()->isIntegerTy() &&
+           "Allocation array size is not an integer!");
   }
   return Amt;
 }
index 75988cca72c8896452198dd10964b9ff3669f03f..4ff03dbe9f8647753cc794d91f5808289d447e4f 100644 (file)
@@ -1371,8 +1371,8 @@ void Verifier::visitAllocaInst(AllocaInst &AI) {
           &AI);
   Assert1(PTy->getElementType()->isSized(), "Cannot allocate unsized type",
           &AI);
-  Assert1(AI.getArraySize()->getType()->isIntegerTy(32),
-          "Alloca array size must be i32", &AI);
+  Assert1(AI.getArraySize()->getType()->isIntegerTy(),
+          "Alloca array size must have integer type", &AI);
   visitInstruction(AI);
 }
 
diff --git a/test/CodeGen/X86/alloca-align-rounding-32.ll b/test/CodeGen/X86/alloca-align-rounding-32.ll
new file mode 100644 (file)
index 0000000..c0f1a18
--- /dev/null
@@ -0,0 +1,15 @@
+; RUN: llc < %s -march=x86 -mtriple=i686-apple-darwin | grep and | count 1
+
+declare void @bar(<2 x i64>* %n)
+
+define void @foo(i32 %h) {
+  %p = alloca <2 x i64>, i32 %h
+  call void @bar(<2 x i64>* %p)
+  ret void
+}
+
+define void @foo2(i32 %h) {
+  %p = alloca <2 x i64>, i32 %h, align 32
+  call void @bar(<2 x i64>* %p)
+  ret void
+}
index f45e9b84b2640562b143a73599a349427603ca54..3c87dbf2bd78b2e1d8b6283bd3d4dc1f09f1b929 100644 (file)
@@ -1,16 +1,15 @@
-; RUN: llc < %s -march=x86 -mtriple=i686-apple-darwin | grep and | count 1
 ; RUN: llc < %s -march=x86-64 -mtriple=i686-pc-linux | grep and | count 1
 
 declare void @bar(<2 x i64>* %n)
 
-define void @foo(i32 %h) {
-  %p = alloca <2 x i64>, i32 %h
+define void @foo(i64 %h) {
+  %p = alloca <2 x i64>, i64 %h
   call void @bar(<2 x i64>* %p)
   ret void
 }
 
-define void @foo2(i32 %h) {
-  %p = alloca <2 x i64>, i32 %h, align 32
+define void @foo2(i64 %h) {
+  %p = alloca <2 x i64>, i64 %h, align 32
   call void @bar(<2 x i64>* %p)
   ret void
 }