  public void parse(final Builder builder) throws IOException {
    builder.startDoc(token(filename));
    final Stack<NodeIterator> stack = new Stack<NodeIterator>();
    stack.push(new NodeIterator(root));
    while(!stack.empty()) {
      final NodeIterator ni = stack.peek();
      if(ni.more()) {
        final Node n = ni.curr();
        if(n instanceof Element) {
          stack.push(new NodeIterator(n));
          final NamedNodeMap at = n.getAttributes();
          final int as = at.getLength();
          atts.reset();
          for(int a = 0; a < as; a++) {
            atts.add(token(at.item(a).getNodeName()),
                token(at.item(a).getNodeValue()));
          }
          builder.startElem(token(n.getNodeName()), atts);
        } else if(n instanceof Text) {
          builder.text(new TokenBuilder(n.getNodeValue()));
        } else if(n instanceof Comment) {
          builder.comment(new TokenBuilder(n.getNodeValue()));
        } else if(n instanceof ProcessingInstruction) {
          builder.pi(new TokenBuilder(n.getNodeName() + ' ' +
              n.getNodeValue()));
          builder.text(new TokenBuilder(n.getNodeValue()));
        }
        nodes++;
      } else {
        stack.pop();
        if(stack.empty()) break;
        builder.endElem(token(stack.peek().curr().getNodeName()));
      }
    }
    builder.endDoc();
  }

  public void parse(final Builder builder) throws IOException {
    builder.startDoc(token(filename));
    final Stack<NodeIterator> stack = new Stack<NodeIterator>();
    stack.push(new NodeIterator(root));
    while(!stack.empty()) {
      final NodeIterator ni = stack.peek();
      if(ni.more()) {
        final Node n = ni.curr();
        if(n instanceof Element) {
          stack.push(new NodeIterator(n));
          final NamedNodeMap at = n.getAttributes();
          final int as = at.getLength();
          atts.reset();
          for(int a = 0; a < as; a++) {
            final byte[] att = token(at.item(a).getNodeName());
            if (eq(att, XMLNS)) {
              builder.startNS(EMPTY, token(at.item(a).getNodeValue()));
            } else if (eq(att, XMLNSC)) {
              builder.startNS(substring(att, 6), 
                  token(at.item(a).getNodeValue()));
            } else {
              atts.add(att, token(at.item(a).getNodeValue()));
            }
          }
          builder.startElem(token(n.getNodeName()), atts);
        } else if(n instanceof Text) {
          builder.text(new TokenBuilder(n.getNodeValue()));
        } else if(n instanceof Comment) {
          builder.comment(new TokenBuilder(n.getNodeValue()));
        } else if(n instanceof ProcessingInstruction) {
          builder.pi(new TokenBuilder(n.getNodeName() + ' ' +
              n.getNodeValue()));
          builder.text(new TokenBuilder(n.getNodeValue()));
        }
        nodes++;
      } else {
        stack.pop();
        if(stack.empty()) break;
        builder.endElem(token(stack.peek().curr().getNodeName()));
      }
    }
    builder.endDoc();
  }
