[Beignet] [PATCH] Add SROA and GVN pass to default optLevel.
Yang Rong
rong.r.yang at intel.com
Mon Mar 10 23:43:51 PDT 2014
SROA and GVN may introduce some integer type not support by backend.
Remove this type assert in GenWrite, and found these types, set the unit to
invalid. If unit is invalid, use optLevel 0, which not include SROA and GVN, and
try again.
Signed-off-by: Yang Rong <rong.r.yang at intel.com>
---
backend/src/backend/program.cpp | 15 ++++++++++++---
backend/src/ir/context.cpp | 3 ++-
backend/src/ir/unit.cpp | 2 +-
backend/src/ir/unit.hpp | 4 +++-
backend/src/llvm/llvm_gen_backend.cpp | 26 ++++++++++++++++++--------
backend/src/llvm/llvm_to_gen.cpp | 5 +++--
6 files changed, 39 insertions(+), 16 deletions(-)
diff --git a/backend/src/backend/program.cpp b/backend/src/backend/program.cpp
index f656299..6b445fa 100644
--- a/backend/src/backend/program.cpp
+++ b/backend/src/backend/program.cpp
@@ -103,12 +103,21 @@ namespace gbe {
BVAR(OCL_OUTPUT_GEN_IR, false);
bool Program::buildFromLLVMFile(const char *fileName, std::string &error, int optLevel) {
- ir::Unit unit;
- if (llvmToGen(unit, fileName, optLevel) == false) {
+ ir::Unit *unit = new ir::Unit();
+ if (llvmToGen(*unit, fileName, optLevel) == false) {
error = std::string(fileName) + " not found";
return false;
}
- this->buildFromUnit(unit, error);
+ //If unit is not valid, maybe some thing don't support by backend, introduce by some passes
+ //use optLevel 0 to try again.
+ if(!unit->getValid()) {
+ delete unit; //clear unit
+ unit = new ir::Unit();
+ llvmToGen(*unit, fileName, 0); //supose file is exit and llvmToGen will not return false.
+ }
+ assert(unit->getValid());
+ this->buildFromUnit(*unit, error);
+ delete unit;
return true;
}
diff --git a/backend/src/ir/context.cpp b/backend/src/ir/context.cpp
index d6815e1..ff5c575 100644
--- a/backend/src/ir/context.cpp
+++ b/backend/src/ir/context.cpp
@@ -157,7 +157,8 @@ namespace ir {
bb->append(*insnPtr);
#if GBE_DEBUG
std::string whyNot;
- GBE_ASSERTM(insnPtr->wellFormed(whyNot), whyNot.c_str());
+ if(getUnit().getValid())
+ GBE_ASSERTM(insnPtr->wellFormed(whyNot), whyNot.c_str());
#endif /* GBE_DEBUG */
// Close the current block if this is a branch
diff --git a/backend/src/ir/unit.cpp b/backend/src/ir/unit.cpp
index 4aeffe9..4f9d740 100644
--- a/backend/src/ir/unit.cpp
+++ b/backend/src/ir/unit.cpp
@@ -27,7 +27,7 @@
namespace gbe {
namespace ir {
- Unit::Unit(PointerSize pointerSize) : pointerSize(pointerSize) {}
+ Unit::Unit(PointerSize pointerSize) : pointerSize(pointerSize), valid(true) {}
Unit::~Unit(void) {
for (const auto &pair : functions) GBE_DELETE(pair.second);
}
diff --git a/backend/src/ir/unit.hpp b/backend/src/ir/unit.hpp
index d8eab79..adebd3f 100644
--- a/backend/src/ir/unit.hpp
+++ b/backend/src/ir/unit.hpp
@@ -72,12 +72,15 @@ namespace ir {
ConstantSet& getConstantSet(void) { return constantSet; }
/*! Return the constant set */
const ConstantSet& getConstantSet(void) const { return constantSet; }
+ void setValid(bool value) { valid = value; }
+ bool getValid() { return valid; }
private:
friend class ContextInterface; //!< Can free modify the unit
hash_map<std::string, Function*> functions; //!< All the defined functions
ConstantSet constantSet; //!< All the constants defined in the unit
PointerSize pointerSize; //!< Size shared by all pointers
GBE_CLASS(Unit);
+ bool valid;
};
/*! Output the unit string in the given stream */
@@ -87,4 +90,3 @@ namespace ir {
} /* namespace gbe */
#endif /* __GBE_IR_UNIT_HPP__ */
-
diff --git a/backend/src/llvm/llvm_gen_backend.cpp b/backend/src/llvm/llvm_gen_backend.cpp
index dcc1497..227ef09 100644
--- a/backend/src/llvm/llvm_gen_backend.cpp
+++ b/backend/src/llvm/llvm_gen_backend.cpp
@@ -178,7 +178,7 @@ namespace gbe
}
/*! LLVM IR Type to Gen IR type translation */
- static ir::Type getType(const ir::Context &ctx, const Type *type)
+ static ir::Type getType(ir::Context &ctx, const Type *type)
{
GBE_ASSERT(isScalarType(type));
if (type->isFloatTy() == true)
@@ -202,12 +202,12 @@ namespace gbe
return ir::TYPE_S32;
if (type == Type::getInt64Ty(type->getContext()))
return ir::TYPE_S64;
- GBE_ASSERT(0);
+ ctx.getUnit().setValid(false);
return ir::TYPE_S64;
}
/*! LLVM IR Type to Gen IR unsigned type translation */
- static ir::Type getUnsignedType(const ir::Context &ctx, const Type *type)
+ static ir::Type getUnsignedType(ir::Context &ctx, const Type *type)
{
GBE_ASSERT(type->isIntegerTy() == true);
if (type == Type::getInt1Ty(type->getContext()))
@@ -220,12 +220,12 @@ namespace gbe
return ir::TYPE_U32;
if (type == Type::getInt64Ty(type->getContext()))
return ir::TYPE_U64;
- GBE_ASSERT(0);
+ ctx.getUnit().setValid(false);
return ir::TYPE_U64;
}
/*! Type to register family translation */
- static ir::RegisterFamily getFamily(const ir::Context &ctx, const Type *type)
+ static ir::RegisterFamily getFamily(ir::Context &ctx, const Type *type)
{
GBE_ASSERT(isScalarType(type) == true);
if (type == Type::getInt1Ty(type->getContext()))
@@ -240,14 +240,14 @@ namespace gbe
return ir::FAMILY_QWORD;
if (type->isPointerTy())
return ctx.getPointerFamily();
- GBE_ASSERT(0);
+ ctx.getUnit().setValid(false);
return ir::FAMILY_BOOL;
}
/*! Get number of element to process dealing either with a vector or a scalar
* value
*/
- static ir::Type getVectorInfo(const ir::Context &ctx, Type *llvmType, Value *value, uint32_t &elemNum, bool useUnsigned = false)
+ static ir::Type getVectorInfo(ir::Context &ctx, Type *llvmType, Value *value, uint32_t &elemNum, bool useUnsigned = false)
{
ir::Type type;
if (llvmType->isVectorTy() == true) {
@@ -810,7 +810,8 @@ namespace gbe
const uint64_t u64 = CI->getZExtValue();
return doIt(u64);
} else {
- GBE_ASSERTM(false, "Unsupported integer size");
+ //GBE_ASSERTM(false, "Unsupported integer size");
+ doIt.invalid();
return doIt(uint64_t(0));
}
}
@@ -855,6 +856,9 @@ namespace gbe
template <typename T> ir::ImmediateIndex operator() (const T &t) {
return ctx.newImmediate(t);
}
+ void invalid() {
+ ctx.getUnit().setValid(false);
+ }
ir::Context &ctx;
};
@@ -1845,6 +1849,9 @@ namespace gbe
template <typename T> ir::Immediate operator() (const T &t) {
return ir::Immediate(t);
}
+ void invalid() {
+ ctx.getUnit().setValid(false);
+ }
ir::Context &ctx;
};
@@ -2188,6 +2195,9 @@ namespace gbe
template <typename T> INLINE uint64_t operator() (const T &t) {
return uint64_t(t);
}
+ void invalid() {
+ ctx.getUnit().setValid(false);
+ }
ir::Context &ctx;
};
diff --git a/backend/src/llvm/llvm_to_gen.cpp b/backend/src/llvm/llvm_to_gen.cpp
index 8b2ac04..9e18a57 100644
--- a/backend/src/llvm/llvm_to_gen.cpp
+++ b/backend/src/llvm/llvm_to_gen.cpp
@@ -116,7 +116,8 @@ namespace gbe
MPM.add(createFunctionAttrsPass()); // Set readonly/readnone attrs
//MPM.add(createScalarReplAggregatesPass(64, true, -1, -1, 64))
- //MPM.add(createSROAPass(/*RequiresDomTree*/ false));
+ if(optLevel > 0)
+ MPM.add(createSROAPass(/*RequiresDomTree*/ false));
MPM.add(createEarlyCSEPass()); // Catch trivial redundancies
MPM.add(createJumpThreadingPass()); // Thread jumps.
MPM.add(createCorrelatedValuePropagationPass()); // Propagate conditionals
@@ -135,7 +136,7 @@ namespace gbe
MPM.add(createLoopDeletionPass()); // Delete dead loops
MPM.add(createLoopUnrollPass()); // Unroll small loops
if(optLevel > 0)
- MPM.add(createGVNPass(true)); // Remove redundancies
+ MPM.add(createGVNPass()); // Remove redundancies
MPM.add(createMemCpyOptPass()); // Remove memcpy / form memset
MPM.add(createSCCPPass()); // Constant prop with SCCP
--
1.8.3.2
More information about the Beignet
mailing list