1 56 57 67 68 package thread; 69 70 import java.io.FileInputStream ; 71 import java.io.FileNotFoundException ; 72 import java.io.IOException ; 73 import java.io.InputStreamReader ; 74 import java.io.StringReader ; 75 76 import org.enhydra.apache.xerces.parsers.DOMParser; 77 import org.enhydra.apache.xerces.parsers.SAXParser; 78 import org.w3c.dom.Document ; 79 import org.w3c.dom.NamedNodeMap ; 80 import org.w3c.dom.Node ; 81 import org.xml.sax.AttributeList ; 82 import org.xml.sax.HandlerBase ; 83 import org.xml.sax.InputSource ; 84 import org.xml.sax.SAXException ; 85 import org.xml.sax.SAXParseException ; 86 87 public class Test { 88 89 90 class InFileInfo 99 { 100 public String fileName; 101 public String fileContent; int checkSum; } 107 108 final int MAXINFILES = 25; 118 class RunInfo 119 { 120 boolean quiet; 121 boolean verbose; 122 int numThreads; 123 boolean validating; 124 boolean dom; 125 boolean reuseParser; 126 boolean inMemory; 127 boolean dumpOnErr; 128 int totalTime; 129 int numInputFiles; 130 InFileInfo files[] = new InFileInfo[MAXINFILES]; 131 } 132 133 134 class ThreadInfo 143 { 144 boolean fHeartBeat; int fParses; int fThreadNum; 149 ThreadInfo() { 150 fHeartBeat = false; 151 fParses = 0; 152 fThreadNum = -1; 153 } 154 } 155 156 157 RunInfo gRunInfo = new RunInfo(); 164 ThreadInfo gThreadInfo[]; 165 166 167 168 class ThreadParser extends HandlerBase 179 { 180 private int fCheckSum; 181 private SAXParser fSAXParser; 182 private DOMParser fDOMParser; 183 184 185 public void characters(char chars[], int start, int length) { 189 addToCheckSum(chars, start, length);} 190 public void ignorableWhitespace(char chars[], int start, int length) { 191 addToCheckSum(chars, start, length);} 192 193 public void warning(SAXParseException ex) { 194 System.err.print("*** Warning "+ 195 ex.getMessage());} 196 197 public void error(SAXParseException ex) { 198 System.err.print("*** Error "+ 199 ex.getMessage());} 200 201 public void fatalError(SAXParseException ex) { 202 System.err.print("***** Fatal error "+ 203 ex.getMessage());} 204 205 ThreadParser() 210 { 211 if (gRunInfo.dom) { 212 fDOMParser = new org.enhydra.apache.xerces.parsers.DOMParser(); 214 try { 215 fDOMParser.setFeature( "http://xml.org/sax/features/validation", 216 gRunInfo.validating); 217 } 218 catch (Exception e) {} 219 fDOMParser.setErrorHandler(this); 220 } 221 else 222 { 223 fSAXParser = new org.enhydra.apache.xerces.parsers.SAXParser(); 225 try { 226 fSAXParser.setFeature( "http://xml.org/sax/features/validation", 227 gRunInfo.validating); 228 } 229 catch (Exception e) {} 230 fSAXParser.setDocumentHandler(this); 231 fSAXParser.setErrorHandler(this); 232 } 233 234 } 235 236 int parse(int fileNum) 246 { 247 InputSource mbis = null; 248 InFileInfo fInfo = gRunInfo.files[fileNum]; 249 250 fCheckSum = 0; 251 252 if (gRunInfo.inMemory) { 253 mbis = new InputSource (new StringReader (fInfo.fileContent)); 254 } 255 256 try 257 { 258 if (gRunInfo.dom) { 259 if (gRunInfo.inMemory) 261 fDOMParser.parse(mbis); 262 else 263 fDOMParser.parse(fInfo.fileName); 264 Document doc = fDOMParser.getDocument(); 265 domCheckSum(doc); 266 } 267 else 268 { 269 if (gRunInfo.inMemory) 271 fSAXParser.parse(mbis); 272 else 273 fSAXParser.parse(fInfo.fileName); 274 } 275 } 276 277 catch (SAXException e) 278 { 279 String exceptionMessage = e.getMessage(); 280 System.err.println(" during parsing: " + fInfo.fileName + 281 " Exception message is: " + exceptionMessage); 282 } 283 catch (IOException e) 284 { 285 String exceptionMessage = e.getMessage(); 286 System.err.println(" during parsing: " + fInfo.fileName + 287 " Exception message is: " + exceptionMessage); 288 } 289 290 return fCheckSum; 291 } 292 293 294 private void addToCheckSum(char chars[], int start, int len) 299 { 300 int i; 302 for (i=start; i<len; i++) 303 fCheckSum = fCheckSum*5 + chars[i]; 304 } 305 306 private void addToCheckSum(String chars) 311 { 312 int i; 313 int len = chars.length(); 314 for (i=0; i<len; i++) 315 fCheckSum = fCheckSum*5 + chars.charAt(i); 316 } 317 318 319 320 public void startElement(String name, AttributeList attributes) 326 { 327 addToCheckSum(name); 328 329 int n = attributes.getLength(); 330 int i; 331 for (i=0; i<n; i++) 332 { 333 String attNam = attributes.getName(i); 334 addToCheckSum(attNam); 335 String attVal = attributes.getValue(i); 336 addToCheckSum(attVal); 337 } 338 } 339 340 341 public void domCheckSum(Node node) 346 { 347 String s; 348 Node child; 349 NamedNodeMap attributes; 350 351 switch (node.getNodeType() ) 352 { 353 case Node.ELEMENT_NODE: 354 { 355 s = node.getNodeName(); 357 attributes = node.getAttributes(); int numAttributes = attributes.getLength(); 359 int i; 360 for (i=0; i<numAttributes; i++) 361 domCheckSum(attributes.item(i)); 362 363 addToCheckSum(s); for (child=node.getFirstChild(); child!=null; child=child.getNextSibling()) 365 domCheckSum(child); 366 367 break; 368 } 369 370 371 case Node.ATTRIBUTE_NODE: 372 { 373 s = node.getNodeName(); addToCheckSum(s); 375 s = node.getNodeValue(); if (s != null) 377 addToCheckSum(s); 378 break; 379 } 380 381 382 case Node.TEXT_NODE: 383 case Node.CDATA_SECTION_NODE: 384 { 385 s = node.getNodeValue(); 386 addToCheckSum(s); 387 break; 388 } 389 390 case Node.ENTITY_REFERENCE_NODE: 391 case Node.DOCUMENT_NODE: 392 { 393 for (child=node.getFirstChild(); child!=null; child=child.getNextSibling()) 397 domCheckSum(child); 398 break; 399 } 400 } 401 } 402 403 404 public int reCheck() 411 { 412 if (gRunInfo.dom) { 413 fCheckSum = 0; 414 Document doc = fDOMParser.getDocument(); 415 domCheckSum(doc); 416 } 417 return fCheckSum; 418 } 419 420 public void domPrint() 425 { 426 System.out.println("Begin DOMPrint ..."); 427 if (gRunInfo.dom) 428 domPrint(fDOMParser.getDocument()); 429 System.out.println("End DOMPrint"); 430 } 431 432 void domPrint(Node node) 438 { 439 440 String s; 441 Node child; 442 NamedNodeMap attributes; 443 444 switch (node.getNodeType() ) 445 { 446 case Node.ELEMENT_NODE: 447 { 448 System.out.print("<"); 449 System.out.print(node.getNodeName()); 451 attributes = node.getAttributes(); int numAttributes = attributes.getLength(); 453 int i; 454 for (i=0; i<numAttributes; i++) { 455 domPrint(attributes.item(i)); 456 } 457 System.out.print(">"); 458 459 for (child=node.getFirstChild(); child!=null; child=child.getNextSibling()) 460 domPrint(child); 461 462 System.out.print("</"); 463 System.out.print(node.getNodeName()); 464 System.out.print(">"); 465 break; 466 } 467 468 469 case Node.ATTRIBUTE_NODE: 470 { 471 System.out.print(" "); 472 System.out.print(node.getNodeName()); System.out.print("= \""); 474 System.out.print(node.getNodeValue()); System.out.print("\""); 476 break; 477 } 478 479 480 case Node.TEXT_NODE: 481 case Node.CDATA_SECTION_NODE: 482 { 483 System.out.print(node.getNodeValue()); 484 break; 485 } 486 487 case Node.ENTITY_REFERENCE_NODE: 488 case Node.DOCUMENT_NODE: 489 { 490 for (child=node.getFirstChild(); child!=null; child=child.getNextSibling()) 494 domPrint(child); 495 break; 496 } 497 } 498 } 499 500 } 502 503 515 void parseCommandLine(String argv[]) 516 { 517 gRunInfo.quiet = false; gRunInfo.verbose = false; 519 gRunInfo.numThreads = 2; 520 gRunInfo.validating = false; 521 gRunInfo.dom = false; 522 gRunInfo.reuseParser = false; 523 gRunInfo.inMemory = false; 524 gRunInfo.dumpOnErr = false; 525 gRunInfo.totalTime = 0; 526 gRunInfo.numInputFiles = 0; 527 528 try { 530 int argnum = 0; 531 int argc = argv.length; 532 while (argnum < argc) 533 { 534 if (argv[argnum].equals("-quiet")) 535 gRunInfo.quiet = true; 536 else if (argv[argnum].equals("-verbose")) 537 gRunInfo.verbose = true; 538 else if (argv[argnum].equals("-v")) 539 gRunInfo.validating = true; 540 else if (argv[argnum].equals("-dom")) 541 gRunInfo.dom = true; 542 else if (argv[argnum].equals("-reuse")) 543 gRunInfo.reuseParser = true; 544 else if (argv[argnum].equals("-dump")) 545 gRunInfo.dumpOnErr = true; 546 else if (argv[argnum].equals("-mem")) 547 gRunInfo.inMemory = true; 548 else if (argv[argnum].equals("-threads")) 549 { 550 ++argnum; 551 if (argnum >= argc) 552 throw new Exception (); 553 try { 554 gRunInfo.numThreads = Integer.parseInt(argv[argnum]); 555 } 556 catch (NumberFormatException e) { 557 throw new Exception (); 558 } 559 if (gRunInfo.numThreads < 0) 560 throw new Exception (); 561 } 562 else if (argv[argnum].equals("-time")) 563 { 564 ++argnum; 565 if (argnum >= argc) 566 throw new Exception (); 567 try { 568 gRunInfo.totalTime = Integer.parseInt(argv[argnum]); 569 } 570 catch (NumberFormatException e) { 571 throw new Exception (); 572 } 573 if (gRunInfo.totalTime < 1) 574 throw new Exception (); 575 } 576 else if (argv[argnum].charAt(0) == '-') 577 { 578 System.err.println("Unrecognized command line option. Scanning" 579 + " \"" + argv[argnum] + "\""); 580 throw new Exception (); 581 } 582 else 583 { 584 gRunInfo.numInputFiles++; 585 if (gRunInfo.numInputFiles >= MAXINFILES) 586 { 587 System.err.println("Too many input files. Limit is " 588 + MAXINFILES); 589 throw new Exception (); 590 } 591 gRunInfo.files[gRunInfo.numInputFiles-1] = new InFileInfo(); 592 gRunInfo.files[gRunInfo.numInputFiles-1].fileName = argv[argnum]; 593 } 594 argnum++; 595 } 596 597 if (gRunInfo.numInputFiles == 0) 600 { 601 System.err.println("No input XML file specified on command line."); 602 throw new Exception (); 603 }; 604 605 606 } 607 catch (Exception e) 608 { 609 System.err.print("usage: java thread.Test [-v] [-threads nnn] [-time nnn] [-quiet] [-verbose] xmlfile...\n" + 610 " -v Use validating parser. Non-validating is default. \n" + 611 " -dom Use a DOM parser. Default is SAX. \n" + 612 " -quiet Suppress periodic status display. \n" + 613 " -verbose Display extra messages. \n" + 614 " -reuse Retain and reuse parser. Default creates new for each parse.\n" + 615 " -threads nnn Number of threads. Default is 2. \n" + 616 " -time nnn Total time to run, in seconds. Default is forever.\n" + 617 " -dump Dump DOM tree on error.\n" + 618 " -mem Read files into memory once only, and parse them from there.\n" 619 ); 620 System.exit(1); 621 } 622 } 623 624 625 void ReadFilesIntoMemory() 636 { 637 int fileNum; 638 InputStreamReader fileF; 639 char chars[] = new char[1024]; 640 StringBuffer buf = new StringBuffer (); 641 642 if (gRunInfo.inMemory) 643 { 644 for (fileNum = 0; fileNum <gRunInfo.numInputFiles; fileNum++) 645 { 646 InFileInfo fInfo = gRunInfo.files[fileNum]; 647 buf.setLength(0); 648 try { 649 FileInputStream in = new FileInputStream ( fInfo.fileName ); 650 fileF = new InputStreamReader (in); 651 int len = 0; 652 while ((len = fileF.read(chars, 0, chars.length)) > 0) { 653 buf.append(chars, 0, len); 654 } 655 fInfo.fileContent = buf.toString(); 656 fileF.close(); 657 } 658 catch (FileNotFoundException e) { 659 System.err.print("File not found: \"" + 660 fInfo.fileName + "\"."); 661 System.exit(-1); 662 } 663 catch (IOException e) { 664 System.err.println("Error reading file \"" + 665 fInfo.fileName + "\"."); 666 System.exit(-1); 667 } 668 } 669 } 670 } 671 672 673 674 688 689 class thread extends Thread { 690 691 ThreadInfo thInfo; 692 693 thread (ThreadInfo param) { 694 thInfo = param; 695 } 696 697 public void run() 698 { 699 ThreadParser thParser = null; 700 701 if (gRunInfo.verbose) 702 System.out.println("Thread " + thInfo.fThreadNum + ": starting"); 703 704 int docNum = gRunInfo.numInputFiles; 705 706 while (true) 711 { 712 713 if (thParser == null) 714 thParser = new ThreadParser(); 715 716 docNum++; 717 718 if (docNum >= gRunInfo.numInputFiles) 719 docNum = 0; 720 721 InFileInfo fInfo = gRunInfo.files[docNum]; 722 723 if (gRunInfo.verbose ) 724 System.out.println("Thread " + thInfo.fThreadNum + 725 ": starting file " + fInfo.fileName); 726 727 728 int checkSum = 0; 729 checkSum = thParser.parse(docNum); 730 731 if (checkSum != gRunInfo.files[docNum].checkSum) 732 { 733 System.err.println("\nThread " + thInfo.fThreadNum + 734 ": Parse Check sum error on file \"" + 735 fInfo.fileName + "\". Expected " + 736 fInfo.checkSum + ", got " + checkSum); 737 738 int secondTryCheckSum = thParser.reCheck(); 740 System.err.println(" Retry checksum is " + secondTryCheckSum); 741 if (gRunInfo.dumpOnErr) 742 thParser.domPrint(); 743 System.out.flush(); 744 System.exit(-1); 745 } 746 747 if (gRunInfo.reuseParser == false) 748 { 749 thParser = null; 750 } 751 752 753 thInfo.fHeartBeat = true; 754 thInfo.fParses++; 755 } 756 } 758 } 760 761 767 void run(String argv[]) 768 { 769 parseCommandLine(argv); 770 771 ReadFilesIntoMemory(); 776 777 778 ThreadParser mainParser = new ThreadParser(); 784 int n; 785 boolean errors = false; 786 int cksum; 787 788 789 for (n = 0; n < gRunInfo.numInputFiles; n++) 790 { 791 String fileName = gRunInfo.files[n].fileName; 792 if (gRunInfo.verbose) 793 System.out.print(fileName + " checksum is "); 794 795 cksum = mainParser.parse(n); 796 797 if (cksum == 0) 798 { 799 System.err.println("An error occured while initially parsing" + 800 fileName); 801 errors = true; 802 } 803 804 gRunInfo.files[n].checkSum = cksum; 805 if (gRunInfo.verbose ) 806 System.out.println(cksum); 807 if (gRunInfo.dumpOnErr && errors) 808 mainParser.domPrint(); 809 810 } 811 if (errors) 812 System.exit(1); 813 814 818 if (gRunInfo.numThreads == 0) 819 return; 820 821 gThreadInfo = new ThreadInfo[gRunInfo.numThreads]; 822 823 int threadNum; 824 for (threadNum=0; threadNum < gRunInfo.numThreads; threadNum++) 825 { 826 gThreadInfo[threadNum] = new ThreadInfo(); 827 gThreadInfo[threadNum].fThreadNum = threadNum; 828 thread t = new thread(gThreadInfo[threadNum]); 829 t.start(); 830 } 831 832 838 long startTime = System.currentTimeMillis(); 839 long elapsedSeconds = 0; 840 while (gRunInfo.totalTime == 0 || gRunInfo.totalTime > elapsedSeconds) 841 { 842 try { 843 Thread.sleep(1000); 844 } 845 catch (InterruptedException e) { 846 } 848 if (gRunInfo.quiet == false && gRunInfo.verbose == false) 849 { 850 char c = '+'; 851 for (threadNum=0; threadNum < gRunInfo.numThreads; threadNum++) 852 { 853 if (gThreadInfo[threadNum].fHeartBeat == false) 854 { 855 c = '.'; 856 break; 857 } 858 } 859 System.out.print(c); 860 System.out.flush(); 861 if (c == '+') 862 for (threadNum=0; threadNum < gRunInfo.numThreads; threadNum++) 863 gThreadInfo[threadNum].fHeartBeat = false; 864 } 865 elapsedSeconds = (System.currentTimeMillis() - startTime) / 1000; 866 }; 867 868 double totalParsesCompleted = 0; 875 for (threadNum=0; threadNum < gRunInfo.numThreads; threadNum++) 876 { 877 totalParsesCompleted += gThreadInfo[threadNum].fParses; 878 } 880 881 double parsesPerMinute = 882 totalParsesCompleted / (((double)gRunInfo.totalTime) / ((double)60)); 883 System.out.println("\n" + parsesPerMinute + " parses per minute."); 884 885 System.exit(0); 889 } 890 891 static public void main(String argv[]) { 892 Test test = new Test(); 893 test.run(argv); 894 } 895 896 } | Popular Tags |