예제 #1
0
파일: Conj.cs 프로젝트: glycerine/SDFCalc
        public override PathCond Or(PathCond other)
        {
            if (this.Is(true) || other.Is(true))
            {
                return(TRUE);
            }
            else if (this.Is(false))
            {
                return(other);
            }
            else if (other.Is(false))
            {
                return(this);
            }
            else if (conds.Contains(other))
            {
                // Reduce ((p1 & ... & pn)) | pi to pi
                return(other);
            }
            else if (other is Disj)
            {
                // TODO: This doesn't preserve order of disjuncts:
                return(other.Or(this));
            }
            else if (other is Conj)
            {
                if ((other as Conj).conds.Contains(this))
                {
                    // Reduce (pi | (p1 & ... & pn)) to pi
                    return(this);
                }
                else
                {
                    HashList <PathCond> intersect = HashList <PathCond> .Intersection(this.conds, (other as Conj).conds);

                    if (intersect.Count > 0)
                    {
                        // Reduce (p1 & ... & pn & q1 & ... & qm) | (p1 & ... & pn & r1 & ... & rk)
                        // to (p1 & ... & pn & (q1 & ... & qm | r1 & ... & rk).
                        // The pi go in intersect, qi in thisRest, and ri in otherRest.
                        HashList <PathCond> thisRest = HashList <PathCond> .Difference(this.conds, intersect);

                        HashList <PathCond> otherRest = HashList <PathCond> .Difference((other as Conj).conds, intersect);

                        // This recursion terminates because thisRest is smaller than this.conds
                        intersect.Add(Conj.Make(thisRest.ToArray()).Or(Conj.Make(otherRest.ToArray())));
                        return(Conj.Make(intersect.ToArray()));
                    }
                    else
                    {
                        return(Disj.Make(AddItem(this.conds, other)));
                    }
                }
            }
            else
            {
                return(Disj.Make(this, other));
            }
        }
예제 #2
0
        public void ComputeEvalConds()
        {
            const int THRESHOLD = 30;
            // Compute evaluation condition for each cell
            IDictionary <FullCellAddr, PathCond> evalConds = new Dictionary <FullCellAddr, PathCond>();

            evalConds[outputCell] = PathCond.TRUE;
            // The outputCell is also the first ccell processed below
            for (int i = programList.Count - 1; i >= 0; i--)
            {
                ComputeCell ccell     = programList[i];
                int         bound     = THRESHOLD;
                bool        isSerious = ccell.expr.IsSerious(ref bound);
                PathCond    evalCond  = evalConds[ccell.cellAddr];
                // Console.WriteLine("evalConds[{0}{1}] = {2}\n", casv.cellAddr, isSerious ? "" : ":TRIVIAL", evalCond);
                if (isSerious && !evalCond.Is(true))
                {
                    Console.WriteLine("Setting EvalCond[{0}] = {1}", ccell.cellAddr, evalCond);
                    ccell.EvalCond = evalCond.ToCGExpr();
                }
                ccell.expr.EvalCond(evalCond, evalConds, caches);
            }
        }