示例#1
0
 @Override
 public String det() {
   final String path = input.io().path();
   return path.isEmpty()
       ? Util.info(LINE_X, input.line())
       : Util.info(SCANPOS_X_X, input.io().path(), input.line());
 }
示例#2
0
  /**
   * Scans an external ID.
   *
   * @param f full flag
   * @param r root flag
   * @return id
   * @throws IOException I/O exception
   */
  private byte[] externalID(final boolean f, final boolean r) throws IOException {
    byte[] cont = null;
    final boolean pub = consume(PUBLIC);
    if (pub || consume(SYSTEM)) {
      checkS();
      if (pub) {
        pubidLit();
        if (f) checkS();
      }
      final int qu = consume(); // [11]
      if (qu == '\'' || qu == '"') {
        int ch;
        final TokenBuilder tok = new TokenBuilder();
        while ((ch = nextChar()) != qu) tok.add(ch);
        if (!f) return null;
        final String name = string(tok.finish());
        if (!dtd && r) return cont;

        final XMLInput tin = input;
        try {
          final IO file = input.io().merge(name);
          cont = file.read();
        } catch (final IOException ex) {
          Util.debug(ex);
          // skip unknown DTDs/entities
          cont = new byte[] {'?'};
        }
        input = new XMLInput(new IOContent(cont, name));

        if (consume(XDECL)) {
          check(XML);
          s();
          if (version()) checkS();
          s();
          if (encoding() == null) error(TEXTENC);
          ch = nextChar();
          if (s(ch)) ch = nextChar();
          if (ch != '?') error(WRONGCHAR, '?', ch);
          ch = nextChar();
          if (ch != '>') error(WRONGCHAR, '>', ch);
          cont = Arrays.copyOfRange(cont, input.pos(), cont.length);
        }

        s();
        if (r) {
          extSubsetDecl();
          if (!consume((char) 0)) error(INVEND);
        }
        input = tin;
      } else {
        if (f) error(SCANQUOTE, (char) qu);
        prev(1);
      }
    }
    return cont;
  }
示例#3
0
 /**
  * Reads next character or throws an exception if all bytes have been read.
  *
  * @return next character
  * @throws IOException I/O exception
  */
 private int consume() throws IOException {
   while (true) {
     final int ch = input.read();
     if (ch == -1) return 0;
     if (ch == '%' && pe) { // [69]
       final byte[] key = name(true);
       final byte[] val = pents.get(key);
       if (val == null) error(UNKNOWNPE, key);
       check(';');
       input.add(val, true);
     } else {
       return ch;
     }
   }
 }
示例#4
0
 /**
  * Scans an attribute value. [10]
  *
  * @param ch current character
  * @throws IOException I/O exception
  */
 private void attValue(final int ch) throws IOException {
   boolean wrong = false;
   int c = ch;
   do {
     if (c == 0) error(ATTCLOSE, (char) c);
     wrong |= c == '\'' || c == '"';
     if (c == '<') error(wrong ? ATTCLOSE : ATTCHAR, (char) c);
     if (c == 0x0A) c = ' ';
     if (c == '&') {
       // verify...
       final byte[] r = ref(true);
       if (r.length == 1) token.add(r);
       else if (!input.add(r, false)) error(RECENT);
     } else {
       token.add(c);
     }
   } while ((c = consume()) != quote);
 }
示例#5
0
  /**
   * Initializes the scanner.
   *
   * @param f input file
   * @param pr database properties
   * @param frag allow parsing of document fragment
   * @throws IOException I/O exception
   */
  XMLScanner(final IO f, final Prop pr, final boolean frag) throws IOException {
    input = new XMLInput(f);
    fragment = frag;

    try {
      for (int e = 0; e < ENTITIES.length; e += 2) {
        ents.add(token(ENTITIES[e]), token(ENTITIES[e + 1]));
      }
      dtd = pr.is(Prop.DTD);
      chop = pr.is(Prop.CHOP);

      String enc = null;
      // process document declaration...
      if (consume(DOCDECL)) {
        if (s()) {
          if (!version()) error(DECLSTART);
          boolean s = s();
          enc = encoding();
          if (enc != null) {
            if (!s) error(WSERROR);
            s = s();
          }
          if (sddecl() != null && !s) error(WSERROR);
          s();
          final int ch = nextChar();
          if (ch != '?' || nextChar() != '>') error(DECLWRONG);
        } else {
          prev(5);
        }
      }
      encoding = enc == null ? UTF8 : enc;

      if (!fragment) {
        final int n = consume();
        if (!s(n)) {
          if (n != '<') error(BEFOREROOT);
          prev(1);
        }
      }
    } catch (final IOException ex) {
      input.close();
      throw ex;
    }
  }
示例#6
0
 /**
  * Scans XML text.
  *
  * @param ch current character
  * @throws IOException I/O exception
  */
 private void content(final int ch) throws IOException {
   type = Type.TEXT;
   boolean f = true;
   int c = ch;
   while (c != 0) {
     if (c != '<') {
       if (c == '&') {
         // scan entity
         final byte[] r = ref(true);
         if (r.length == 1) token.add(r);
         else if (!input.add(r, false)) error(RECENT);
       } else {
         if (c == ']') {
           // ']]>' not allowed in content
           if (consume() == ']') {
             if (consume() == '>') error(CONTCDATA);
             prev(1);
           }
           prev(1);
         }
         // add character to cached content
         token.add(c);
       }
     } else {
       if (!f && !isCDATA()) {
         text = false;
         prev(1);
         if (chop) token.trim();
         return;
       }
       cDATA();
     }
     c = consume();
     f = false;
   }
   // end of file
   if (!fragment) {
     if (!ws(token.finish())) error(AFTERROOT);
     type = Type.EOF;
   }
 }
示例#7
0
 /**
  * Scans a document encoding.
  *
  * @return encoding
  * @throws IOException I/O exception
  */
 private String encoding() throws IOException {
   if (!consume(ENCOD)) {
     if (fragment) error(TEXTENC);
     return null;
   }
   s();
   check('=');
   s();
   final TokenBuilder enc = new TokenBuilder();
   final int d = qu();
   int ch = nextChar();
   if (letter(ch) && ch != '_') {
     while (letterOrDigit(ch) || ch == '.' || ch == '-') {
       enc.add(ch);
       ch = nextChar();
     }
     prev(1);
   }
   check((char) d);
   if (enc.isEmpty()) error(DECLENCODE, enc);
   final String e = string(enc.finish());
   input.encoding(e);
   return e;
 }
示例#8
0
 /**
  * Jumps the specified number of characters back.
  *
  * @param p number of characters
  */
 private void prev(final int p) {
   input.prev(p);
 }
示例#9
0
 /**
  * Finishes file scanning.
  *
  * @throws IOException I/O exception
  */
 void close() throws IOException {
   input.close();
   if (!fragment && prolog) error(DOCEMPTY);
 }
示例#10
0
 @Override
 public double prog() {
   final double l = input.length();
   return l <= 0 ? 0 : input.pos() / l;
 }