public void BlockSurroundedIf() { const int COUNT = 7; Parser parser = new Parser(Path.Combine(AppDomain.CurrentDomain.BaseDirectory, @"Data\BlockSurroundedIf.gngr")); parser.parse(); ASTVisitor astv = new ASTVisitor(parser.ast); TestVisitor tv = new TestVisitor(astv.cfg); // create new instance to fool compiler CFGEntry entry = new CFGEntry(); CFGBasicBlock b1 = new CFGBasicBlock(); CFGBasicBlock b2 = new CFGBasicBlock(); CFGBasicBlock b3 = new CFGBasicBlock(); CFGBasicBlock b4 = new CFGBasicBlock(); CFGBasicBlock b5 = new CFGBasicBlock(); for (int i = 0; i < COUNT; i++) { switch (i) { case 0: entry = (CFGEntry)tv.visitedNodes[i]; Assert.IsInstanceOfType(entry, typeof(CFGEntry), $"{i}/1"); break; case 1: b1 = (CFGBasicBlock)tv.visitedNodes[i]; Assert.IsInstanceOfType(b1, typeof(CFGBasicBlock), $"{i}/1"); Assert.AreEqual(entry, b1.parents[0], $"{i}/1"); break; case 2: b2 = (CFGBasicBlock)tv.visitedNodes[i]; Assert.IsInstanceOfType(b2, typeof(CFGBasicBlock), $"{i}/1"); Assert.AreEqual(b1, b2.parents[0], $"{i}/2"); break; case 3: b3 = (CFGBasicBlock)tv.visitedNodes[i]; Assert.IsInstanceOfType(b3, typeof(CFGBasicBlock), $"{i}/1"); Assert.AreEqual(b2, b3.parents[0], $"{i}/2"); break; case 4: b4 = (CFGBasicBlock)tv.visitedNodes[i]; Assert.IsInstanceOfType(b4, typeof(CFGBasicBlock), $"{i}/1"); Assert.AreEqual(b3, b4.parents[0], $"{i}/2"); Assert.AreEqual(b2, b4.parents[1], $"{i}/3"); break; case 5: b5 = (CFGBasicBlock)tv.visitedNodes[i]; Assert.IsInstanceOfType(b5, typeof(CFGBasicBlock), $"{i}/1"); Assert.AreEqual(b4, b5.parents[0], $"{i}/2"); Assert.AreEqual(b1, b5.parents[1], $"{i}/3"); break; case 6: CFGExit exit = (CFGExit)tv.visitedNodes[i]; Assert.IsInstanceOfType(exit, typeof(CFGExit), $"{i}/1"); Assert.AreEqual(b5, exit.parents[0], $"{i}/2"); break; } } }
public void visitWhile(While w) { // assume the header is the current node CFGBasicBlock whileHeader = (CFGBasicBlock)this.currentNode; addStatement(w); visitChildren(w); // exiting the statement list // we have to link whatever is the current basic block // back to the head basic block for this while this.currentNode.add(whileHeader); }
public void visitStatementList(StatementList sl) { if (sl.Count() > 0) { // use this to determine if we need to link the node succeeding // this statement list to be linked to it bool link = true; Node linkNode; // the basic block representing the current point in the statement list CFGBasicBlock slbb = new CFGBasicBlock(); linkNode = slbb; // add this basic block as the child to the current node // and then set it as the current node this.currentNode.add(slbb); this.currentNode = slbb; for (int i = 0; i < sl.Count(); i++) { // if this statement list has been broken // create a new basic block and link it if (this.currentNode != slbb) { // do not link this block to the successer of the statement list link = false; // if there are more statements to come CFGBasicBlock bb = new CFGBasicBlock(); // we've just exited out of some kind of branch, make this new block a child of it this.currentNode.add(bb); // now make this new block a child of the original statement list slbb.add(bb); // now the new block becomes the representative statement list slbb = bb; this.currentNode = bb; // why does this work????? clearLinkNodes(); } // handle the next statement Node nextStatement = sl.get(i); if (nextStatement.GetType() == typeof(While)) { // a while statement needs a basic block of its own CFGBasicBlock bb = new CFGBasicBlock(); this.currentNode.add(bb); slbb = bb; this.currentNode = slbb; } sl.get(i).accept(this); } if (link == true) { linkNodes.Add(linkNode); } } }
private void addStatement(Node statement) { CFGBasicBlock currentBasicBlock = currentNode as CFGBasicBlock; currentBasicBlock.addStatement(statement); }
public void visitBasicBlock(CFGBasicBlock bb) { visitCollection(bb); }