class ValidatorResult visitAddRecExpr(const SCEVAddRecExpr *Expr) { if (!Expr->isAffine()) { DEBUG(dbgs() << "INVALID: AddRec is not affine"); return ValidatorResult(SCEVType::INVALID); } ValidatorResult Start = visit(Expr->getStart()); ValidatorResult Recurrence = visit(Expr->getStepRecurrence(SE)); if (!Start.isValid()) return Start; if (!Recurrence.isValid()) return Recurrence; auto *L = Expr->getLoop(); if (R->contains(L) && (!Scope || !L->contains(Scope))) { DEBUG(dbgs() << "INVALID: AddRec out of a loop whose exit value is not " "synthesizable"); return ValidatorResult(SCEVType::INVALID); } if (R->contains(L)) { if (Recurrence.isINT()) { ValidatorResult Result(SCEVType::IV); Result.addParamsFrom(Start); return Result; } DEBUG(dbgs() << "INVALID: AddRec within scop has non-int" "recurrence part"); return ValidatorResult(SCEVType::INVALID); } assert(Start.isConstant() && Recurrence.isConstant() && "Expected 'Start' and 'Recurrence' to be constant"); // Directly generate ValidatorResult for Expr if 'start' is zero. if (Expr->getStart()->isZero()) return ValidatorResult(SCEVType::PARAM, Expr); // Translate AddRecExpr from '{start, +, inc}' into 'start + {0, +, inc}' // if 'start' is not zero. const SCEV *ZeroStartExpr = SE.getAddRecExpr( SE.getConstant(Expr->getStart()->getType(), 0), Expr->getStepRecurrence(SE), Expr->getLoop(), Expr->getNoWrapFlags()); ValidatorResult ZeroStartResult = ValidatorResult(SCEVType::PARAM, ZeroStartExpr); ZeroStartResult.addParamsFrom(Start); return ZeroStartResult; }
class ValidatorResult visitSMaxExpr(const SCEVSMaxExpr *Expr) { ValidatorResult Return(SCEVType::INT, Expr); for (int i = 0, e = Expr->getNumOperands(); i < e; ++i) { ValidatorResult Op = visit(Expr->getOperand(i)); if (!Op.isValid()) return Op; Return.merge(Op); } return Return; }