comparison graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/NodeUtil.java @ 17399:5787218bad91

Truffle: implemented recursive node iterator and node streams for the graal runtime.
author Christian Humer <christian.humer@gmail.com>
date Thu, 09 Oct 2014 17:25:18 +0200
parents 846c059e3ecf
children c88ab4f1f04a
comparison
equal deleted inserted replaced
17398:9e1ec84d2899 17399:5787218bad91
342 342
343 static Iterator<Node> makeIterator(Node node) { 343 static Iterator<Node> makeIterator(Node node) {
344 return NodeClass.get(node.getClass()).makeIterator(node); 344 return NodeClass.get(node.getClass()).makeIterator(node);
345 } 345 }
346 346
347 public static Iterator<Node> makeRecursiveIterator(Node node) {
348 return new RecursiveNodeIterator(node);
349 }
350
351 private final static class RecursiveNodeIterator implements Iterator<Node> {
352 private final List<Iterator<Node>> iteratorStack = new ArrayList<>();
353
354 public RecursiveNodeIterator(final Node node) {
355 iteratorStack.add(new Iterator<Node>() {
356
357 private boolean visited;
358
359 public void remove() {
360 throw new UnsupportedOperationException();
361 }
362
363 public Node next() {
364 if (visited) {
365 throw new NoSuchElementException();
366 }
367 visited = true;
368 return node;
369 }
370
371 public boolean hasNext() {
372 return !visited;
373 }
374 });
375 }
376
377 public boolean hasNext() {
378 return peekIterator() != null;
379 }
380
381 public Node next() {
382 Iterator<Node> iterator = peekIterator();
383 if (iterator == null) {
384 throw new NoSuchElementException();
385 }
386
387 Node node = iterator.next();
388 if (node != null) {
389 Iterator<Node> childIterator = makeIterator(node);
390 if (childIterator.hasNext()) {
391 iteratorStack.add(childIterator);
392 }
393 }
394 return node;
395 }
396
397 private Iterator<Node> peekIterator() {
398 int tos = iteratorStack.size() - 1;
399 while (tos >= 0) {
400 Iterator<Node> iterable = iteratorStack.get(tos);
401 if (iterable.hasNext()) {
402 return iterable;
403 } else {
404 iteratorStack.remove(tos--);
405 }
406 }
407 return null;
408 }
409
410 public void remove() {
411 throw new UnsupportedOperationException();
412 }
413 }
414
347 private static long[] toLongArray(List<Long> list) { 415 private static long[] toLongArray(List<Long> list) {
348 long[] array = new long[list.size()]; 416 long[] array = new long[list.size()];
349 for (int i = 0; i < list.size(); i++) { 417 for (int i = 0; i < list.size(); i++) {
350 array[i] = list.get(i); 418 array[i] = list.get(i);
351 } 419 }
604 }); 672 });
605 return nodeList; 673 return nodeList;
606 } 674 }
607 675
608 public static int countNodes(Node root) { 676 public static int countNodes(Node root) {
609 return countNodes(root, null, false); 677 Iterator<Node> nodeIterator = makeRecursiveIterator(root);
678 int count = 0;
679 while (nodeIterator.hasNext()) {
680 nodeIterator.next();
681 count++;
682 }
683 return count;
610 } 684 }
611 685
612 public static int countNodes(Node root, NodeCountFilter filter) { 686 public static int countNodes(Node root, NodeCountFilter filter) {
613 return countNodes(root, filter, false); 687 Iterator<Node> nodeIterator = makeRecursiveIterator(root);
614 } 688 int count = 0;
615 689 while (nodeIterator.hasNext()) {
616 public static int countNodes(Node root, NodeCountFilter filter, boolean visitInlinedCallNodes) { 690 Node node = nodeIterator.next();
617 NodeCountVisitor nodeCount = new NodeCountVisitor(filter, visitInlinedCallNodes); 691 if (node != null && filter.isCounted(node)) {
618 root.accept(nodeCount); 692 count++;
619 return nodeCount.nodeCount; 693 }
694 }
695 return count;
620 } 696 }
621 697
622 public interface NodeCountFilter { 698 public interface NodeCountFilter {
623 699
624 boolean isCounted(Node node); 700 boolean isCounted(Node node);
625
626 }
627
628 private static final class NodeCountVisitor implements NodeVisitor {
629
630 private final boolean visitInlinedCallNodes;
631 int nodeCount;
632 private final NodeCountFilter filter;
633
634 private NodeCountVisitor(NodeCountFilter filter, boolean visitInlinedCallNodes) {
635 this.filter = filter;
636 this.visitInlinedCallNodes = visitInlinedCallNodes;
637 }
638
639 @Override
640 public boolean visit(Node node) {
641 if (filter == null || filter.isCounted(node)) {
642 nodeCount++;
643 }
644
645 if (visitInlinedCallNodes && node instanceof DirectCallNode) {
646 DirectCallNode call = (DirectCallNode) node;
647 if (call.isInlined()) {
648 Node target = ((RootCallTarget) call.getCurrentCallTarget()).getRootNode();
649 if (target != null) {
650 target.accept(this);
651 }
652 }
653 }
654
655 return true;
656 }
657 701
658 } 702 }
659 703
660 public static String printCompactTreeToString(Node node) { 704 public static String printCompactTreeToString(Node node) {
661 StringWriter out = new StringWriter(); 705 StringWriter out = new StringWriter();