1 57 58 package org.enhydra.apache.xerces.readers; 59 60 import java.io.Reader ; 61 import java.util.Vector ; 62 63 import org.enhydra.apache.xerces.framework.XMLErrorReporter; 64 import org.enhydra.apache.xerces.utils.CharDataChunk; 65 import org.enhydra.apache.xerces.utils.ImplementationMessages; 66 import org.enhydra.apache.xerces.utils.QName; 67 import org.enhydra.apache.xerces.utils.StringHasher; 68 import org.enhydra.apache.xerces.utils.StringPool; 69 import org.enhydra.apache.xerces.utils.XMLCharacterProperties; 70 71 77 public class StreamingCharReader extends XMLEntityReader { 78 79 88 public StreamingCharReader(XMLEntityHandler entityHandler, XMLErrorReporter errorReporter, boolean sendCharDataAsCharArray, Reader reader, StringPool stringPool) throws Exception { 89 super(entityHandler, errorReporter, sendCharDataAsCharArray); 90 fStringPool = stringPool; 91 fCharacterStream = reader; 92 fCurrentChunk = CharDataChunk.createChunk(fStringPool, null); 93 loadFirstChar(); 94 } 95 96 110 protected void deferException(int errorCode, Object [] args, int offset) { 111 if (fDeferredErrors == null) 112 fDeferredErrors = new Vector (); 113 DeferredError de = new DeferredError(errorCode, args, offset); 114 fDeferredErrors.addElement(de); 115 } 116 117 125 protected XMLEntityHandler.EntityReader changeReaders() throws Exception { 126 XMLEntityHandler.EntityReader nextReader = super.changeReaders(); 127 fCurrentChunk.releaseChunk(); 128 fCurrentChunk = null; 129 return nextReader; 130 } 131 132 145 153 public void append(XMLEntityHandler.CharBuffer charBuffer, int offset, int length) { 154 fCurrentChunk.append(charBuffer, offset, length); 155 } 156 157 165 public int addString(int offset, int length) { 166 if (length == 0) 167 return 0; 168 return fCurrentChunk.addString(offset, length); 169 } 170 171 179 public int addSymbol(int offset, int length) { 180 if (length == 0) 181 return 0; 182 return fCurrentChunk.addSymbol(offset, length, 0); 183 } 184 185 188 public boolean lookingAtChar(char chr, boolean skipPastChar) throws Exception { 189 int ch = fMostRecentChar; 190 if (ch != chr) { 191 if (ch == 0) { 192 if (atEOF(fCurrentOffset + 1)) { 193 return changeReaders().lookingAtChar(chr, skipPastChar); 194 } 195 } 196 return false; 197 } 198 if (skipPastChar) { 199 fCharacterCounter++; 200 loadNextChar(); 201 } 202 return true; 203 } 204 205 208 public boolean lookingAtValidChar(boolean skipPastChar) throws Exception { 209 int ch = fMostRecentChar; 210 if (ch < 0xD800) { 211 if (ch >= 0x20 || ch == 0x09) { 212 if (skipPastChar) { 213 fCharacterCounter++; 214 loadNextChar(); 215 } 216 return true; 217 } 218 if (ch == 0x0A) { 219 if (skipPastChar) { 220 fLinefeedCounter++; 221 fCharacterCounter = 1; 222 loadNextChar(); 223 } 224 return true; 225 } 226 if (ch == 0) { 227 if (atEOF(fCurrentOffset + 1)) { 228 return changeReaders().lookingAtValidChar(skipPastChar); 229 } 230 } 231 return false; 232 } 233 if (ch > 0xFFFD) { 234 return false; 235 } 236 if (ch < 0xDC00) { 237 CharDataChunk savedChunk = fCurrentChunk; 238 int savedIndex = fCurrentIndex; 239 int savedOffset = fCurrentOffset; 240 ch = loadNextChar(); 241 boolean valid = (ch >= 0xDC00 && ch < 0xE000); 242 if (!valid || !skipPastChar) { 243 fCurrentChunk = savedChunk; 244 fCurrentIndex = savedIndex; 245 fCurrentOffset = savedOffset; 246 fMostRecentData = savedChunk.toCharArray(); 247 fMostRecentChar = fMostRecentData[savedIndex] & 0xFFFF; 248 return valid; 249 } 250 } else if (ch < 0xE000) { 251 return false; 252 } 253 if (skipPastChar) { 254 fCharacterCounter++; 255 loadNextChar(); 256 } 257 return true; 258 } 259 260 263 public boolean lookingAtSpace(boolean skipPastChar) throws Exception { 264 int ch = fMostRecentChar; 265 if (ch > 0x20) 266 return false; 267 if (ch == 0x20 || ch == 0x09) { 268 if (!skipPastChar) 269 return true; 270 fCharacterCounter++; 271 } else if (ch == 0x0A) { 272 if (!skipPastChar) 273 return true; 274 fLinefeedCounter++; 275 fCharacterCounter = 1; 276 } else { 277 if (ch == 0) { if (atEOF(fCurrentOffset + 1)) { 279 return changeReaders().lookingAtSpace(skipPastChar); 280 } 281 } 282 return false; 283 } 284 loadNextChar(); 285 return true; 286 } 287 288 291 public void skipToChar(char chr) throws Exception { 292 int ch = fMostRecentChar; 296 while (true) { 297 if (ch == chr) 298 return; 299 if (ch == 0) { 300 if (atEOF(fCurrentOffset + 1)) { 301 changeReaders().skipToChar(chr); 302 return; 303 } 304 fCharacterCounter++; 305 } else if (ch == 0x0A) { 306 fLinefeedCounter++; 307 fCharacterCounter = 1; 308 } else if (ch >= 0xD800 && ch < 0xDC00) { 309 fCharacterCounter++; 310 ch = loadNextChar(); 311 if (ch < 0xDC00 || ch >= 0xE000) 312 continue; 313 } else 314 fCharacterCounter++; 315 ch = loadNextChar(); 316 } 317 } 318 319 322 public void skipPastSpaces() throws Exception { 323 int ch = fMostRecentChar; 324 while (true) { 325 if (ch == 0x20 || ch == 0x09) { 326 fCharacterCounter++; 327 } else if (ch == 0x0A) { 328 fLinefeedCounter++; 329 fCharacterCounter = 1; 330 } else { 331 if (ch == 0 && atEOF(fCurrentOffset + 1)) 332 changeReaders().skipPastSpaces(); 333 return; 334 } 335 ch = loadNextChar(); 336 } 337 } 338 339 342 public void skipPastName(char fastcheck) throws Exception { 343 int ch = fMostRecentChar; 344 if (ch < 0x80) { 345 if (XMLCharacterProperties.fgAsciiInitialNameChar[ch] == 0) 346 return; 347 } else { 348 if (!fCalledCharPropInit) { 349 XMLCharacterProperties.initCharFlags(); 350 fCalledCharPropInit = true; 351 } 352 if ((XMLCharacterProperties.fgCharFlags[ch] & XMLCharacterProperties.E_InitialNameCharFlag) == 0) 353 return; 354 } 355 while (true) { 356 fCharacterCounter++; 357 ch = loadNextChar(); 358 if (fastcheck == ch) 359 return; 360 if (ch < 0x80) { 361 if (XMLCharacterProperties.fgAsciiNameChar[ch] == 0) 362 return; 363 } else { 364 if (!fCalledCharPropInit) { 365 XMLCharacterProperties.initCharFlags(); 366 fCalledCharPropInit = true; 367 } 368 if ((XMLCharacterProperties.fgCharFlags[ch] & XMLCharacterProperties.E_NameCharFlag) == 0) 369 return; 370 } 371 } 372 } 373 374 377 public void skipPastNmtoken(char fastcheck) throws Exception { 378 int ch = fMostRecentChar; 379 while (true) { 380 if (fastcheck == ch) 381 return; 382 if (ch < 0x80) { 383 if (XMLCharacterProperties.fgAsciiNameChar[ch] == 0) 384 return; 385 } else { 386 if (!fCalledCharPropInit) { 387 XMLCharacterProperties.initCharFlags(); 388 fCalledCharPropInit = true; 389 } 390 if ((XMLCharacterProperties.fgCharFlags[ch] & XMLCharacterProperties.E_NameCharFlag) == 0) 391 return; 392 } 393 fCharacterCounter++; 394 ch = loadNextChar(); 395 } 396 } 397 398 401 public boolean skippedString(char[] s) throws Exception { 402 int ch = fMostRecentChar; 403 if (ch != s[0]) 404 return false; 405 int length = s.length; 406 CharDataChunk dataChunk = fCurrentChunk; 407 int offset = fCurrentOffset; 408 int index = fCurrentIndex; 409 ch = loadNextChar(); 410 for (int i = 1; i < length; i++) { 411 if (ch != s[i]) { 412 fCurrentChunk = dataChunk; 413 fCurrentIndex = index; 414 fCurrentOffset = offset; 415 fMostRecentData = dataChunk.toCharArray(); 416 fMostRecentChar = fMostRecentData[index] & 0xFFFF; 417 return false; 418 } 419 ch = loadNextChar(); 420 } 421 fCharacterCounter += length; 422 return true; 423 } 424 425 428 public int scanInvalidChar() throws Exception { 429 int ch = fMostRecentChar; 430 if (ch == 0x0A) { 431 fLinefeedCounter++; 432 fCharacterCounter = 1; 433 loadNextChar(); 434 } else if (ch == 0) { 435 if (atEOF(fCurrentOffset + 1)) { 436 return changeReaders().scanInvalidChar(); 437 } 438 if (fDeferredErrors != null) { 439 for (int i = 0; i < fDeferredErrors.size(); i++) { 440 DeferredError de = (DeferredError)fDeferredErrors.elementAt(i); 441 if (de.offset == fCurrentIndex) { 442 fErrorReporter.reportError(fErrorReporter.getLocator(), 443 ImplementationMessages.XERCES_IMPLEMENTATION_DOMAIN, 444 de.errorCode, 445 0, 446 de.args, 447 XMLErrorReporter.ERRORTYPE_FATAL_ERROR); 448 fDeferredErrors.removeElementAt(i); 449 fCharacterCounter++; 450 loadNextChar(); 451 return -1; 452 } 453 } 454 } 455 fCharacterCounter++; 456 loadNextChar(); 457 } else { 458 fCharacterCounter++; 459 if (ch >= 0xD800 && ch < 0xDC00) { 460 int ch2 = loadNextChar(); 461 if (ch2 >= 0xDC00 && ch2 < 0xE000) { 462 ch = ((ch-0xD800)<<10)+(ch2-0xDC00)+0x10000; 463 loadNextChar(); 464 } 465 } else 466 loadNextChar(); 467 } 468 return ch; 469 } 470 471 474 public int scanCharRef(boolean hex) throws Exception { 475 int ch = fMostRecentChar; 476 if (ch == 0) { 477 if (atEOF(fCurrentOffset + 1)) { 478 return changeReaders().scanCharRef(hex); 479 } 480 return XMLEntityHandler.CHARREF_RESULT_INVALID_CHAR; 481 } 482 int num = 0; 483 if (hex) { 484 if (ch > 'f' || XMLCharacterProperties.fgAsciiXDigitChar[ch] == 0) 485 return XMLEntityHandler.CHARREF_RESULT_INVALID_CHAR; 486 num = ch - (ch < 'A' ? '0' : (ch < 'a' ? 'A' : 'a') - 10); 487 } else { 488 if (ch < '0' || ch > '9') 489 return XMLEntityHandler.CHARREF_RESULT_INVALID_CHAR; 490 num = ch - '0'; 491 } 492 fCharacterCounter++; 493 loadNextChar(); 494 boolean toobig = false; 495 while (true) { 496 ch = fMostRecentChar; 497 if (ch == 0) 498 break; 499 if (hex) { 500 if (ch > 'f' || XMLCharacterProperties.fgAsciiXDigitChar[ch] == 0) 501 break; 502 } else { 503 if (ch < '0' || ch > '9') 504 break; 505 } 506 fCharacterCounter++; 507 loadNextChar(); 508 if (hex) { 509 int dig = ch - (ch < 'A' ? '0' : (ch < 'a' ? 'A' : 'a') - 10); 510 num = (num << 4) + dig; 511 } else { 512 int dig = ch - '0'; 513 num = (num * 10) + dig; 514 } 515 if (num > 0x10FFFF) { 516 toobig = true; 517 num = 0; 518 } 519 } 520 if (ch != ';') 521 return XMLEntityHandler.CHARREF_RESULT_SEMICOLON_REQUIRED; 522 fCharacterCounter++; 523 loadNextChar(); 524 if (toobig) 525 return XMLEntityHandler.CHARREF_RESULT_OUT_OF_RANGE; 526 return num; 527 } 528 529 532 public int scanStringLiteral() throws Exception { 533 boolean single; 534 if (!(single = lookingAtChar('\'', true)) && !lookingAtChar('\"', true)) { 535 return XMLEntityHandler.STRINGLIT_RESULT_QUOTE_REQUIRED; 536 } 537 int offset = fCurrentOffset; 538 char qchar = single ? '\'' : '\"'; 539 while (!lookingAtChar(qchar, false)) { 540 if (!lookingAtValidChar(true)) { 541 return XMLEntityHandler.STRINGLIT_RESULT_INVALID_CHAR; 542 } 543 } 544 int stringIndex = addString(offset, fCurrentOffset - offset); 545 lookingAtChar(qchar, true); return stringIndex; 547 } 548 549 556 public int scanAttValue(char qchar, boolean asSymbol) throws Exception 557 { 558 int offset = fCurrentOffset; 559 while (true) { 560 if (lookingAtChar(qchar, false)) { 561 break; 562 } 563 if (lookingAtChar(' ', true)) { 564 continue; 565 } 566 if (lookingAtSpace(false)) { 567 return XMLEntityHandler.ATTVALUE_RESULT_COMPLEX; 568 } 569 if (lookingAtChar('&', false)) { 570 return XMLEntityHandler.ATTVALUE_RESULT_COMPLEX; 571 } 572 if (lookingAtChar('<', false)) { 573 return XMLEntityHandler.ATTVALUE_RESULT_LESSTHAN; 574 } 575 if (!lookingAtValidChar(true)) { 576 return XMLEntityHandler.ATTVALUE_RESULT_INVALID_CHAR; 577 } 578 } 579 int result = asSymbol ? addSymbol(offset, fCurrentOffset - offset) : addString(offset, fCurrentOffset - offset); 580 lookingAtChar(qchar, true); 581 return result; 582 } 583 584 591 public int scanEntityValue(int qchar, boolean createString) throws Exception 592 { 593 int offset = fCurrentOffset; 594 while (true) { 595 if (atEOF(fCurrentOffset + 1)) { 596 changeReaders(); 597 return XMLEntityHandler.ENTITYVALUE_RESULT_END_OF_INPUT; 598 } 599 if (qchar != -1 && lookingAtChar((char)qchar, false)) { 600 if (!createString) 601 return XMLEntityHandler.ENTITYVALUE_RESULT_FINISHED; 602 break; 603 } 604 if (lookingAtChar('&', false)) { 605 return XMLEntityHandler.ENTITYVALUE_RESULT_REFERENCE; 606 } 607 if (lookingAtChar('%', false)) { 608 return XMLEntityHandler.ENTITYVALUE_RESULT_PEREF; 609 } 610 if (!lookingAtValidChar(true)) { 611 return XMLEntityHandler.ENTITYVALUE_RESULT_INVALID_CHAR; 612 } 613 } 614 int result = addString(offset, fCurrentOffset - offset); 615 lookingAtChar((char)qchar, true); 616 return result; 617 } 618 619 622 public int scanName(char fastcheck) throws Exception { 623 int ch = fMostRecentChar; 624 if (ch < 0x80) { 625 if (XMLCharacterProperties.fgAsciiInitialNameChar[ch] == 0) 626 return -1; 627 } else { 628 if (!fCalledCharPropInit) { 629 XMLCharacterProperties.initCharFlags(); 630 fCalledCharPropInit = true; 631 } 632 if ((XMLCharacterProperties.fgCharFlags[ch] & XMLCharacterProperties.E_InitialNameCharFlag) == 0) 633 return -1; 634 } 635 int offset = fCurrentOffset; 636 fCharacterCounter++; 637 int hashcode = 0; 638 while (true) { 639 hashcode = StringHasher.hashChar(hashcode, ch); 640 ch = loadNextChar(); 641 if (fastcheck == ch) 642 break; 643 if (ch < 0x80) { 644 if (XMLCharacterProperties.fgAsciiNameChar[ch] == 0) 645 break; 646 } else { 647 if (!fCalledCharPropInit) { 648 XMLCharacterProperties.initCharFlags(); 649 fCalledCharPropInit = true; 650 } 651 if ((XMLCharacterProperties.fgCharFlags[ch] & XMLCharacterProperties.E_NameCharFlag) == 0) 652 break; 653 } 654 fCharacterCounter++; 655 } 656 hashcode = StringHasher.finishHash(hashcode); 657 int length = fCurrentOffset - offset; 658 int nameIndex = fCurrentChunk.addSymbol(offset, length, hashcode); 659 return nameIndex; 660 } 661 662 665 public boolean scanExpectedName(char fastcheck, StringPool.CharArrayRange expectedName) throws Exception { 666 char[] expected = expectedName.chars; 667 int offset = expectedName.offset; 668 int len = expectedName.length; 669 int ch = fMostRecentChar; 670 for (int i = 0; i < len; i++) { 671 if (ch != expected[offset++]) { 672 skipPastNmtoken(fastcheck); 673 return false; 674 } 675 fCharacterCounter++; 676 ch = loadNextChar(); 677 } 678 if (ch == fastcheck) 679 return true; 680 if (ch < 0x80) { 681 if (XMLCharacterProperties.fgAsciiNameChar[ch] == 0) 682 return true; 683 } else { 684 if (!fCalledCharPropInit) { 685 XMLCharacterProperties.initCharFlags(); 686 fCalledCharPropInit = true; 687 } 688 if ((XMLCharacterProperties.fgCharFlags[ch] & XMLCharacterProperties.E_NameCharFlag) == 0) 689 return true; 690 } 691 skipPastNmtoken(fastcheck); 692 return false; 693 } 694 695 698 public void scanQName(char fastcheck, QName qname) throws Exception { 699 int ch = fMostRecentChar; 700 if (ch < 0x80) { 701 if (XMLCharacterProperties.fgAsciiInitialNameChar[ch] == 0) { 702 qname.clear(); 703 return; 704 } 705 if (ch == ':') { 706 qname.clear(); 707 return; 708 } 709 } else { 710 if (!fCalledCharPropInit) { 711 XMLCharacterProperties.initCharFlags(); 712 fCalledCharPropInit = true; 713 } 714 if ((XMLCharacterProperties.fgCharFlags[ch] & XMLCharacterProperties.E_InitialNameCharFlag) == 0) { 715 qname.clear(); 716 return; 717 } 718 } 719 int offset = fCurrentOffset; 720 fCharacterCounter++; 721 int hashcode = 0; 722 int prefixend = -1; 723 while (true) { 724 hashcode = StringHasher.hashChar(hashcode, ch); 725 ch = loadNextChar(); 726 if (fastcheck == ch) 727 break; 728 if (ch < 0x80) { 729 if (XMLCharacterProperties.fgAsciiNameChar[ch] == 0) 730 break; 731 if (ch == ':') { 732 if (prefixend != -1) 733 break; 734 prefixend = fCurrentOffset; 735 CharDataChunk savedChunk = fCurrentChunk; 743 int savedOffset = fCurrentOffset; 744 int savedIndex = fCurrentIndex; 745 ch = loadNextChar(); 746 fCurrentChunk = savedChunk; 747 fCurrentOffset = savedOffset; 748 fCurrentIndex = savedIndex; 749 fMostRecentData = savedChunk.toCharArray(); 750 boolean lpok = true; 751 if (ch < 0x80) { 752 if (XMLCharacterProperties.fgAsciiInitialNameChar[ch] == 0 || ch == ':') 753 lpok = false; 754 } else { 755 if (!fCalledCharPropInit) { 756 XMLCharacterProperties.initCharFlags(); 757 fCalledCharPropInit = true; 758 } 759 if ((XMLCharacterProperties.fgCharFlags[ch] & XMLCharacterProperties.E_InitialNameCharFlag) == 0) 760 lpok = false; 761 } 762 ch = ':'; 763 if (!lpok) { 764 prefixend = -1; 765 fMostRecentChar = ch; 766 break; 767 } 768 } 769 } else { 770 if (!fCalledCharPropInit) { 771 XMLCharacterProperties.initCharFlags(); 772 fCalledCharPropInit = true; 773 } 774 if ((XMLCharacterProperties.fgCharFlags[ch] & XMLCharacterProperties.E_NameCharFlag) == 0) 775 break; 776 } 777 fCharacterCounter++; 778 } 779 hashcode = StringHasher.finishHash(hashcode); 780 int length = fCurrentOffset - offset; 781 qname.rawname = fCurrentChunk.addSymbol(offset, length, hashcode); 782 qname.prefix = prefixend == -1 ? -1 : addSymbol(offset, prefixend - offset); 783 qname.localpart = prefixend == -1 ? qname.rawname : addSymbol(prefixend + 1, fCurrentOffset - (prefixend + 1)); 784 qname.uri = StringPool.EMPTY_STRING; 785 786 } 788 794 public int scanContent(QName element) throws Exception { 795 if (fCallClearPreviousChunk && fCurrentChunk.clearPreviousChunk()) 796 fCallClearPreviousChunk = false; 797 int charDataOffset = fCurrentOffset; 798 int ch = fMostRecentChar; 799 if (ch < 0x80) { 800 switch (XMLCharacterProperties.fgAsciiWSCharData[ch]) { 801 case 0: 802 fCharacterCounter++; 803 ch = loadNextChar(); 804 break; 805 case 1: fCharacterCounter++; 807 ch = loadNextChar(); 808 if (!fInCDSect) { 809 return recognizeMarkup(ch); 810 } 811 break; 812 case 2: fCharacterCounter++; 814 ch = loadNextChar(); 815 if (!fInCDSect) { 816 return recognizeReference(ch); 817 } 818 break; 819 case 3: fCharacterCounter++; 821 ch = loadNextChar(); 822 if (ch != ']') 823 break; 824 { 825 CharDataChunk dataChunk = fCurrentChunk; 826 int index = fCurrentIndex; 827 int offset = fCurrentOffset; 828 if (loadNextChar() != '>') { 829 fCurrentChunk = dataChunk; 830 fCurrentIndex = index; 831 fCurrentOffset = offset; 832 fMostRecentData = dataChunk.toCharArray(); 833 fMostRecentChar = ']'; 834 break; 835 } 836 } 837 loadNextChar(); 838 fCharacterCounter += 2; 839 return XMLEntityHandler.CONTENT_RESULT_END_OF_CDSECT; 840 case 4: if (ch == 0 && atEOF(fCurrentOffset + 1)) { 842 changeReaders(); 843 return XMLEntityHandler.CONTENT_RESULT_INVALID_CHAR; } 845 return XMLEntityHandler.CONTENT_RESULT_INVALID_CHAR; 846 case 5: 847 do { 848 if (ch == 0x0A) { 849 fLinefeedCounter++; 850 fCharacterCounter = 1; 851 } else 852 fCharacterCounter++; 853 ch = loadNextChar(); 854 } while (ch == 0x20 || ch == 0x09 || ch == 0x0A); 855 if (ch < 0x80) { 856 switch (XMLCharacterProperties.fgAsciiCharData[ch]) { 857 case 0: 858 fCharacterCounter++; 859 ch = loadNextChar(); 860 break; 861 case 1: if (!fInCDSect) { 863 callCharDataHandler(charDataOffset, fCurrentOffset, true); 864 fCharacterCounter++; 865 ch = loadNextChar(); 866 return recognizeMarkup(ch); 867 } 868 fCharacterCounter++; 869 ch = loadNextChar(); 870 break; 871 case 2: if (!fInCDSect) { 873 callCharDataHandler(charDataOffset, fCurrentOffset, true); 874 fCharacterCounter++; 875 ch = loadNextChar(); 876 return recognizeReference(ch); 877 } 878 fCharacterCounter++; 879 ch = loadNextChar(); 880 break; 881 case 3: int endOffset = fCurrentOffset; 883 ch = loadNextChar(); 884 if (ch != ']') { 885 fCharacterCounter++; 886 break; 887 } 888 { 889 CharDataChunk dataChunk = fCurrentChunk; 890 int index = fCurrentIndex; 891 int offset = fCurrentOffset; 892 if (loadNextChar() != '>') { 893 fCurrentChunk = dataChunk; 894 fCurrentIndex = index; 895 fCurrentOffset = offset; 896 fMostRecentData = dataChunk.toCharArray(); 897 fMostRecentChar = ']'; 898 fCharacterCounter++; 899 break; 900 } 901 } 902 loadNextChar(); 903 callCharDataHandler(charDataOffset, endOffset, true); 904 fCharacterCounter += 3; 905 return XMLEntityHandler.CONTENT_RESULT_END_OF_CDSECT; 906 case 4: callCharDataHandler(charDataOffset, fCurrentOffset, true); 908 if (ch == 0 && atEOF(fCurrentOffset + 1)) { 909 changeReaders(); 910 return XMLEntityHandler.CONTENT_RESULT_INVALID_CHAR; } 912 return XMLEntityHandler.CONTENT_RESULT_INVALID_CHAR; 913 } 914 } else if (!skipMultiByteCharData(ch)) { 915 callCharDataHandler(charDataOffset, fCurrentOffset, true); 916 return XMLEntityHandler.CONTENT_RESULT_INVALID_CHAR; 917 } 918 break; 919 } 920 } else if (!skipMultiByteCharData(ch)) { 921 return XMLEntityHandler.CONTENT_RESULT_INVALID_CHAR; 922 } 923 ch = skipAsciiCharData(); 924 while (true) { 925 if (ch < 0x80) { 926 switch (XMLCharacterProperties.fgAsciiCharData[ch]) { 927 case 0: 928 fCharacterCounter++; 929 ch = loadNextChar(); 930 break; 931 case 1: if (!fInCDSect) { 933 callCharDataHandler(charDataOffset, fCurrentOffset, false); 934 fCharacterCounter++; 935 ch = loadNextChar(); 936 return recognizeMarkup(ch); 937 } 938 fCharacterCounter++; 939 ch = loadNextChar(); 940 break; 941 case 2: if (!fInCDSect) { 943 callCharDataHandler(charDataOffset, fCurrentOffset, false); 944 fCharacterCounter++; 945 ch = loadNextChar(); 946 return recognizeReference(ch); 947 } 948 fCharacterCounter++; 949 ch = loadNextChar(); 950 break; 951 case 3: int endOffset = fCurrentOffset; 953 ch = loadNextChar(); 954 if (ch != ']') { 955 fCharacterCounter++; 956 break; 957 } 958 CharDataChunk dataChunk = fCurrentChunk; 959 int index = fCurrentIndex; 960 int offset = fCurrentOffset; 961 if (loadNextChar() != '>') { 962 fCurrentChunk = dataChunk; 963 fCurrentIndex = index; 964 fCurrentOffset = offset; 965 fMostRecentData = dataChunk.toCharArray(); 966 fMostRecentChar = ']'; 967 fCharacterCounter++; 968 break; 969 } 970 loadNextChar(); 971 callCharDataHandler(charDataOffset, endOffset, false); 972 fCharacterCounter += 3; 973 return XMLEntityHandler.CONTENT_RESULT_END_OF_CDSECT; 974 case 4: if (ch == 0x0A) { 976 fLinefeedCounter++; 977 fCharacterCounter = 1; 978 ch = loadNextChar(); 979 break; 980 } 981 callCharDataHandler(charDataOffset, fCurrentOffset, false); 982 if (ch == 0 && atEOF(fCurrentOffset + 1)) { 983 changeReaders(); 984 return XMLEntityHandler.CONTENT_RESULT_INVALID_CHAR; } 986 return XMLEntityHandler.CONTENT_RESULT_INVALID_CHAR; 987 } 988 } else { 989 if (!skipMultiByteCharData(ch)) { 990 callCharDataHandler(charDataOffset, fCurrentOffset, false); 991 return XMLEntityHandler.CONTENT_RESULT_INVALID_CHAR; 992 } 993 ch = fMostRecentChar; 994 } 995 } 996 } 997 998 private static final char[] cdata_string = { 'C','D','A','T','A','[' }; 1002 private StringPool fStringPool = null; 1003 private boolean fCallClearPreviousChunk = true; 1004 private Vector fDeferredErrors = null; 1005 1006 private class DeferredError { 1010 int errorCode; 1011 Object [] args; 1012 int offset; 1013 DeferredError(int ec, Object [] a, int o) { 1014 errorCode = ec; 1015 args = a; 1016 offset = o; 1017 } 1018 } 1019 1020 1024 1028 private int recognizeMarkup(int ch) throws Exception { 1029 switch (ch) { 1030 case 0: 1031 return XMLEntityHandler.CONTENT_RESULT_MARKUP_END_OF_INPUT; 1032 case '?': 1033 fCharacterCounter++; 1034 loadNextChar(); 1035 return XMLEntityHandler.CONTENT_RESULT_START_OF_PI; 1036 case '!': 1037 fCharacterCounter++; 1038 ch = loadNextChar(); 1039 if (ch == 0) { 1040 fCharacterCounter--; 1041 fCurrentOffset--; 1042 return XMLEntityHandler.CONTENT_RESULT_MARKUP_END_OF_INPUT; 1043 } 1044 if (ch == '-') { 1045 fCharacterCounter++; 1046 ch = loadNextChar(); 1047 if (ch == 0) { 1048 fCharacterCounter -= 2; 1049 fCurrentOffset -= 2; 1050 return XMLEntityHandler.CONTENT_RESULT_MARKUP_END_OF_INPUT; 1051 } 1052 if (ch == '-') { 1053 fCharacterCounter++; 1054 loadNextChar(); 1055 return XMLEntityHandler.CONTENT_RESULT_START_OF_COMMENT; 1056 } 1057 break; 1058 } 1059 if (ch == '[') { 1060 for (int i = 0; i < 6; i++) { 1061 fCharacterCounter++; 1062 ch = loadNextChar(); 1063 if (ch == 0) { 1064 fCharacterCounter -= (2 + i); 1065 fCurrentOffset -= (2 + i); 1066 return XMLEntityHandler.CONTENT_RESULT_MARKUP_END_OF_INPUT; 1067 } 1068 if (ch != cdata_string[i]) { 1069 return XMLEntityHandler.CONTENT_RESULT_MARKUP_NOT_RECOGNIZED; 1070 } 1071 } 1072 fCharacterCounter++; 1073 loadNextChar(); 1074 return XMLEntityHandler.CONTENT_RESULT_START_OF_CDSECT; 1075 } 1076 break; 1077 case '/': 1078 fCharacterCounter++; 1079 loadNextChar(); 1080 return XMLEntityHandler.CONTENT_RESULT_START_OF_ETAG; 1081 default: 1082 return XMLEntityHandler.CONTENT_RESULT_START_OF_ELEMENT; 1083 } 1084 return XMLEntityHandler.CONTENT_RESULT_MARKUP_NOT_RECOGNIZED; 1085 } 1086 1087 1091 private int recognizeReference(int ch) throws Exception { 1092 if (ch == 0) { 1093 return XMLEntityHandler.CONTENT_RESULT_REFERENCE_END_OF_INPUT; 1094 } 1095 if (ch == '#') { 1101 fCharacterCounter++; 1102 loadNextChar(); 1103 return XMLEntityHandler.CONTENT_RESULT_START_OF_CHARREF; 1104 } else { 1105 return XMLEntityHandler.CONTENT_RESULT_START_OF_ENTITYREF; 1106 } 1107 } 1108 1109 1112 private boolean skipMultiByteCharData(int ch) throws Exception { 1113 if (ch < 0xD800) { 1114 loadNextChar(); 1115 return true; 1116 } 1117 if (ch > 0xFFFD) 1118 return false; 1119 if (ch >= 0xDC00 && ch < 0xE000) 1120 return false; 1121 if (ch >= 0xD800 && ch < 0xDC00) { 1122 CharDataChunk savedChunk = fCurrentChunk; 1123 int savedIndex = fCurrentIndex; 1124 int savedOffset = fCurrentOffset; 1125 ch = loadNextChar(); 1126 if (ch < 0xDC00 || ch >= 0xE000) { 1127 fCurrentChunk = savedChunk; 1128 fCurrentIndex = savedIndex; 1129 fCurrentOffset = savedOffset; 1130 fMostRecentData = savedChunk.toCharArray(); 1131 fMostRecentChar = fMostRecentData[savedIndex] & 0xFFFF; 1132 return false; 1133 } 1134 } 1135 loadNextChar(); 1136 return true; 1137 } 1138 1139 1145 private int skipAsciiCharData() throws Exception { 1146 int ch = fMostRecentChar; 1147 while (true) { 1148 if (ch >= 0x80) { 1149 return ch; 1150 } 1151 if (XMLCharacterProperties.fgAsciiCharData[ch] == 0) { 1152 fCharacterCounter++; 1153 } else if (ch == 0x0A) { 1154 fLinefeedCounter++; 1155 fCharacterCounter = 1; 1156 } else { 1157 return ch; 1158 } 1159 ch = loadNextChar(); 1160 } 1161 } 1162 1163 1171 private void callCharDataHandler(int offset, int endOffset, boolean isWhitespace) throws Exception { 1172 1173 int length = endOffset - offset; 1174 if (!fSendCharDataAsCharArray) { 1175 int stringIndex = addString(offset, length); 1176 if (isWhitespace) 1177 fCharDataHandler.processWhitespace(stringIndex); 1178 else 1179 fCharDataHandler.processCharacters(stringIndex); 1180 return; 1181 } 1182 1183 CharDataChunk dataChunk = fCurrentChunk.chunkFor(offset); 1184 int index = offset & CharDataChunk.CHUNK_MASK; 1185 if (index + length <= CharDataChunk.CHUNK_SIZE) { 1186 if (length != 0) { 1190 if (isWhitespace) 1191 fCharDataHandler.processWhitespace(dataChunk.toCharArray(), index, length); 1192 else 1193 fCharDataHandler.processCharacters(dataChunk.toCharArray(), index, length); 1194 } 1195 return; 1196 } 1197 1198 int count = length; 1202 int nbytes = CharDataChunk.CHUNK_SIZE - index; 1203 if (isWhitespace) 1204 fCharDataHandler.processWhitespace(dataChunk.toCharArray(), index, nbytes); 1205 else 1206 fCharDataHandler.processCharacters(dataChunk.toCharArray(), index, nbytes); 1207 count -= nbytes; 1208 1209 do { 1213 dataChunk = dataChunk.nextChunk(); 1214 if (dataChunk == null) { 1215 throw new RuntimeException (new ImplementationMessages().createMessage(null, ImplementationMessages.INT_DCN, 0, null)); 1216 } 1217 nbytes = count <= CharDataChunk.CHUNK_SIZE ? count : CharDataChunk.CHUNK_SIZE; 1218 if (isWhitespace) 1219 fCharDataHandler.processWhitespace(dataChunk.toCharArray(), 0, nbytes); 1220 else 1221 fCharDataHandler.processCharacters(dataChunk.toCharArray(), 0, nbytes); 1222 count -= nbytes; 1223 } while (count > 0); 1224 } 1225 1226 1232 private int slowLoadNextChar() throws Exception { 1233 fCallClearPreviousChunk = true; 1234 if (fCurrentChunk.nextChunk() != null) { 1235 fCurrentChunk = fCurrentChunk.nextChunk(); 1236 fCurrentIndex = 0; 1237 fMostRecentData = fCurrentChunk.toCharArray(); 1238 return (fMostRecentChar = fMostRecentData[fCurrentIndex] & 0xFFFF); 1239 } else { 1240 fCurrentChunk = CharDataChunk.createChunk(fStringPool, fCurrentChunk); 1241 fCurrentIndex = 0; 1242 fFillIndex = 0; 1243 loadFirstChar(); 1244 return fMostRecentChar; 1245 } 1246 } 1247 1248 1254 private int loadNextChar() throws Exception { 1255 fCurrentOffset++; 1256 if (++fCurrentIndex == CharDataChunk.CHUNK_SIZE) 1257 return slowLoadNextChar(); 1258 if (fCurrentIndex < fFillIndex) 1259 return (fMostRecentChar = fMostRecentData[fCurrentIndex] & 0xFFFF); 1260 return loadMoreChars(); 1261 } 1262 1263 1268 private void loadFirstChar() throws Exception { 1269 fMostRecentData = fCurrentChunk.toCharArray(); 1270 if (fMostRecentData == null) { 1271 fMostRecentData = new char[CharDataChunk.CHUNK_SIZE]; 1272 fCurrentChunk.setCharArray(fMostRecentData); 1273 } 1274 loadMoreChars(); 1275 } 1276 1277 1282 private boolean seenCR = false; 1283 private int oweChar = -1; 1284 private char[] inBuffer = new char[2]; 1285 private int loadMoreChars() throws Exception { 1286 if (oweChar != -1) { 1287 fMostRecentData[fFillIndex] = (char)oweChar; 1288 fFillIndex++; 1289 fLength++; 1290 fMostRecentChar = oweChar; 1291 oweChar = -1; 1292 return fMostRecentChar; 1293 } 1294 int result = -1; 1295 try { 1296 while (true) { 1297 result = fCharacterStream.read(inBuffer, 0, 2); 1298 switch (result) { 1299 case -1: 1300 break; 1301 case 0: 1302 continue; 1303 case 1: 1304 result = inBuffer[0]; 1305 if (seenCR) { 1306 seenCR = false; 1307 if (result == 0x0A) 1308 continue; 1309 } 1310 if (result == 0x0D) { 1311 seenCR = true; 1312 result = 0x0A; 1313 } 1314 fMostRecentChar = (fMostRecentData[fFillIndex] = (char)result); 1315 fFillIndex++; 1316 fLength++; 1317 return fMostRecentChar; 1318 case 2: 1319 result = inBuffer[0]; 1320 boolean readchar2 = false; 1321 if (seenCR) { 1322 seenCR = false; 1323 if (result == 0x0A) { 1324 result = inBuffer[1]; 1325 readchar2 = true; 1326 } 1327 } 1328 if (result == 0x0D) { 1329 seenCR = true; 1330 result = 0x0A; 1331 } 1332 fMostRecentChar = (fMostRecentData[fFillIndex] = (char)result); 1333 fFillIndex++; 1334 fLength++; 1335 if (!readchar2) { 1336 result = inBuffer[1]; 1337 if (seenCR) { 1338 seenCR = false; 1339 if (result == 0x0A) 1340 return fMostRecentChar; 1341 } 1342 if (result == 0x0D) { 1343 seenCR = true; 1344 result = 0x0A; 1345 } 1346 oweChar = result; 1347 } 1348 return fMostRecentChar; 1349 } 1350 break; 1351 } 1352 } catch (java.io.IOException ex) { 1353 } 1354 try { 1358 fCharacterStream.close(); 1359 } catch (java.io.IOException ex) { 1360 } 1361 fCharacterStream = null; 1362 fMostRecentChar = (fMostRecentData[fFillIndex] = 0); 1363 return 0; 1364 } 1365 1366 1372 private boolean atEOF(int offset) { 1373 return (offset > fLength); 1374 } 1375 1376 protected Reader fCharacterStream = null; 1380 protected CharDataChunk fCurrentChunk = null; 1381 protected int fCurrentIndex = 0; 1382 protected int fFillIndex = 0; 1383 protected char[] fMostRecentData = null; 1384 protected int fMostRecentChar = 0; 1385 protected int fLength = 0; 1386 protected boolean fCalledCharPropInit = false; 1387 1388} 1389 | Popular Tags |