public void buildMonitorFlags() {

    for (Statement st : stats) {
      st.buildMonitorFlags();
    }

    switch (type) {
      case TYPE_BASICBLOCK:
        BasicBlockStatement bblock = (BasicBlockStatement) this;
        InstructionSequence seq = bblock.getBlock().getSeq();

        if (seq != null && seq.length() > 0) {
          for (int i = 0; i < seq.length(); i++) {
            if (seq.getInstr(i).opcode == CodeConstants.opc_monitorexit) {
              containsMonitorExit = true;
              break;
            }
          }
          isMonitorEnter = (seq.getLastInstr().opcode == CodeConstants.opc_monitorenter);
        }
        break;
      case TYPE_SEQUENCE:
      case TYPE_IF:
        containsMonitorExit = false;
        for (Statement st : stats) {
          containsMonitorExit |= st.isContainsMonitorExit();
        }

        break;
      case TYPE_SYNCRONIZED:
      case TYPE_ROOT:
      case TYPE_GENERAL:
        break;
      default:
        containsMonitorExit = false;
        for (Statement st : stats) {
          containsMonitorExit |= st.isContainsMonitorExit();
        }
    }
  }
  public void collapseNodesToStatement(Statement stat) {

    Statement head = stat.getFirst();
    Statement post = stat.getPost();

    VBStyleCollection<Statement, Integer> setNodes = stat.getStats();

    // post edges
    if (post != null) {
      for (StatEdge edge : post.getEdges(STATEDGE_DIRECT_ALL, DIRECTION_BACKWARD)) {
        if (stat.containsStatementStrict(edge.getSource())) {
          edge.getSource().changeEdgeType(DIRECTION_FORWARD, edge, StatEdge.TYPE_BREAK);
          stat.addLabeledEdge(edge);
        }
      }
    }

    // regular head edges
    for (StatEdge prededge : head.getAllPredecessorEdges()) {

      if (prededge.getType() != StatEdge.TYPE_EXCEPTION
          && stat.containsStatementStrict(prededge.getSource())) {
        prededge.getSource().changeEdgeType(DIRECTION_FORWARD, prededge, StatEdge.TYPE_CONTINUE);
        stat.addLabeledEdge(prededge);
      }

      head.removePredecessor(prededge);
      prededge.getSource().changeEdgeNode(DIRECTION_FORWARD, prededge, stat);
      stat.addPredecessor(prededge);
    }

    if (setNodes.containsKey(first.id)) {
      first = stat;
    }

    // exception edges
    Set<Statement> setHandlers =
        new HashSet<Statement>(head.getNeighbours(StatEdge.TYPE_EXCEPTION, DIRECTION_FORWARD));
    for (Statement node : setNodes) {
      setHandlers.retainAll(node.getNeighbours(StatEdge.TYPE_EXCEPTION, DIRECTION_FORWARD));
    }

    if (!setHandlers.isEmpty()) {

      for (StatEdge edge : head.getEdges(StatEdge.TYPE_EXCEPTION, DIRECTION_FORWARD)) {
        Statement handler = edge.getDestination();

        if (setHandlers.contains(handler)) {
          if (!setNodes.containsKey(handler.id)) {
            stat.addSuccessor(new StatEdge(stat, handler, edge.getExceptions()));
          }
        }
      }

      for (Statement node : setNodes) {
        for (StatEdge edge : node.getEdges(StatEdge.TYPE_EXCEPTION, DIRECTION_FORWARD)) {
          if (setHandlers.contains(edge.getDestination())) {
            node.removeSuccessor(edge);
          }
        }
      }
    }

    if (post != null
        && !stat.getNeighbours(StatEdge.TYPE_EXCEPTION, DIRECTION_FORWARD)
            .contains(post)) { // TODO: second condition redundant?
      stat.addSuccessor(new StatEdge(StatEdge.TYPE_REGULAR, stat, post));
    }

    // adjust statement collection
    for (Statement st : setNodes) {
      stats.removeWithKey(st.id);
    }

    stats.addWithKey(stat, stat.id);

    stat.setAllParent();
    stat.setParent(this);

    stat.buildContinueSet();
    // monitorenter and monitorexit
    stat.buildMonitorFlags();

    if (stat.type == TYPE_SWITCH) {
      // special case switch, sorting leaf nodes
      ((SwitchStatement) stat).sortEdgesAndNodes();
    }
  }