+inline const ConstantInt *operator*(const DefZero &L, const DefZero &R) {
+ if (L == 0 || R == 0) return 0;
+ return Mul(L, R, false);
+}
+inline const ConstantInt *operator*(const DefOne &L, const DefZero &R) {
+ if (R == 0) return getUnsignedConstant(0, L.getType());
+ if (L == 0) return R->equalsInt(1) ? 0 : R.getVal();
+ return Mul(L, R, true);
+}
+inline const ConstantInt *operator*(const DefZero &L, const DefOne &R) {
+ if (L == 0 || R == 0) return L.getVal();
+ return Mul(R, L, false);
+}
+
+// handleAddition - Add two expressions together, creating a new expression that
+// represents the composite of the two...
+//
+static ExprType handleAddition(ExprType Left, ExprType Right, Value *V) {
+ const Type *Ty = V->getType();
+ if (Left.ExprTy > Right.ExprTy)
+ std::swap(Left, Right); // Make left be simpler than right
+
+ switch (Left.ExprTy) {
+ case ExprType::Constant:
+ return ExprType(Right.Scale, Right.Var,
+ DefZero(Right.Offset, Ty) + DefZero(Left.Offset, Ty));
+ case ExprType::Linear: // RHS side must be linear or scaled
+ case ExprType::ScaledLinear: // RHS must be scaled
+ if (Left.Var != Right.Var) // Are they the same variables?
+ return V; // if not, we don't know anything!
+
+ return ExprType(DefOne(Left.Scale , Ty) + DefOne(Right.Scale , Ty),
+ Right.Var,
+ DefZero(Left.Offset, Ty) + DefZero(Right.Offset, Ty));
+ default:
+ assert(0 && "Dont' know how to handle this case!");
+ return ExprType();
+ }
+}
+
+// negate - Negate the value of the specified expression...
+//
+static inline ExprType negate(const ExprType &E, Value *V) {
+ const Type *Ty = V->getType();
+ ConstantInt *Zero = getUnsignedConstant(0, Ty);
+ ConstantInt *One = getUnsignedConstant(1, Ty);
+ ConstantInt *NegOne = cast<ConstantInt>(*Zero - *One);
+ if (NegOne == 0) return V; // Couldn't subtract values...
+
+ return ExprType(DefOne (E.Scale , Ty) * NegOne, E.Var,
+ DefZero(E.Offset, Ty) * NegOne);
+}
+