Beispiel #1
0
        public void PropagatePrecondition(Func <string, Implementation> NameToImpl, Action <string, IWeight> SetPrecondition)
        {
            foreach (var node in Nodes)
            {
                node.weight = iw.Zero(impl);
            }
            entryNode.weight = precondition;

            var worklist = new SortedSet <Node>(entryNode);

            worklist.Add(entryNode);

            while (worklist.Any())
            {
                var node = worklist.First();
                worklist.Remove(node);

                foreach (var edge in node.Successors)
                {
                    var c = edge.PropagatePrecondition(ProcSummary, NameToImpl, SetPrecondition);
                    if (c)
                    {
                        worklist.Add(edge.tgt);
                    }
                }
            }
        }
Beispiel #2
0
        public IntraGraph(Implementation impl, IWeight iw, Func <string, IWeight> ProcSummary)
        {
            this.impl         = impl;
            this.Id           = impl.Name;
            this.ProcSummary  = ProcSummary;
            priority          = 0;
            idToNode          = new Dictionary <string, Node>();
            Nodes             = new List <Node>();
            Edges             = new List <Edge>();
            calleeToEdgeSrc   = new Dictionary <string, HashSet <Node> >();
            this.iw           = iw;
            this.summary      = iw.Zero(impl);
            this.precondition = iw.Zero(impl);

            returnNodes         = new List <Node>();
            summaryChanged      = false;
            preconditionChanged = false;
            computedBefore      = false;

            // Create nodes
            foreach (var block in impl.Blocks)
            {
                var n1 = new Node(block.Label + "::in", iw.Zero(impl));
                var n2 = new Node(block.Label + "::out", iw.Zero(impl));
                Nodes.Add(n1);
                Nodes.Add(n2);

                var edge = new Edge(n1, n2, block.Cmds.OfType <Cmd>());
                n1.AddEdge(edge);
                n2.AddEdge(edge);
                Edges.Add(edge);

                // return nodes
                if (block.TransferCmd is ReturnCmd)
                {
                    returnNodes.Add(n2);
                }

                // calls
                foreach (var callee in edge.Callees)
                {
                    if (!calleeToEdgeSrc.ContainsKey(callee))
                    {
                        calleeToEdgeSrc.Add(callee, new HashSet <Node>());
                    }
                    calleeToEdgeSrc[callee].Add(n1);
                }
            }

            Nodes.Iter(n => idToNode.Add(n.Id, n));
            entryNode = idToNode[impl.Blocks[0].Label + "::in"];

            // connecting edges
            foreach (var block in impl.Blocks)
            {
                var gc = block.TransferCmd as GotoCmd;
                if (gc == null)
                {
                    continue;
                }

                var src = idToNode[block.Label + "::out"];

                var edges = gc.labelNames
                            .OfType <string>()
                            .Select(s => idToNode[s + "::in"])
                            .Select(tgt => new Edge(src, tgt, new Cmd[] { }));

                edges.Iter(e => { Edges.Add(e); e.src.AddEdge(e); e.tgt.AddEdge(e); });
            }

            // Compute priorities
            var sccs = new StronglyConnectedComponents <Node>(Nodes,
                                                              new Adjacency <Node>(n => n.Successors.Select(e => e.tgt)),
                                                              new Adjacency <Node>(n => n.Predecessors.Select(e => e.src)));

            sccs.Compute();

            int p = 0;

            foreach (var scc in sccs)
            {
                scc.Iter(n => n.priority = p);
                p++;
            }
        }