summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorChris Lattner <sabre@nondot.org>2007-08-03 00:16:29 +0000
committerChris Lattner <sabre@nondot.org>2007-08-03 00:16:29 +0000
commit73ab9b3c14673ebeaf2bf2f7bda3b0b1c2bbad7c (patch)
treeff7f72601d2e0459544c4a41a3ef85d27b32da7d
parent9e751cae2756933c9eec8076ff767bf9dc7a6a72 (diff)
downloadbcm5719-llvm-73ab9b3c14673ebeaf2bf2f7bda3b0b1c2bbad7c.tar.gz
bcm5719-llvm-73ab9b3c14673ebeaf2bf2f7bda3b0b1c2bbad7c.zip
implement lvalue to rvalue conversion for ocuvector components. We can now compile stuff
like this: typedef __attribute__(( ocu_vector_type(4) )) float float4; float4 test1(float4 V) { return V.wzyx+V; } to: _test1: pshufd $27, %xmm0, %xmm1 addps %xmm0, %xmm1 movaps %xmm1, %xmm0 ret and: _test1: mfspr r2, 256 oris r3, r2, 4096 mtspr 256, r3 li r3, lo16(LCPI1_0) lis r4, ha16(LCPI1_0) lvx v3, r4, r3 vperm v3, v2, v2, v3 vaddfp v2, v3, v2 mtspr 256, r2 blr llvm-svn: 40771
-rw-r--r--clang/CodeGen/CGExpr.cpp26
-rw-r--r--clang/CodeGen/CodeGenFunction.h3
2 files changed, 28 insertions, 1 deletions
diff --git a/clang/CodeGen/CGExpr.cpp b/clang/CodeGen/CGExpr.cpp
index 1a841f9d81d..7d8dc8c33b9 100644
--- a/clang/CodeGen/CGExpr.cpp
+++ b/clang/CodeGen/CGExpr.cpp
@@ -282,6 +282,30 @@ RValue CodeGenFunction::EmitLoadOfLValue(LValue LV, QualType ExprType) {
return RValue::get(Builder.CreateExtractElement(Vec, LV.getVectorIdx(),
"vecext"));
}
+
+ // If this is a reference to a subset of the elements of a vector, either
+ // shuffle the input or extract/insert them as appropriate.
+ if (LV.isOCUVectorComp()) {
+ llvm::Value *Vec = Builder.CreateLoad(LV.getOCUVectorAddr(), "tmp");
+ unsigned NumElts = cast<VectorType>(ExprType)->getNumElements();
+
+ // Start out with an undef of the result type.
+ llvm::Value *Result = llvm::UndefValue::get(ConvertType(ExprType));
+
+ unsigned EncFields = LV.getOCUVectorComp();
+
+ // Extract/Insert each element of the result.
+ for (unsigned i = 0; i != NumElts; ++i) {
+ unsigned InIdx = OCUVectorComponent::getAccessedFieldNo(i, EncFields);
+ llvm::Value *Elt = llvm::ConstantInt::get(llvm::Type::Int32Ty, InIdx);
+ Elt = Builder.CreateExtractElement(Vec, Elt, "tmp");
+
+ llvm::Value *OutIdx = llvm::ConstantInt::get(llvm::Type::Int32Ty, i);
+ Result = Builder.CreateInsertElement(Result, Elt, OutIdx, "tmp");
+ }
+
+ return RValue::get(Result);
+ }
assert(0 && "Bitfield ref not impl!");
}
@@ -505,6 +529,8 @@ RValue CodeGenFunction::EmitExpr(const Expr *E) {
return EmitLoadOfLValue(E);
case Expr::ArraySubscriptExprClass:
return EmitArraySubscriptExprRV(cast<ArraySubscriptExpr>(E));
+ case Expr::OCUVectorComponentClass:
+ return EmitLoadOfLValue(E);
case Expr::PreDefinedExprClass:
case Expr::StringLiteralClass:
return RValue::get(EmitLValue(E).getAddress());
diff --git a/clang/CodeGen/CodeGenFunction.h b/clang/CodeGen/CodeGenFunction.h
index 37614e95f06..919e68c91d0 100644
--- a/clang/CodeGen/CodeGenFunction.h
+++ b/clang/CodeGen/CodeGenFunction.h
@@ -141,6 +141,7 @@ public:
llvm::Value *getVectorAddr() const { assert(isVectorElt()); return V; }
llvm::Value *getVectorIdx() const { assert(isVectorElt()); return VectorIdx; }
// ocu vector components.
+ llvm::Value *getOCUVectorAddr() const { assert(isOCUVectorComp()); return V; }
unsigned getOCUVectorComp() const {
assert(isOCUVectorComp());
return VectorComp;
@@ -164,7 +165,7 @@ public:
static LValue MakeOCUVectorComp(llvm::Value *Vec, unsigned Components) {
LValue R;
- R.LVType = VectorElt;
+ R.LVType = OCUVectorComp;
R.V = Vec;
R.VectorComp = Components;
return R;
OpenPOWER on IntegriCloud