r215991 - ext_vector IRGen. Patch to allow indexing into

Fariborz Jahanian fjahanian at apple.com
Tue Aug 19 10:17:40 PDT 2014


Author: fjahanian
Date: Tue Aug 19 12:17:40 2014
New Revision: 215991

URL: http://llvm.org/viewvc/llvm-project?rev=215991&view=rev
Log:
ext_vector IRGen. Patch to allow indexing into 
ext_vector_type's 'hi/lo' components when
used as lvalue. rdar://18031917 pr20697

Added:
    cfe/trunk/test/CodeGen/ext-vector-indexing.c
Modified:
    cfe/trunk/lib/CodeGen/CGExpr.cpp
    cfe/trunk/lib/CodeGen/CodeGenFunction.h

Modified: cfe/trunk/lib/CodeGen/CGExpr.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGExpr.cpp?rev=215991&r1=215990&r2=215991&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CGExpr.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGExpr.cpp Tue Aug 19 12:17:40 2014
@@ -1361,6 +1361,28 @@ RValue CodeGenFunction::EmitLoadOfExtVec
   return RValue::get(Vec);
 }
 
+/// @brief Generates lvalue for partial ext_vector access.
+llvm::Value *CodeGenFunction::EmitExtVectorElementLValue(LValue LV) {
+  llvm::Value *VectorAddress = LV.getExtVectorAddr();
+  const VectorType *ExprVT = LV.getType()->getAs<VectorType>();
+  QualType EQT = ExprVT->getElementType();
+  llvm::Type *VectorElementTy = CGM.getTypes().ConvertType(EQT);
+  llvm::Type *VectorElementPtrToTy = VectorElementTy->getPointerTo();
+  
+  llvm::Value *CastToPointerElement =
+    Builder.CreateBitCast(VectorAddress,
+                          VectorElementPtrToTy, "conv.ptr.element");
+  
+  const llvm::Constant *Elts = LV.getExtVectorElts();
+  unsigned ix = getAccessedFieldNo(0, Elts);
+  
+  llvm::Value *VectorBasePtrPlusIx =
+    Builder.CreateInBoundsGEP(CastToPointerElement,
+                              llvm::ConstantInt::get(SizeTy, ix), "add.ptr");
+  
+  return VectorBasePtrPlusIx;
+}
+
 /// @brief Load of global gamed gegisters are always calls to intrinsics.
 RValue CodeGenFunction::EmitLoadOfGlobalRegLValue(LValue LV) {
   assert((LV.getType()->isIntegerType() || LV.getType()->isPointerType()) &&
@@ -2323,7 +2345,8 @@ LValue CodeGenFunction::EmitArraySubscri
 
   // If the base is a vector type, then we are forming a vector element lvalue
   // with this subscript.
-  if (E->getBase()->getType()->isVectorType()) {
+  if (E->getBase()->getType()->isVectorType() &&
+      !isa<ExtVectorElementExpr>(E->getBase())) {
     // Emit the vector as an lvalue to get its address.
     LValue LHS = EmitLValue(E->getBase());
     assert(LHS.isSimple() && "Can only subscript lvalue vectors here!");
@@ -2339,8 +2362,17 @@ LValue CodeGenFunction::EmitArraySubscri
   // size is a VLA or Objective-C interface.
   llvm::Value *Address = nullptr;
   CharUnits ArrayAlignment;
-  if (const VariableArrayType *vla =
-        getContext().getAsVariableArrayType(E->getType())) {
+  if (isa<ExtVectorElementExpr>(E->getBase())) {
+    LValue LV = EmitLValue(E->getBase());
+    Address = EmitExtVectorElementLValue(LV);
+    Address = Builder.CreateInBoundsGEP(Address, Idx, "arrayidx");
+    const VectorType *ExprVT = LV.getType()->getAs<VectorType>();
+    QualType EQT = ExprVT->getElementType();
+    return MakeAddrLValue(Address, EQT,
+                          getContext().getTypeAlignInChars(EQT));
+  }
+  else if (const VariableArrayType *vla =
+           getContext().getAsVariableArrayType(E->getType())) {
     // The base must be a pointer, which is not an aggregate.  Emit
     // it.  It needs to be emitted first in case it's what captures
     // the VLA bounds.

Modified: cfe/trunk/lib/CodeGen/CodeGenFunction.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CodeGenFunction.h?rev=215991&r1=215990&r2=215991&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CodeGenFunction.h (original)
+++ cfe/trunk/lib/CodeGen/CodeGenFunction.h Tue Aug 19 12:17:40 2014
@@ -2096,6 +2096,8 @@ public:
   LValue EmitCastLValue(const CastExpr *E);
   LValue EmitMaterializeTemporaryExpr(const MaterializeTemporaryExpr *E);
   LValue EmitOpaqueValueLValue(const OpaqueValueExpr *e);
+  
+  llvm::Value *EmitExtVectorElementLValue(LValue V);
 
   RValue EmitRValueForField(LValue LV, const FieldDecl *FD, SourceLocation Loc);
 

Added: cfe/trunk/test/CodeGen/ext-vector-indexing.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGen/ext-vector-indexing.c?rev=215991&view=auto
==============================================================================
--- cfe/trunk/test/CodeGen/ext-vector-indexing.c (added)
+++ cfe/trunk/test/CodeGen/ext-vector-indexing.c Tue Aug 19 12:17:40 2014
@@ -0,0 +1,14 @@
+// RUN: %clang_cc1 -triple x86_64-unknown-unknown -emit-llvm %s -o - | FileCheck %s
+
+typedef __attribute__(( ext_vector_type(4) )) float float4;
+// CHECK: @test
+void test()
+{
+  float4 va;
+  va.hi[0] = 3.0;
+// CHECK:  [[VA:%.*]] = alloca <4 x float>
+// CHECK:  [[CONV:%.*]] = bitcast <4 x float>* [[VA]] to float*
+// CHECK:  [[ADD:%.*]] = getelementptr inbounds float* [[CONV]], i64 2
+// CHECK:  [[ARRIDX:%.*]] = getelementptr inbounds float* [[ADD]], i64 0
+// CHECK:   store float 3.000000e+00, float* [[ARRIDX]]
+}





More information about the cfe-commits mailing list