public static int GetCount(ICode countReferences, ICode root) { var v = new VisitorContToCounter(countReferences); v.Visit(root); return(v.Count); }
protected override ICode VisitContinuation(StmtContinuation s) { if (!s.LeaveProtectedRegion) { // Must never substitute when leaving protected region. // This would change which statements were inside the try/catch/finally region if (s.To.StmtType == Stmt.NodeType.Continuation && !((StmtContinuation)s.To).LeaveProtectedRegion) { var newCont = new StmtContinuation(s.Ctx, ((StmtContinuation)s.To).To, false); return(this.Visit(newCont)); } var count = VisitorContToCounter.GetCount(s.To, this.root); if (count == 1) { return(this.Visit(s.To)); } } return(base.VisitContinuation(s)); }
public static ICode V(ICode ast) { var ctx = ast.Ctx; var blockInfo = VisitorSubstituteIrreducable.FindSuitableBlocks.GetInfo(ast); var bInfo = blockInfo.Select(x => new { toCount = VisitorContToCounter.GetCount(x.Key, ast), ast = x.Key, codeCount = x.Value.numICodes, }).ToArray(); var block = bInfo.Where(x => x.toCount >= 2).OrderBy(x => x.toCount * x.codeCount).FirstOrDefault(); if (block == null) { return(ast); } var phis = new Dictionary <Expr, Expr>(); var blockCopies = Enumerable.Range(0, block.toCount - 1) .Select(x => { var v = new VisitorDuplicateCode(); var ret = v.Visit(block.ast); phis = phis.Merge(v.phiMap, (a, b) => new ExprVarPhi(ctx) { Exprs = new[] { a, b } }); return(ret); }) .Concat(block.ast) .ToArray(); var contTos = VisitorFindContinuationsRecursive.Get(ast).Where(x => x.To == block.ast).ToArray(); for (int i = 0; i < contTos.Length; i++) { var contTo = contTos[i]; var blockCopy = blockCopies[i]; ast = VisitorReplace.V(ast, contTo, blockCopy); } ast = VisitorReplaceExprUse.V(ast, phis); return(ast); }
public static int GetCount(ICode countReferences, ICode root) { var v = new VisitorContToCounter(countReferences); v.Visit(root); return v.Count; }