[Beignet] [PATCH v2 2/2] GBE: Add some missing constant expression cases.
Zhigang Gong
zhigang.gong at linux.intel.com
Sun Dec 14 17:17:49 PST 2014
Ping for review.
On Thu, Dec 04, 2014 at 05:45:17PM +0800, Zhigang Gong wrote:
> From: Zhigang Gong <zhigang.gong at linux.intel.com>
>
> Major for two types of constant expression cases:
> 1. The destination is a vector.
> 2. Some missing operators.
>
> Signed-off-by: Zhigang Gong <zhigang.gong at linux.intel.com>
> ---
> backend/src/ir/context.hpp | 4 +-
> backend/src/ir/immediate.cpp | 34 +++++++++++++++--
> backend/src/ir/immediate.hpp | 70 +++++++++++++++++++++++++++++++++--
> backend/src/llvm/llvm_gen_backend.cpp | 38 ++++++++++++++++++-
> 4 files changed, 135 insertions(+), 11 deletions(-)
>
> diff --git a/backend/src/ir/context.hpp b/backend/src/ir/context.hpp
> index 485d558..cf5109d 100644
> --- a/backend/src/ir/context.hpp
> +++ b/backend/src/ir/context.hpp
> @@ -74,11 +74,11 @@ namespace ir {
> return fn->newImmediate(imm);
> }
> /*! Create a new immediate value */
> - INLINE ImmediateIndex newImmediate(vector<ImmediateIndex>indexVector) {
> + INLINE ImmediateIndex newImmediate(vector<ImmediateIndex>indexVector, Type dstType) {
> vector<const Immediate*> immVector;
> for( uint32_t i = 0; i < indexVector.size(); i++)
> immVector.push_back(&fn->getImmediate(indexVector[i]));
> - const Immediate imm(immVector);
> + const Immediate imm(immVector, dstType);
> return fn->newImmediate(imm);
> }
> /*! Create an integer immediate value */
> diff --git a/backend/src/ir/immediate.cpp b/backend/src/ir/immediate.cpp
> index 7d26925..1aac9bc 100644
> --- a/backend/src/ir/immediate.cpp
> +++ b/backend/src/ir/immediate.cpp
> @@ -132,7 +132,7 @@ using namespace ir;
> }
>
> Immediate Immediate::less (const Immediate &left, const Immediate &right) {
> - GBE_ASSERT(left.getType() > TYPE_BOOL && left.getType() <= TYPE_U64);
> + GBE_ASSERT(left.getType() > TYPE_BOOL && left.getType() <= TYPE_DOUBLE);
> switch (left.getType()) {
> default:
> GBE_ASSERT(0);
> @@ -149,6 +149,30 @@ using namespace ir;
> }
> }
>
> + Immediate Immediate::extract (const Immediate &left, const Immediate &right, Type dstType) {
> + GBE_ASSERT(left.getType() > TYPE_BOOL && left.getType() <= TYPE_DOUBLE);
> + GBE_ASSERT(dstType == left.getType());
> + uint32_t index = right.getIntegerValue();
> + GBE_ASSERT(index >= 0 && index < left.getElemNum());
> + if (left.type != IMM_TYPE_COMP) {
> + switch (left.getType()) {
> + default:
> + GBE_ASSERT(0);
> + case TYPE_BOOL: return Immediate(left.data.b[index]);
> + case TYPE_S8: return Immediate(left.data.s8[index]);
> + case TYPE_U8: return Immediate(left.data.u8[index]);
> + case TYPE_S16: return Immediate(left.data.s16[index]);
> + case TYPE_U16: return Immediate(left.data.u16[index]);
> + case TYPE_S32: return Immediate(left.data.s32[index]);
> + case TYPE_U32: return Immediate(left.data.u32[index]);
> + case TYPE_S64: return Immediate(left.data.s64[index]);
> + case TYPE_U64: return Immediate(left.data.u64[index]);
> + case TYPE_FLOAT: return Immediate(left.data.f32[index]);
> + case TYPE_DOUBLE: return Immediate(left.data.f64[index]);
> + }
> + } else
> + return *left.data.immVec[index];
> + }
>
> Immediate::Immediate(ImmOpCode op, const Immediate &left, const Immediate &right, Type dstType) {
> switch (op) {
> @@ -180,7 +204,7 @@ using namespace ir;
> case IMM_LSHR:
> {
> if (left.getElemNum() == 1)
> - lshr(left, right);
> + *this = lshr(left, right);
> else {
> GBE_ASSERT(right.getIntegerValue() <= (left.getElemNum() * left.getTypeSize() * 8));
> GBE_ASSERT(right.getIntegerValue() % (left.getTypeSize() * 8) == 0);
> @@ -216,16 +240,17 @@ using namespace ir;
> case IMM_OLT: *this = less(left, right); break;
> case IMM_OGT: *this = left > right; break;
> case IMM_ORD: *this = (left == left) && (right == right); break;
> + case IMM_EXTRACT: *this = extract(left, right, dstType); break;
> }
> // If the dst type is large int, we will not change the imm type to large int.
> GBE_ASSERT(type == (ImmType)dstType || dstType == TYPE_LARGE_INT || dstType == TYPE_BOOL);
> }
>
> - Immediate::Immediate(const vector<const Immediate*> immVec) {
> + Immediate::Immediate(const vector<const Immediate*> immVec, Type dstType) {
> if (immVec.size() == 1) {
> *this = *immVec[0];
> } else if (!(immVec[0]->isCompType()) && immVec[0]->elemNum == 1) {
> - this->type = immVec[0]->type;
> + this->type = (ImmType)dstType;
> this->elemNum = immVec.size();
> if (immVec[0]->getTypeSize() * immVec.size() < 8)
> this->data.p = &this->defaultData;
> @@ -238,6 +263,7 @@ using namespace ir;
> p += immVec[i]->getTypeSize();
> }
> } else {
> + GBE_ASSERT(0);
> this->type = IMM_TYPE_COMP;
> if (immVec.size() * sizeof(Immediate*) < 8)
> this->data.p = &this->defaultData;
> diff --git a/backend/src/ir/immediate.hpp b/backend/src/ir/immediate.hpp
> index 1f18a4c..7b6ba34 100644
> --- a/backend/src/ir/immediate.hpp
> +++ b/backend/src/ir/immediate.hpp
> @@ -56,7 +56,11 @@ namespace ir {
> IMM_FPTOUI,
> IMM_FPTOSI,
> IMM_SITOFP,
> - IMM_UITOFP
> + IMM_UITOFP,
> + IMM_EXTRACT,
> + IMM_SEXT,
> + IMM_ZEXT,
> + IMM_FPEXT
> } ImmOpCode;
>
> typedef enum {
> @@ -158,7 +162,7 @@ namespace ir {
> DECL_CONSTRUCTOR(double, f64, TYPE_DOUBLE, elemNum)
> #undef DECL_CONSTRUCTOR
>
> - Immediate(const vector<const Immediate*> immVec);
> + Immediate(const vector<const Immediate*> immVec, Type dstType);
>
> INLINE int64_t getIntegerValue(void) const {
> switch (type) {
> @@ -176,6 +180,22 @@ namespace ir {
> }
> }
>
> + INLINE uint64_t getUnsignedIntegerValue(void) const {
> + switch (type) {
> + default:
> + GBE_ASSERT(0 && "Invalid immediate type.\n");
> + case TYPE_BOOL: return *data.b;
> + case TYPE_S8: return *data.s8;
> + case TYPE_U8: return *data.u8;
> + case TYPE_S16: return *data.s16;
> + case TYPE_U16: return *data.u16;
> + case TYPE_S32: return *data.s32;
> + case TYPE_U32: return *data.u32;
> + case TYPE_S64: return *data.s64;
> + case TYPE_U64: return *data.u64;
> + }
> + }
> +
> INLINE float getFloatValue(void) const {
> GBE_ASSERT(type == IMM_TYPE_FLOAT);
> return *data.f32;
> @@ -208,13 +228,54 @@ namespace ir {
> copy(other, 0, 1);
> break;
> case IMM_BITCAST:
> - *this = other;
> - type = (ImmType)dstType;
> + if (other.type != IMM_TYPE_COMP) {
> + *this = other;
> + type = (ImmType)dstType;
> + } else {
> + vector<const Immediate*> immVec;
> + for(uint32_t i = 0; i < other.getElemNum(); i++)
> + immVec.push_back(other.data.immVec[i]);
> + *this = Immediate(immVec, dstType);
> + }
> break;
> case IMM_FPTOUI: *this = Immediate((uint32_t)*other.data.f32); break;
> case IMM_FPTOSI: *this = Immediate((int32_t)*other.data.f32); break;
> case IMM_UITOFP: *this = Immediate((float)*other.data.u32); break;
> case IMM_SITOFP: *this = Immediate((float)*other.data.s32); break;
> + case IMM_SEXT:
> + {
> + int64_t value = other.getIntegerValue();
> + if (other.getType() == TYPE_BOOL)
> + value = -value;
> + switch (dstType) {
> + default:
> + GBE_ASSERT(0 && "Illegal sext constant expression");
> + case TYPE_S8: *this = Immediate((int8_t)value); break;
> + case TYPE_S16: *this = Immediate((int16_t)value); break;
> + case TYPE_S32: *this = Immediate((int32_t)value); break;
> + case TYPE_S64: *this = Immediate((int64_t)value); break;
> + }
> + }
> + case IMM_ZEXT:
> + {
> + uint64_t value = other.getUnsignedIntegerValue();
> + switch (dstType) {
> + default:
> + GBE_ASSERT(0 && "Illegal sext constant expression");
> + case TYPE_U8: *this = Immediate((uint8_t)value); break;
> + case TYPE_U16: *this = Immediate((uint16_t)value); break;
> + case TYPE_U32: *this = Immediate((uint32_t)value); break;
> + case TYPE_U64: *this = Immediate((uint64_t)value); break;
> + }
> + break;
> + }
> + case IMM_FPEXT:
> + {
> + GBE_ASSERT(other.getType() == TYPE_FLOAT && dstType == TYPE_DOUBLE);
> + double value = other.getFloatValue();
> + *this = Immediate(value);
> + break;
> + }
> }
> }
>
> @@ -265,6 +326,7 @@ namespace ir {
> Immediate operator>> (const Immediate &) const;
> static Immediate lshr (const Immediate &left, const Immediate &right);
> static Immediate less (const Immediate &left, const Immediate &right);
> + static Immediate extract (const Immediate &left, const Immediate &right, Type dstType);
>
> void copy(const Immediate &other, int32_t offset, uint32_t num);
> GBE_CLASS(Immediate);
> diff --git a/backend/src/llvm/llvm_gen_backend.cpp b/backend/src/llvm/llvm_gen_backend.cpp
> index c7ecc44..a438f09 100644
> --- a/backend/src/llvm/llvm_gen_backend.cpp
> +++ b/backend/src/llvm/llvm_gen_backend.cpp
> @@ -902,7 +902,7 @@ namespace gbe
> vector<ir::ImmediateIndex> immVector;
> for (uint32_t i = 0; i < cv->getNumOperands(); i++)
> immVector.push_back(processConstantImmIndex(cv->getOperand(i)));
> - return ctx.newImmediate(immVector);
> + return ctx.newImmediate(immVector, getType(ctx, cv->getType()->getElementType()));
> }
> }
>
> @@ -1045,11 +1045,25 @@ namespace gbe
>
> if (dyn_cast<ConstantExpr>(CPV)) {
> ConstantExpr *ce = dyn_cast<ConstantExpr>(CPV);
> +
> + if (!isScalarType(ce->getType())) {
> + VectorType *vecType = cast<VectorType>(ce->getType());
> + GBE_ASSERT(ce->getOpcode() == Instruction::BitCast);
> + GBE_ASSERT(isScalarType(vecType->getElementType()));
> + ir::Type elemType = getType(ctx, vecType->getElementType());
> +
> + const ir::ImmediateIndex immIndex = processConstantImmIndex(ce->getOperand(0), -1);
> + const ir::Immediate imm = ctx.getImmediate(immIndex);
> + GBE_ASSERT(vecType->getNumElements() == imm.getElemNum() &&
> + getTypeByteSize(unit, vecType->getElementType()) == imm.getTypeSize());
> + return ctx.processImm(ir::IMM_BITCAST, immIndex, elemType);
> + }
> ir::Type type = getType(ctx, ce->getType());
> switch (ce->getOpcode()) {
> default:
> ce->dump();
> GBE_ASSERT(0 && "unsupported ce opcode.\n");
> + case Instruction::FPTrunc:
> case Instruction::Trunc:
> {
> const ir::ImmediateIndex immIndex = processConstantImmIndex(ce->getOperand(0), -1);
> @@ -1066,6 +1080,9 @@ namespace gbe
> case Instruction::FPToSI:
> case Instruction::SIToFP:
> case Instruction::UIToFP:
> + case Instruction::SExt:
> + case Instruction::ZExt:
> + case Instruction::FPExt:
> {
> const ir::ImmediateIndex immIndex = processConstantImmIndex(ce->getOperand(0), -1);
> switch (ce->getOpcode()) {
> @@ -1075,15 +1092,26 @@ namespace gbe
> case Instruction::FPToSI: return ctx.processImm(ir::IMM_FPTOSI, immIndex, type);
> case Instruction::SIToFP: return ctx.processImm(ir::IMM_SITOFP, immIndex, type);
> case Instruction::UIToFP: return ctx.processImm(ir::IMM_UITOFP, immIndex, type);
> + case Instruction::SExt: return ctx.processImm(ir::IMM_SEXT, immIndex, type);
> + case Instruction::ZExt: return ctx.processImm(ir::IMM_ZEXT, immIndex, type);
> + case Instruction::FPExt: return ctx.processImm(ir::IMM_FPEXT, immIndex, type);
> }
> }
> +
> + case Instruction::ExtractElement:
> case Instruction::FCmp:
> case Instruction::ICmp:
> + case Instruction::FAdd:
> case Instruction::Add:
> case Instruction::Sub:
> + case Instruction::FSub:
> case Instruction::Mul:
> + case Instruction::FMul:
> case Instruction::SDiv:
> + case Instruction::UDiv:
> + case Instruction::FDiv:
> case Instruction::SRem:
> + case Instruction::FRem:
> case Instruction::Shl:
> case Instruction::AShr:
> case Instruction::LShr:
> @@ -1096,15 +1124,23 @@ namespace gbe
> default:
> //ce->dump();
> GBE_ASSERTM(0, "Unsupported constant expression.\n");
> +
> + case Instruction::ExtractElement:
> + return ctx.processImm(ir::IMM_EXTRACT, lhs, rhs, type);
> case Instruction::Add:
> + case Instruction::FAdd:
> return ctx.processImm(ir::IMM_ADD, lhs, rhs, type);
> + case Instruction::FSub:
> case Instruction::Sub:
> return ctx.processImm(ir::IMM_SUB, lhs, rhs, type);
> case Instruction::Mul:
> + case Instruction::FMul:
> return ctx.processImm(ir::IMM_MUL, lhs, rhs, type);
> case Instruction::SDiv:
> + case Instruction::FDiv:
> return ctx.processImm(ir::IMM_DIV, lhs, rhs, type);
> case Instruction::SRem:
> + case Instruction::FRem:
> return ctx.processImm(ir::IMM_REM, lhs, rhs, type);
> case Instruction::Shl:
> return ctx.processImm(ir::IMM_SHL, lhs, rhs, type);
> --
> 1.8.3.2
>
> _______________________________________________
> Beignet mailing list
> Beignet at lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/beignet
More information about the Beignet
mailing list