summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMichael Kuperstein <mkuper@google.com>2016-12-21 18:29:47 +0000
committerMichael Kuperstein <mkuper@google.com>2016-12-21 18:29:47 +0000
commit88f15eedbbf49c88f4386e0400936b8874fd5717 (patch)
tree11d9754154f8ebe160c60bc3a38022c611c0ec16
parentdd92c78669da0c3e0c285b0723ee5ecba12ca1df (diff)
downloadbcm5719-llvm-88f15eedbbf49c88f4386e0400936b8874fd5717.tar.gz
bcm5719-llvm-88f15eedbbf49c88f4386e0400936b8874fd5717.zip
[LLParser] Parse vector GEP constant expression correctly
The constantexpr parsing was too constrained and rejected legal vector GEPs. This relaxes it to be similar to the ones for instruction parsing. This fixes PR30816. Differential Revision: https://reviews.llvm.org/D28013 llvm-svn: 290261
-rw-r--r--llvm/lib/AsmParser/LLParser.cpp11
-rw-r--r--llvm/test/Assembler/getelementptr_vec_ce.ll9
-rw-r--r--llvm/test/Assembler/getelementptr_vec_ce2.ll8
3 files changed, 24 insertions, 4 deletions
diff --git a/llvm/lib/AsmParser/LLParser.cpp b/llvm/lib/AsmParser/LLParser.cpp
index 712a2c6762d..d1891b7feb0 100644
--- a/llvm/lib/AsmParser/LLParser.cpp
+++ b/llvm/lib/AsmParser/LLParser.cpp
@@ -3193,20 +3193,23 @@ bool LLParser::ParseValID(ValID &ID, PerFunctionState *PFS) {
ExplicitTypeLoc,
"explicit pointee type doesn't match operand's pointee type");
+ unsigned GEPWidth =
+ BaseType->isVectorTy() ? BaseType->getVectorNumElements() : 0;
+
ArrayRef<Constant *> Indices(Elts.begin() + 1, Elts.end());
for (Constant *Val : Indices) {
Type *ValTy = Val->getType();
if (!ValTy->getScalarType()->isIntegerTy())
return Error(ID.Loc, "getelementptr index must be an integer");
- if (ValTy->isVectorTy() != BaseType->isVectorTy())
- return Error(ID.Loc, "getelementptr index type missmatch");
if (ValTy->isVectorTy()) {
unsigned ValNumEl = ValTy->getVectorNumElements();
- unsigned PtrNumEl = BaseType->getVectorNumElements();
- if (ValNumEl != PtrNumEl)
+ if (GEPWidth && (ValNumEl != GEPWidth))
return Error(
ID.Loc,
"getelementptr vector index has a wrong number of elements");
+ // GEPWidth may have been unknown because the base is a scalar,
+ // but it is known now.
+ GEPWidth = ValNumEl;
}
}
diff --git a/llvm/test/Assembler/getelementptr_vec_ce.ll b/llvm/test/Assembler/getelementptr_vec_ce.ll
new file mode 100644
index 00000000000..4cf2964a57f
--- /dev/null
+++ b/llvm/test/Assembler/getelementptr_vec_ce.ll
@@ -0,0 +1,9 @@
+; RUN: llvm-as < %s | llvm-dis | FileCheck %s
+
+@G = global [4 x i32] zeroinitializer
+
+; CHECK-LABEL: @foo
+; CHECK: ret <4 x i32*> getelementptr ([4 x i32], [4 x i32]* @G, <4 x i32> zeroinitializer, <4 x i32> <i32 0, i32 1, i32 2, i32 3>)
+define <4 x i32*> @foo() {
+ ret <4 x i32*> getelementptr ([4 x i32], [4 x i32]* @G, i32 0, <4 x i32> <i32 0, i32 1, i32 2, i32 3>)
+}
diff --git a/llvm/test/Assembler/getelementptr_vec_ce2.ll b/llvm/test/Assembler/getelementptr_vec_ce2.ll
new file mode 100644
index 00000000000..06362c8b3f6
--- /dev/null
+++ b/llvm/test/Assembler/getelementptr_vec_ce2.ll
@@ -0,0 +1,8 @@
+; RUN: not llvm-as < %s 2>&1 | FileCheck %s
+
+@G = global [4 x [4 x i32]] zeroinitializer
+
+; CHECK: getelementptr vector index has a wrong number of elements
+define <4 x i32*> @foo() {
+ ret <4 x i32*> getelementptr ([4 x [4 x i32]], [4 x [4 x i32]]* @G, i32 0, <4 x i32> <i32 0, i32 1, i32 2, i32 3>, <8 x i32> zeroinitializer)
+}
OpenPOWER on IntegriCloud