1 /* 2 * xmllint.c : a small tester program for XML input. 3 * 4 * See Copyright for the status of this software. 5 * 6 * daniel (at) veillard.com 7 */ 8 9 #include "libxml.h" 10 11 #include <string.h> 12 #include <stdarg.h> 13 #include <assert.h> 14 15 #if defined (_WIN32) && !defined(__CYGWIN__) 16 #if defined (_MSC_VER) || defined(__BORLANDC__) 17 #include <winsock2.h> 18 #pragma comment(lib, "ws2_32.lib") 19 #define gettimeofday(p1,p2) 20 #endif /* _MSC_VER */ 21 #endif /* _WIN32 */ 22 23 #ifdef HAVE_SYS_TIME_H 24 #include <sys/time.h> 25 #endif 26 #ifdef HAVE_TIME_H 27 #include <time.h> 28 #endif 29 30 #ifdef __MINGW32__ 31 #define _WINSOCKAPI_ 32 #include <wsockcompat.h> 33 #include <winsock2.h> 34 #undef XML_SOCKLEN_T 35 #define XML_SOCKLEN_T unsigned int 36 #endif 37 38 #ifdef HAVE_SYS_TIMEB_H 39 #include <sys/timeb.h> 40 #endif 41 42 #ifdef HAVE_SYS_TYPES_H 43 #include <sys/types.h> 44 #endif 45 #ifdef HAVE_SYS_STAT_H 46 #include <sys/stat.h> 47 #endif 48 #ifdef HAVE_FCNTL_H 49 #include <fcntl.h> 50 #endif 51 #ifdef HAVE_UNISTD_H 52 #include <unistd.h> 53 #endif 54 #ifdef HAVE_SYS_MMAN_H 55 #include <sys/mman.h> 56 /* seems needed for Solaris */ 57 #ifndef MAP_FAILED 58 #define MAP_FAILED ((void *) -1) 59 #endif 60 #endif 61 #ifdef HAVE_STDLIB_H 62 #include <stdlib.h> 63 #endif 64 #ifdef HAVE_LIBREADLINE 65 #include <readline/readline.h> 66 #ifdef HAVE_LIBHISTORY 67 #include <readline/history.h> 68 #endif 69 #endif 70 71 #include <libxml/xmlmemory.h> 72 #include <libxml/parser.h> 73 #include <libxml/parserInternals.h> 74 #include <libxml/HTMLparser.h> 75 #include <libxml/HTMLtree.h> 76 #include <libxml/tree.h> 77 #include <libxml/xpath.h> 78 #include <libxml/debugXML.h> 79 #include <libxml/xmlerror.h> 80 #ifdef LIBXML_XINCLUDE_ENABLED 81 #include <libxml/xinclude.h> 82 #endif 83 #ifdef LIBXML_CATALOG_ENABLED 84 #include <libxml/catalog.h> 85 #endif 86 #include <libxml/globals.h> 87 #include <libxml/xmlreader.h> 88 #ifdef LIBXML_SCHEMATRON_ENABLED 89 #include <libxml/schematron.h> 90 #endif 91 #ifdef LIBXML_SCHEMAS_ENABLED 92 #include <libxml/relaxng.h> 93 #include <libxml/xmlschemas.h> 94 #endif 95 #ifdef LIBXML_PATTERN_ENABLED 96 #include <libxml/pattern.h> 97 #endif 98 #ifdef LIBXML_C14N_ENABLED 99 #include <libxml/c14n.h> 100 #endif 101 #ifdef LIBXML_OUTPUT_ENABLED 102 #include <libxml/xmlsave.h> 103 #endif 104 105 #ifndef XML_XML_DEFAULT_CATALOG 106 #define XML_XML_DEFAULT_CATALOG "file:///etc/xml/catalog" 107 #endif 108 109 typedef enum { 110 XMLLINT_RETURN_OK = 0, /* No error */ 111 XMLLINT_ERR_UNCLASS, /* Unclassified */ 112 XMLLINT_ERR_DTD, /* Error in DTD */ 113 XMLLINT_ERR_VALID, /* Validation error */ 114 XMLLINT_ERR_RDFILE, /* CtxtReadFile error */ 115 XMLLINT_ERR_SCHEMACOMP, /* Schema compilation */ 116 XMLLINT_ERR_OUT, /* Error writing output */ 117 XMLLINT_ERR_SCHEMAPAT, /* Error in schema pattern */ 118 XMLLINT_ERR_RDREGIS, /* Error in Reader registration */ 119 XMLLINT_ERR_MEM /* Out of memory error */ 120 } xmllintReturnCode; 121 #ifdef LIBXML_DEBUG_ENABLED 122 static int shell = 0; 123 static int debugent = 0; 124 #endif 125 static int debug = 0; 126 static int maxmem = 0; 127 #ifdef LIBXML_TREE_ENABLED 128 static int copy = 0; 129 #endif /* LIBXML_TREE_ENABLED */ 130 static int recovery = 0; 131 static int noent = 0; 132 static int noblanks = 0; 133 static int noout = 0; 134 static int nowrap = 0; 135 #ifdef LIBXML_OUTPUT_ENABLED 136 static int format = 0; 137 static const char *output = NULL; 138 static int compress = 0; 139 static int oldout = 0; 140 #endif /* LIBXML_OUTPUT_ENABLED */ 141 #ifdef LIBXML_VALID_ENABLED 142 static int valid = 0; 143 static int postvalid = 0; 144 static char * dtdvalid = NULL; 145 static char * dtdvalidfpi = NULL; 146 #endif 147 #ifdef LIBXML_SCHEMAS_ENABLED 148 static char * relaxng = NULL; 149 static xmlRelaxNGPtr relaxngschemas = NULL; 150 static char * schema = NULL; 151 static xmlSchemaPtr wxschemas = NULL; 152 #endif 153 #ifdef LIBXML_SCHEMATRON_ENABLED 154 static char * schematron = NULL; 155 static xmlSchematronPtr wxschematron = NULL; 156 #endif 157 static int repeat = 0; 158 static int insert = 0; 159 #if defined(LIBXML_HTML_ENABLED) || defined(LIBXML_VALID_ENABLED) 160 static int html = 0; 161 static int xmlout = 0; 162 #endif 163 static int htmlout = 0; 164 #ifdef LIBXML_PUSH_ENABLED 165 static int push = 0; 166 #endif /* LIBXML_PUSH_ENABLED */ 167 #ifdef HAVE_SYS_MMAN_H 168 static int memory = 0; 169 #endif 170 static int testIO = 0; 171 static char *encoding = NULL; 172 #ifdef LIBXML_XINCLUDE_ENABLED 173 static int xinclude = 0; 174 #endif 175 static int dtdattrs = 0; 176 static int loaddtd = 0; 177 static xmllintReturnCode progresult = XMLLINT_RETURN_OK; 178 static int timing = 0; 179 static int generate = 0; 180 static int dropdtd = 0; 181 #ifdef LIBXML_CATALOG_ENABLED 182 static int catalogs = 0; 183 static int nocatalogs = 0; 184 #endif 185 #ifdef LIBXML_C14N_ENABLED 186 static int canonical = 0; 187 static int exc_canonical = 0; 188 #endif 189 #ifdef LIBXML_READER_ENABLED 190 static int stream = 0; 191 static int walker = 0; 192 #endif /* LIBXML_READER_ENABLED */ 193 static int chkregister = 0; 194 static int nbregister = 0; 195 #ifdef LIBXML_SAX1_ENABLED 196 static int sax1 = 0; 197 #endif /* LIBXML_SAX1_ENABLED */ 198 #ifdef LIBXML_PATTERN_ENABLED 199 static const char *pattern = NULL; 200 static xmlPatternPtr patternc = NULL; 201 static xmlStreamCtxtPtr patstream = NULL; 202 #endif 203 static int options = XML_PARSE_COMPACT; 204 static int sax = 0; 205 static int oldxml10 = 0; 206 207 /************************************************************************ 208 * * 209 * Entity loading control and customization. * 210 * * 211 ************************************************************************/ 212 #define MAX_PATHS 64 213 #ifdef _WIN32 214 # define PATH_SEPARATOR ';' 215 #else 216 # define PATH_SEPARATOR ':' 217 #endif 218 static xmlChar *paths[MAX_PATHS + 1]; 219 static int nbpaths = 0; 220 static int load_trace = 0; 221 222 static 223 void parsePath(const xmlChar *path) { 224 const xmlChar *cur; 225 226 if (path == NULL) 227 return; 228 while (*path != 0) { 229 if (nbpaths >= MAX_PATHS) { 230 fprintf(stderr, "MAX_PATHS reached: too many paths\n"); 231 return; 232 } 233 cur = path; 234 while ((*cur == ' ') || (*cur == PATH_SEPARATOR)) 235 cur++; 236 path = cur; 237 while ((*cur != 0) && (*cur != ' ') && (*cur != PATH_SEPARATOR)) 238 cur++; 239 if (cur != path) { 240 paths[nbpaths] = xmlStrndup(path, cur - path); 241 if (paths[nbpaths] != NULL) 242 nbpaths++; 243 path = cur; 244 } 245 } 246 } 247 248 static xmlExternalEntityLoader defaultEntityLoader = NULL; 249 250 static xmlParserInputPtr 251 xmllintExternalEntityLoader(const char *URL, const char *ID, 252 xmlParserCtxtPtr ctxt) { 253 xmlParserInputPtr ret; 254 warningSAXFunc warning = NULL; 255 errorSAXFunc err = NULL; 256 257 int i; 258 const char *lastsegment = URL; 259 const char *iter = URL; 260 261 if ((nbpaths > 0) && (iter != NULL)) { 262 while (*iter != 0) { 263 if (*iter == '/') 264 lastsegment = iter + 1; 265 iter++; 266 } 267 } 268 269 if ((ctxt != NULL) && (ctxt->sax != NULL)) { 270 warning = ctxt->sax->warning; 271 err = ctxt->sax->error; 272 ctxt->sax->warning = NULL; 273 ctxt->sax->error = NULL; 274 } 275 276 if (defaultEntityLoader != NULL) { 277 ret = defaultEntityLoader(URL, ID, ctxt); 278 if (ret != NULL) { 279 if (warning != NULL) 280 ctxt->sax->warning = warning; 281 if (err != NULL) 282 ctxt->sax->error = err; 283 if (load_trace) { 284 fprintf \ 285 (stderr, 286 "Loaded URL=\"%s\" ID=\"%s\"\n", 287 URL ? URL : "(null)", 288 ID ? ID : "(null)"); 289 } 290 return(ret); 291 } 292 } 293 for (i = 0;i < nbpaths;i++) { 294 xmlChar *newURL; 295 296 newURL = xmlStrdup((const xmlChar *) paths[i]); 297 newURL = xmlStrcat(newURL, (const xmlChar *) "/"); 298 newURL = xmlStrcat(newURL, (const xmlChar *) lastsegment); 299 if (newURL != NULL) { 300 ret = defaultEntityLoader((const char *)newURL, ID, ctxt); 301 if (ret != NULL) { 302 if (warning != NULL) 303 ctxt->sax->warning = warning; 304 if (err != NULL) 305 ctxt->sax->error = err; 306 if (load_trace) { 307 fprintf \ 308 (stderr, 309 "Loaded URL=\"%s\" ID=\"%s\"\n", 310 newURL, 311 ID ? ID : "(null)"); 312 } 313 xmlFree(newURL); 314 return(ret); 315 } 316 xmlFree(newURL); 317 } 318 } 319 if (err != NULL) 320 ctxt->sax->error = err; 321 if (warning != NULL) { 322 ctxt->sax->warning = warning; 323 if (URL != NULL) 324 warning(ctxt, "failed to load external entity \"%s\"\n", URL); 325 else if (ID != NULL) 326 warning(ctxt, "failed to load external entity \"%s\"\n", ID); 327 } 328 return(NULL); 329 } 330 /************************************************************************ 331 * * 332 * Memory allocation consumption debugging * 333 * * 334 ************************************************************************/ 335 336 static void 337 OOM(void) 338 { 339 fprintf(stderr, "Ran out of memory needs > %d bytes\n", maxmem); 340 progresult = XMLLINT_ERR_MEM; 341 } 342 343 static void 344 myFreeFunc(void *mem) 345 { 346 xmlMemFree(mem); 347 } 348 static void * 349 myMallocFunc(size_t size) 350 { 351 void *ret; 352 353 ret = xmlMemMalloc(size); 354 if (ret != NULL) { 355 if (xmlMemUsed() > maxmem) { 356 OOM(); 357 xmlMemFree(ret); 358 return (NULL); 359 } 360 } 361 return (ret); 362 } 363 static void * 364 myReallocFunc(void *mem, size_t size) 365 { 366 void *ret; 367 368 ret = xmlMemRealloc(mem, size); 369 if (ret != NULL) { 370 if (xmlMemUsed() > maxmem) { 371 OOM(); 372 xmlMemFree(ret); 373 return (NULL); 374 } 375 } 376 return (ret); 377 } 378 static char * 379 myStrdupFunc(const char *str) 380 { 381 char *ret; 382 383 ret = xmlMemoryStrdup(str); 384 if (ret != NULL) { 385 if (xmlMemUsed() > maxmem) { 386 OOM(); 387 xmlFree(ret); 388 return (NULL); 389 } 390 } 391 return (ret); 392 } 393 /************************************************************************ 394 * * 395 * Internal timing routines to remove the necessity to have * 396 * unix-specific function calls. * 397 * * 398 ************************************************************************/ 399 400 #ifndef HAVE_GETTIMEOFDAY 401 #ifdef HAVE_SYS_TIMEB_H 402 #ifdef HAVE_SYS_TIME_H 403 #ifdef HAVE_FTIME 404 405 static int 406 my_gettimeofday(struct timeval *tvp, void *tzp) 407 { 408 struct timeb timebuffer; 409 410 ftime(&timebuffer); 411 if (tvp) { 412 tvp->tv_sec = timebuffer.time; 413 tvp->tv_usec = timebuffer.millitm * 1000L; 414 } 415 return (0); 416 } 417 #define HAVE_GETTIMEOFDAY 1 418 #define gettimeofday my_gettimeofday 419 420 #endif /* HAVE_FTIME */ 421 #endif /* HAVE_SYS_TIME_H */ 422 #endif /* HAVE_SYS_TIMEB_H */ 423 #endif /* !HAVE_GETTIMEOFDAY */ 424 425 #if defined(HAVE_GETTIMEOFDAY) 426 static struct timeval begin, end; 427 428 /* 429 * startTimer: call where you want to start timing 430 */ 431 static void 432 startTimer(void) 433 { 434 gettimeofday(&begin, NULL); 435 } 436 437 /* 438 * endTimer: call where you want to stop timing and to print out a 439 * message about the timing performed; format is a printf 440 * type argument 441 */ 442 static void XMLCDECL 443 endTimer(const char *fmt, ...) 444 { 445 long msec; 446 va_list ap; 447 448 gettimeofday(&end, NULL); 449 msec = end.tv_sec - begin.tv_sec; 450 msec *= 1000; 451 msec += (end.tv_usec - begin.tv_usec) / 1000; 452 453 #ifndef HAVE_STDARG_H 454 #error "endTimer required stdarg functions" 455 #endif 456 va_start(ap, fmt); 457 vfprintf(stderr, fmt, ap); 458 va_end(ap); 459 460 fprintf(stderr, " took %ld ms\n", msec); 461 } 462 #elif defined(HAVE_TIME_H) 463 /* 464 * No gettimeofday function, so we have to make do with calling clock. 465 * This is obviously less accurate, but there's little we can do about 466 * that. 467 */ 468 #ifndef CLOCKS_PER_SEC 469 #define CLOCKS_PER_SEC 100 470 #endif 471 472 static clock_t begin, end; 473 static void 474 startTimer(void) 475 { 476 begin = clock(); 477 } 478 static void XMLCDECL 479 endTimer(const char *fmt, ...) 480 { 481 long msec; 482 va_list ap; 483 484 end = clock(); 485 msec = ((end - begin) * 1000) / CLOCKS_PER_SEC; 486 487 #ifndef HAVE_STDARG_H 488 #error "endTimer required stdarg functions" 489 #endif 490 va_start(ap, fmt); 491 vfprintf(stderr, fmt, ap); 492 va_end(ap); 493 fprintf(stderr, " took %ld ms\n", msec); 494 } 495 #else 496 497 /* 498 * We don't have a gettimeofday or time.h, so we just don't do timing 499 */ 500 static void 501 startTimer(void) 502 { 503 /* 504 * Do nothing 505 */ 506 } 507 static void XMLCDECL 508 endTimer(char *format, ...) 509 { 510 /* 511 * We cannot do anything because we don't have a timing function 512 */ 513 #ifdef HAVE_STDARG_H 514 va_start(ap, format); 515 vfprintf(stderr, format, ap); 516 va_end(ap); 517 fprintf(stderr, " was not timed\n", msec); 518 #else 519 /* We don't have gettimeofday, time or stdarg.h, what crazy world is 520 * this ?! 521 */ 522 #endif 523 } 524 #endif 525 /************************************************************************ 526 * * 527 * HTML ouput * 528 * * 529 ************************************************************************/ 530 static char buffer[50000]; 531 532 static void 533 xmlHTMLEncodeSend(void) { 534 char *result; 535 536 result = (char *) xmlEncodeEntitiesReentrant(NULL, BAD_CAST buffer); 537 if (result) { 538 xmlGenericError(xmlGenericErrorContext, "%s", result); 539 xmlFree(result); 540 } 541 buffer[0] = 0; 542 } 543 544 /** 545 * xmlHTMLPrintFileInfo: 546 * @input: an xmlParserInputPtr input 547 * 548 * Displays the associated file and line informations for the current input 549 */ 550 551 static void 552 xmlHTMLPrintFileInfo(xmlParserInputPtr input) { 553 int len; 554 xmlGenericError(xmlGenericErrorContext, "<p>"); 555 556 len = strlen(buffer); 557 if (input != NULL) { 558 if (input->filename) { 559 snprintf(&buffer[len], sizeof(buffer) - len, "%s:%d: ", input->filename, 560 input->line); 561 } else { 562 snprintf(&buffer[len], sizeof(buffer) - len, "Entity: line %d: ", input->line); 563 } 564 } 565 xmlHTMLEncodeSend(); 566 } 567 568 /** 569 * xmlHTMLPrintFileContext: 570 * @input: an xmlParserInputPtr input 571 * 572 * Displays current context within the input content for error tracking 573 */ 574 575 static void 576 xmlHTMLPrintFileContext(xmlParserInputPtr input) { 577 const xmlChar *cur, *base; 578 int len; 579 int n; 580 581 if (input == NULL) return; 582 xmlGenericError(xmlGenericErrorContext, "<pre>\n"); 583 cur = input->cur; 584 base = input->base; 585 while ((cur > base) && ((*cur == '\n') || (*cur == '\r'))) { 586 cur--; 587 } 588 n = 0; 589 while ((n++ < 80) && (cur > base) && (*cur != '\n') && (*cur != '\r')) 590 cur--; 591 if ((*cur == '\n') || (*cur == '\r')) cur++; 592 base = cur; 593 n = 0; 594 while ((*cur != 0) && (*cur != '\n') && (*cur != '\r') && (n < 79)) { 595 len = strlen(buffer); 596 snprintf(&buffer[len], sizeof(buffer) - len, "%c", 597 (unsigned char) *cur++); 598 n++; 599 } 600 len = strlen(buffer); 601 snprintf(&buffer[len], sizeof(buffer) - len, "\n"); 602 cur = input->cur; 603 while ((*cur == '\n') || (*cur == '\r')) 604 cur--; 605 n = 0; 606 while ((cur != base) && (n++ < 80)) { 607 len = strlen(buffer); 608 snprintf(&buffer[len], sizeof(buffer) - len, " "); 609 base++; 610 } 611 len = strlen(buffer); 612 snprintf(&buffer[len], sizeof(buffer) - len, "^\n"); 613 xmlHTMLEncodeSend(); 614 xmlGenericError(xmlGenericErrorContext, "</pre>"); 615 } 616 617 /** 618 * xmlHTMLError: 619 * @ctx: an XML parser context 620 * @msg: the message to display/transmit 621 * @...: extra parameters for the message display 622 * 623 * Display and format an error messages, gives file, line, position and 624 * extra parameters. 625 */ 626 static void XMLCDECL 627 xmlHTMLError(void *ctx, const char *msg, ...) 628 { 629 xmlParserCtxtPtr ctxt = (xmlParserCtxtPtr) ctx; 630 xmlParserInputPtr input; 631 va_list args; 632 int len; 633 634 buffer[0] = 0; 635 input = ctxt->input; 636 if ((input != NULL) && (input->filename == NULL) && (ctxt->inputNr > 1)) { 637 input = ctxt->inputTab[ctxt->inputNr - 2]; 638 } 639 640 xmlHTMLPrintFileInfo(input); 641 642 xmlGenericError(xmlGenericErrorContext, "<b>error</b>: "); 643 va_start(args, msg); 644 len = strlen(buffer); 645 vsnprintf(&buffer[len], sizeof(buffer) - len, msg, args); 646 va_end(args); 647 xmlHTMLEncodeSend(); 648 xmlGenericError(xmlGenericErrorContext, "</p>\n"); 649 650 xmlHTMLPrintFileContext(input); 651 xmlHTMLEncodeSend(); 652 } 653 654 /** 655 * xmlHTMLWarning: 656 * @ctx: an XML parser context 657 * @msg: the message to display/transmit 658 * @...: extra parameters for the message display 659 * 660 * Display and format a warning messages, gives file, line, position and 661 * extra parameters. 662 */ 663 static void XMLCDECL 664 xmlHTMLWarning(void *ctx, const char *msg, ...) 665 { 666 xmlParserCtxtPtr ctxt = (xmlParserCtxtPtr) ctx; 667 xmlParserInputPtr input; 668 va_list args; 669 int len; 670 671 buffer[0] = 0; 672 input = ctxt->input; 673 if ((input != NULL) && (input->filename == NULL) && (ctxt->inputNr > 1)) { 674 input = ctxt->inputTab[ctxt->inputNr - 2]; 675 } 676 677 678 xmlHTMLPrintFileInfo(input); 679 680 xmlGenericError(xmlGenericErrorContext, "<b>warning</b>: "); 681 va_start(args, msg); 682 len = strlen(buffer); 683 vsnprintf(&buffer[len], sizeof(buffer) - len, msg, args); 684 va_end(args); 685 xmlHTMLEncodeSend(); 686 xmlGenericError(xmlGenericErrorContext, "</p>\n"); 687 688 xmlHTMLPrintFileContext(input); 689 xmlHTMLEncodeSend(); 690 } 691 692 /** 693 * xmlHTMLValidityError: 694 * @ctx: an XML parser context 695 * @msg: the message to display/transmit 696 * @...: extra parameters for the message display 697 * 698 * Display and format an validity error messages, gives file, 699 * line, position and extra parameters. 700 */ 701 static void XMLCDECL 702 xmlHTMLValidityError(void *ctx, const char *msg, ...) 703 { 704 xmlParserCtxtPtr ctxt = (xmlParserCtxtPtr) ctx; 705 xmlParserInputPtr input; 706 va_list args; 707 int len; 708 709 buffer[0] = 0; 710 input = ctxt->input; 711 if ((input->filename == NULL) && (ctxt->inputNr > 1)) 712 input = ctxt->inputTab[ctxt->inputNr - 2]; 713 714 xmlHTMLPrintFileInfo(input); 715 716 xmlGenericError(xmlGenericErrorContext, "<b>validity error</b>: "); 717 len = strlen(buffer); 718 va_start(args, msg); 719 vsnprintf(&buffer[len], sizeof(buffer) - len, msg, args); 720 va_end(args); 721 xmlHTMLEncodeSend(); 722 xmlGenericError(xmlGenericErrorContext, "</p>\n"); 723 724 xmlHTMLPrintFileContext(input); 725 xmlHTMLEncodeSend(); 726 progresult = XMLLINT_ERR_VALID; 727 } 728 729 /** 730 * xmlHTMLValidityWarning: 731 * @ctx: an XML parser context 732 * @msg: the message to display/transmit 733 * @...: extra parameters for the message display 734 * 735 * Display and format a validity warning messages, gives file, line, 736 * position and extra parameters. 737 */ 738 static void XMLCDECL 739 xmlHTMLValidityWarning(void *ctx, const char *msg, ...) 740 { 741 xmlParserCtxtPtr ctxt = (xmlParserCtxtPtr) ctx; 742 xmlParserInputPtr input; 743 va_list args; 744 int len; 745 746 buffer[0] = 0; 747 input = ctxt->input; 748 if ((input->filename == NULL) && (ctxt->inputNr > 1)) 749 input = ctxt->inputTab[ctxt->inputNr - 2]; 750 751 xmlHTMLPrintFileInfo(input); 752 753 xmlGenericError(xmlGenericErrorContext, "<b>validity warning</b>: "); 754 va_start(args, msg); 755 len = strlen(buffer); 756 vsnprintf(&buffer[len], sizeof(buffer) - len, msg, args); 757 va_end(args); 758 xmlHTMLEncodeSend(); 759 xmlGenericError(xmlGenericErrorContext, "</p>\n"); 760 761 xmlHTMLPrintFileContext(input); 762 xmlHTMLEncodeSend(); 763 } 764 765 /************************************************************************ 766 * * 767 * Shell Interface * 768 * * 769 ************************************************************************/ 770 #ifdef LIBXML_DEBUG_ENABLED 771 #ifdef LIBXML_XPATH_ENABLED 772 /** 773 * xmlShellReadline: 774 * @prompt: the prompt value 775 * 776 * Read a string 777 * 778 * Returns a pointer to it or NULL on EOF the caller is expected to 779 * free the returned string. 780 */ 781 static char * 782 xmlShellReadline(char *prompt) { 783 #ifdef HAVE_LIBREADLINE 784 char *line_read; 785 786 /* Get a line from the user. */ 787 line_read = readline (prompt); 788 789 /* If the line has any text in it, save it on the history. */ 790 if (line_read && *line_read) 791 add_history (line_read); 792 793 return (line_read); 794 #else 795 char line_read[501]; 796 char *ret; 797 int len; 798 799 if (prompt != NULL) 800 fprintf(stdout, "%s", prompt); 801 if (!fgets(line_read, 500, stdin)) 802 return(NULL); 803 line_read[500] = 0; 804 len = strlen(line_read); 805 ret = (char *) malloc(len + 1); 806 if (ret != NULL) { 807 memcpy (ret, line_read, len + 1); 808 } 809 return(ret); 810 #endif 811 } 812 #endif /* LIBXML_XPATH_ENABLED */ 813 #endif /* LIBXML_DEBUG_ENABLED */ 814 815 /************************************************************************ 816 * * 817 * I/O Interfaces * 818 * * 819 ************************************************************************/ 820 821 static int myRead(FILE *f, char * buf, int len) { 822 return(fread(buf, 1, len, f)); 823 } 824 static void myClose(FILE *f) { 825 if (f != stdin) { 826 fclose(f); 827 } 828 } 829 830 /************************************************************************ 831 * * 832 * SAX based tests * 833 * * 834 ************************************************************************/ 835 836 /* 837 * empty SAX block 838 */ 839 static xmlSAXHandler emptySAXHandlerStruct = { 840 NULL, /* internalSubset */ 841 NULL, /* isStandalone */ 842 NULL, /* hasInternalSubset */ 843 NULL, /* hasExternalSubset */ 844 NULL, /* resolveEntity */ 845 NULL, /* getEntity */ 846 NULL, /* entityDecl */ 847 NULL, /* notationDecl */ 848 NULL, /* attributeDecl */ 849 NULL, /* elementDecl */ 850 NULL, /* unparsedEntityDecl */ 851 NULL, /* setDocumentLocator */ 852 NULL, /* startDocument */ 853 NULL, /* endDocument */ 854 NULL, /* startElement */ 855 NULL, /* endElement */ 856 NULL, /* reference */ 857 NULL, /* characters */ 858 NULL, /* ignorableWhitespace */ 859 NULL, /* processingInstruction */ 860 NULL, /* comment */ 861 NULL, /* xmlParserWarning */ 862 NULL, /* xmlParserError */ 863 NULL, /* xmlParserError */ 864 NULL, /* getParameterEntity */ 865 NULL, /* cdataBlock; */ 866 NULL, /* externalSubset; */ 867 XML_SAX2_MAGIC, 868 NULL, 869 NULL, /* startElementNs */ 870 NULL, /* endElementNs */ 871 NULL /* xmlStructuredErrorFunc */ 872 }; 873 874 static xmlSAXHandlerPtr emptySAXHandler = &emptySAXHandlerStruct; 875 extern xmlSAXHandlerPtr debugSAXHandler; 876 static int callbacks; 877 878 /** 879 * isStandaloneDebug: 880 * @ctxt: An XML parser context 881 * 882 * Is this document tagged standalone ? 883 * 884 * Returns 1 if true 885 */ 886 static int 887 isStandaloneDebug(void *ctx ATTRIBUTE_UNUSED) 888 { 889 callbacks++; 890 if (noout) 891 return(0); 892 fprintf(stdout, "SAX.isStandalone()\n"); 893 return(0); 894 } 895 896 /** 897 * hasInternalSubsetDebug: 898 * @ctxt: An XML parser context 899 * 900 * Does this document has an internal subset 901 * 902 * Returns 1 if true 903 */ 904 static int 905 hasInternalSubsetDebug(void *ctx ATTRIBUTE_UNUSED) 906 { 907 callbacks++; 908 if (noout) 909 return(0); 910 fprintf(stdout, "SAX.hasInternalSubset()\n"); 911 return(0); 912 } 913 914 /** 915 * hasExternalSubsetDebug: 916 * @ctxt: An XML parser context 917 * 918 * Does this document has an external subset 919 * 920 * Returns 1 if true 921 */ 922 static int 923 hasExternalSubsetDebug(void *ctx ATTRIBUTE_UNUSED) 924 { 925 callbacks++; 926 if (noout) 927 return(0); 928 fprintf(stdout, "SAX.hasExternalSubset()\n"); 929 return(0); 930 } 931 932 /** 933 * internalSubsetDebug: 934 * @ctxt: An XML parser context 935 * 936 * Does this document has an internal subset 937 */ 938 static void 939 internalSubsetDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *name, 940 const xmlChar *ExternalID, const xmlChar *SystemID) 941 { 942 callbacks++; 943 if (noout) 944 return; 945 fprintf(stdout, "SAX.internalSubset(%s,", name); 946 if (ExternalID == NULL) 947 fprintf(stdout, " ,"); 948 else 949 fprintf(stdout, " %s,", ExternalID); 950 if (SystemID == NULL) 951 fprintf(stdout, " )\n"); 952 else 953 fprintf(stdout, " %s)\n", SystemID); 954 } 955 956 /** 957 * externalSubsetDebug: 958 * @ctxt: An XML parser context 959 * 960 * Does this document has an external subset 961 */ 962 static void 963 externalSubsetDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *name, 964 const xmlChar *ExternalID, const xmlChar *SystemID) 965 { 966 callbacks++; 967 if (noout) 968 return; 969 fprintf(stdout, "SAX.externalSubset(%s,", name); 970 if (ExternalID == NULL) 971 fprintf(stdout, " ,"); 972 else 973 fprintf(stdout, " %s,", ExternalID); 974 if (SystemID == NULL) 975 fprintf(stdout, " )\n"); 976 else 977 fprintf(stdout, " %s)\n", SystemID); 978 } 979 980 /** 981 * resolveEntityDebug: 982 * @ctxt: An XML parser context 983 * @publicId: The public ID of the entity 984 * @systemId: The system ID of the entity 985 * 986 * Special entity resolver, better left to the parser, it has 987 * more context than the application layer. 988 * The default behaviour is to NOT resolve the entities, in that case 989 * the ENTITY_REF nodes are built in the structure (and the parameter 990 * values). 991 * 992 * Returns the xmlParserInputPtr if inlined or NULL for DOM behaviour. 993 */ 994 static xmlParserInputPtr 995 resolveEntityDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *publicId, const xmlChar *systemId) 996 { 997 callbacks++; 998 if (noout) 999 return(NULL); 1000 /* xmlParserCtxtPtr ctxt = (xmlParserCtxtPtr) ctx; */ 1001 1002 1003 fprintf(stdout, "SAX.resolveEntity("); 1004 if (publicId != NULL) 1005 fprintf(stdout, "%s", (char *)publicId); 1006 else 1007 fprintf(stdout, " "); 1008 if (systemId != NULL) 1009 fprintf(stdout, ", %s)\n", (char *)systemId); 1010 else 1011 fprintf(stdout, ", )\n"); 1012 return(NULL); 1013 } 1014 1015 /** 1016 * getEntityDebug: 1017 * @ctxt: An XML parser context 1018 * @name: The entity name 1019 * 1020 * Get an entity by name 1021 * 1022 * Returns the xmlParserInputPtr if inlined or NULL for DOM behaviour. 1023 */ 1024 static xmlEntityPtr 1025 getEntityDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *name) 1026 { 1027 callbacks++; 1028 if (noout) 1029 return(NULL); 1030 fprintf(stdout, "SAX.getEntity(%s)\n", name); 1031 return(NULL); 1032 } 1033 1034 /** 1035 * getParameterEntityDebug: 1036 * @ctxt: An XML parser context 1037 * @name: The entity name 1038 * 1039 * Get a parameter entity by name 1040 * 1041 * Returns the xmlParserInputPtr 1042 */ 1043 static xmlEntityPtr 1044 getParameterEntityDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *name) 1045 { 1046 callbacks++; 1047 if (noout) 1048 return(NULL); 1049 fprintf(stdout, "SAX.getParameterEntity(%s)\n", name); 1050 return(NULL); 1051 } 1052 1053 1054 /** 1055 * entityDeclDebug: 1056 * @ctxt: An XML parser context 1057 * @name: the entity name 1058 * @type: the entity type 1059 * @publicId: The public ID of the entity 1060 * @systemId: The system ID of the entity 1061 * @content: the entity value (without processing). 1062 * 1063 * An entity definition has been parsed 1064 */ 1065 static void 1066 entityDeclDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *name, int type, 1067 const xmlChar *publicId, const xmlChar *systemId, xmlChar *content) 1068 { 1069 const xmlChar *nullstr = BAD_CAST "(null)"; 1070 /* not all libraries handle printing null pointers nicely */ 1071 if (publicId == NULL) 1072 publicId = nullstr; 1073 if (systemId == NULL) 1074 systemId = nullstr; 1075 if (content == NULL) 1076 content = (xmlChar *)nullstr; 1077 callbacks++; 1078 if (noout) 1079 return; 1080 fprintf(stdout, "SAX.entityDecl(%s, %d, %s, %s, %s)\n", 1081 name, type, publicId, systemId, content); 1082 } 1083 1084 /** 1085 * attributeDeclDebug: 1086 * @ctxt: An XML parser context 1087 * @name: the attribute name 1088 * @type: the attribute type 1089 * 1090 * An attribute definition has been parsed 1091 */ 1092 static void 1093 attributeDeclDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar * elem, 1094 const xmlChar * name, int type, int def, 1095 const xmlChar * defaultValue, xmlEnumerationPtr tree) 1096 { 1097 callbacks++; 1098 if (noout) 1099 return; 1100 if (defaultValue == NULL) 1101 fprintf(stdout, "SAX.attributeDecl(%s, %s, %d, %d, NULL, ...)\n", 1102 elem, name, type, def); 1103 else 1104 fprintf(stdout, "SAX.attributeDecl(%s, %s, %d, %d, %s, ...)\n", 1105 elem, name, type, def, defaultValue); 1106 xmlFreeEnumeration(tree); 1107 } 1108 1109 /** 1110 * elementDeclDebug: 1111 * @ctxt: An XML parser context 1112 * @name: the element name 1113 * @type: the element type 1114 * @content: the element value (without processing). 1115 * 1116 * An element definition has been parsed 1117 */ 1118 static void 1119 elementDeclDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *name, int type, 1120 xmlElementContentPtr content ATTRIBUTE_UNUSED) 1121 { 1122 callbacks++; 1123 if (noout) 1124 return; 1125 fprintf(stdout, "SAX.elementDecl(%s, %d, ...)\n", 1126 name, type); 1127 } 1128 1129 /** 1130 * notationDeclDebug: 1131 * @ctxt: An XML parser context 1132 * @name: The name of the notation 1133 * @publicId: The public ID of the entity 1134 * @systemId: The system ID of the entity 1135 * 1136 * What to do when a notation declaration has been parsed. 1137 */ 1138 static void 1139 notationDeclDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *name, 1140 const xmlChar *publicId, const xmlChar *systemId) 1141 { 1142 callbacks++; 1143 if (noout) 1144 return; 1145 fprintf(stdout, "SAX.notationDecl(%s, %s, %s)\n", 1146 (char *) name, (char *) publicId, (char *) systemId); 1147 } 1148 1149 /** 1150 * unparsedEntityDeclDebug: 1151 * @ctxt: An XML parser context 1152 * @name: The name of the entity 1153 * @publicId: The public ID of the entity 1154 * @systemId: The system ID of the entity 1155 * @notationName: the name of the notation 1156 * 1157 * What to do when an unparsed entity declaration is parsed 1158 */ 1159 static void 1160 unparsedEntityDeclDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *name, 1161 const xmlChar *publicId, const xmlChar *systemId, 1162 const xmlChar *notationName) 1163 { 1164 const xmlChar *nullstr = BAD_CAST "(null)"; 1165 1166 if (publicId == NULL) 1167 publicId = nullstr; 1168 if (systemId == NULL) 1169 systemId = nullstr; 1170 if (notationName == NULL) 1171 notationName = nullstr; 1172 callbacks++; 1173 if (noout) 1174 return; 1175 fprintf(stdout, "SAX.unparsedEntityDecl(%s, %s, %s, %s)\n", 1176 (char *) name, (char *) publicId, (char *) systemId, 1177 (char *) notationName); 1178 } 1179 1180 /** 1181 * setDocumentLocatorDebug: 1182 * @ctxt: An XML parser context 1183 * @loc: A SAX Locator 1184 * 1185 * Receive the document locator at startup, actually xmlDefaultSAXLocator 1186 * Everything is available on the context, so this is useless in our case. 1187 */ 1188 static void 1189 setDocumentLocatorDebug(void *ctx ATTRIBUTE_UNUSED, xmlSAXLocatorPtr loc ATTRIBUTE_UNUSED) 1190 { 1191 callbacks++; 1192 if (noout) 1193 return; 1194 fprintf(stdout, "SAX.setDocumentLocator()\n"); 1195 } 1196 1197 /** 1198 * startDocumentDebug: 1199 * @ctxt: An XML parser context 1200 * 1201 * called when the document start being processed. 1202 */ 1203 static void 1204 startDocumentDebug(void *ctx ATTRIBUTE_UNUSED) 1205 { 1206 callbacks++; 1207 if (noout) 1208 return; 1209 fprintf(stdout, "SAX.startDocument()\n"); 1210 } 1211 1212 /** 1213 * endDocumentDebug: 1214 * @ctxt: An XML parser context 1215 * 1216 * called when the document end has been detected. 1217 */ 1218 static void 1219 endDocumentDebug(void *ctx ATTRIBUTE_UNUSED) 1220 { 1221 callbacks++; 1222 if (noout) 1223 return; 1224 fprintf(stdout, "SAX.endDocument()\n"); 1225 } 1226 1227 /** 1228 * startElementDebug: 1229 * @ctxt: An XML parser context 1230 * @name: The element name 1231 * 1232 * called when an opening tag has been processed. 1233 */ 1234 static void 1235 startElementDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *name, const xmlChar **atts) 1236 { 1237 int i; 1238 1239 callbacks++; 1240 if (noout) 1241 return; 1242 fprintf(stdout, "SAX.startElement(%s", (char *) name); 1243 if (atts != NULL) { 1244 for (i = 0;(atts[i] != NULL);i++) { 1245 fprintf(stdout, ", %s='", atts[i++]); 1246 if (atts[i] != NULL) 1247 fprintf(stdout, "%s'", atts[i]); 1248 } 1249 } 1250 fprintf(stdout, ")\n"); 1251 } 1252 1253 /** 1254 * endElementDebug: 1255 * @ctxt: An XML parser context 1256 * @name: The element name 1257 * 1258 * called when the end of an element has been detected. 1259 */ 1260 static void 1261 endElementDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *name) 1262 { 1263 callbacks++; 1264 if (noout) 1265 return; 1266 fprintf(stdout, "SAX.endElement(%s)\n", (char *) name); 1267 } 1268 1269 /** 1270 * charactersDebug: 1271 * @ctxt: An XML parser context 1272 * @ch: a xmlChar string 1273 * @len: the number of xmlChar 1274 * 1275 * receiving some chars from the parser. 1276 * Question: how much at a time ??? 1277 */ 1278 static void 1279 charactersDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *ch, int len) 1280 { 1281 char out[40]; 1282 int i; 1283 1284 callbacks++; 1285 if (noout) 1286 return; 1287 for (i = 0;(i<len) && (i < 30);i++) 1288 out[i] = ch[i]; 1289 out[i] = 0; 1290 1291 fprintf(stdout, "SAX.characters(%s, %d)\n", out, len); 1292 } 1293 1294 /** 1295 * referenceDebug: 1296 * @ctxt: An XML parser context 1297 * @name: The entity name 1298 * 1299 * called when an entity reference is detected. 1300 */ 1301 static void 1302 referenceDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *name) 1303 { 1304 callbacks++; 1305 if (noout) 1306 return; 1307 fprintf(stdout, "SAX.reference(%s)\n", name); 1308 } 1309 1310 /** 1311 * ignorableWhitespaceDebug: 1312 * @ctxt: An XML parser context 1313 * @ch: a xmlChar string 1314 * @start: the first char in the string 1315 * @len: the number of xmlChar 1316 * 1317 * receiving some ignorable whitespaces from the parser. 1318 * Question: how much at a time ??? 1319 */ 1320 static void 1321 ignorableWhitespaceDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *ch, int len) 1322 { 1323 char out[40]; 1324 int i; 1325 1326 callbacks++; 1327 if (noout) 1328 return; 1329 for (i = 0;(i<len) && (i < 30);i++) 1330 out[i] = ch[i]; 1331 out[i] = 0; 1332 fprintf(stdout, "SAX.ignorableWhitespace(%s, %d)\n", out, len); 1333 } 1334 1335 /** 1336 * processingInstructionDebug: 1337 * @ctxt: An XML parser context 1338 * @target: the target name 1339 * @data: the PI data's 1340 * @len: the number of xmlChar 1341 * 1342 * A processing instruction has been parsed. 1343 */ 1344 static void 1345 processingInstructionDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *target, 1346 const xmlChar *data) 1347 { 1348 callbacks++; 1349 if (noout) 1350 return; 1351 if (data != NULL) 1352 fprintf(stdout, "SAX.processingInstruction(%s, %s)\n", 1353 (char *) target, (char *) data); 1354 else 1355 fprintf(stdout, "SAX.processingInstruction(%s, NULL)\n", 1356 (char *) target); 1357 } 1358 1359 /** 1360 * cdataBlockDebug: 1361 * @ctx: the user data (XML parser context) 1362 * @value: The pcdata content 1363 * @len: the block length 1364 * 1365 * called when a pcdata block has been parsed 1366 */ 1367 static void 1368 cdataBlockDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *value, int len) 1369 { 1370 callbacks++; 1371 if (noout) 1372 return; 1373 fprintf(stdout, "SAX.pcdata(%.20s, %d)\n", 1374 (char *) value, len); 1375 } 1376 1377 /** 1378 * commentDebug: 1379 * @ctxt: An XML parser context 1380 * @value: the comment content 1381 * 1382 * A comment has been parsed. 1383 */ 1384 static void 1385 commentDebug(void *ctx ATTRIBUTE_UNUSED, const xmlChar *value) 1386 { 1387 callbacks++; 1388 if (noout) 1389 return; 1390 fprintf(stdout, "SAX.comment(%s)\n", value); 1391 } 1392 1393 /** 1394 * warningDebug: 1395 * @ctxt: An XML parser context 1396 * @msg: the message to display/transmit 1397 * @...: extra parameters for the message display 1398 * 1399 * Display and format a warning messages, gives file, line, position and 1400 * extra parameters. 1401 */ 1402 static void XMLCDECL 1403 warningDebug(void *ctx ATTRIBUTE_UNUSED, const char *msg, ...) 1404 { 1405 va_list args; 1406 1407 callbacks++; 1408 if (noout) 1409 return; 1410 va_start(args, msg); 1411 fprintf(stdout, "SAX.warning: "); 1412 vfprintf(stdout, msg, args); 1413 va_end(args); 1414 } 1415 1416 /** 1417 * errorDebug: 1418 * @ctxt: An XML parser context 1419 * @msg: the message to display/transmit 1420 * @...: extra parameters for the message display 1421 * 1422 * Display and format a error messages, gives file, line, position and 1423 * extra parameters. 1424 */ 1425 static void XMLCDECL 1426 errorDebug(void *ctx ATTRIBUTE_UNUSED, const char *msg, ...) 1427 { 1428 va_list args; 1429 1430 callbacks++; 1431 if (noout) 1432 return; 1433 va_start(args, msg); 1434 fprintf(stdout, "SAX.error: "); 1435 vfprintf(stdout, msg, args); 1436 va_end(args); 1437 } 1438 1439 /** 1440 * fatalErrorDebug: 1441 * @ctxt: An XML parser context 1442 * @msg: the message to display/transmit 1443 * @...: extra parameters for the message display 1444 * 1445 * Display and format a fatalError messages, gives file, line, position and 1446 * extra parameters. 1447 */ 1448 static void XMLCDECL 1449 fatalErrorDebug(void *ctx ATTRIBUTE_UNUSED, const char *msg, ...) 1450 { 1451 va_list args; 1452 1453 callbacks++; 1454 if (noout) 1455 return; 1456 va_start(args, msg); 1457 fprintf(stdout, "SAX.fatalError: "); 1458 vfprintf(stdout, msg, args); 1459 va_end(args); 1460 } 1461 1462 static xmlSAXHandler debugSAXHandlerStruct = { 1463 internalSubsetDebug, 1464 isStandaloneDebug, 1465 hasInternalSubsetDebug, 1466 hasExternalSubsetDebug, 1467 resolveEntityDebug, 1468 getEntityDebug, 1469 entityDeclDebug, 1470 notationDeclDebug, 1471 attributeDeclDebug, 1472 elementDeclDebug, 1473 unparsedEntityDeclDebug, 1474 setDocumentLocatorDebug, 1475 startDocumentDebug, 1476 endDocumentDebug, 1477 startElementDebug, 1478 endElementDebug, 1479 referenceDebug, 1480 charactersDebug, 1481 ignorableWhitespaceDebug, 1482 processingInstructionDebug, 1483 commentDebug, 1484 warningDebug, 1485 errorDebug, 1486 fatalErrorDebug, 1487 getParameterEntityDebug, 1488 cdataBlockDebug, 1489 externalSubsetDebug, 1490 1, 1491 NULL, 1492 NULL, 1493 NULL, 1494 NULL 1495 }; 1496 1497 xmlSAXHandlerPtr debugSAXHandler = &debugSAXHandlerStruct; 1498 1499 /* 1500 * SAX2 specific callbacks 1501 */ 1502 /** 1503 * startElementNsDebug: 1504 * @ctxt: An XML parser context 1505 * @name: The element name 1506 * 1507 * called when an opening tag has been processed. 1508 */ 1509 static void 1510 startElementNsDebug(void *ctx ATTRIBUTE_UNUSED, 1511 const xmlChar *localname, 1512 const xmlChar *prefix, 1513 const xmlChar *URI, 1514 int nb_namespaces, 1515 const xmlChar **namespaces, 1516 int nb_attributes, 1517 int nb_defaulted, 1518 const xmlChar **attributes) 1519 { 1520 int i; 1521 1522 callbacks++; 1523 if (noout) 1524 return; 1525 fprintf(stdout, "SAX.startElementNs(%s", (char *) localname); 1526 if (prefix == NULL) 1527 fprintf(stdout, ", NULL"); 1528 else 1529 fprintf(stdout, ", %s", (char *) prefix); 1530 if (URI == NULL) 1531 fprintf(stdout, ", NULL"); 1532 else 1533 fprintf(stdout, ", '%s'", (char *) URI); 1534 fprintf(stdout, ", %d", nb_namespaces); 1535 1536 if (namespaces != NULL) { 1537 for (i = 0;i < nb_namespaces * 2;i++) { 1538 fprintf(stdout, ", xmlns"); 1539 if (namespaces[i] != NULL) 1540 fprintf(stdout, ":%s", namespaces[i]); 1541 i++; 1542 fprintf(stdout, "='%s'", namespaces[i]); 1543 } 1544 } 1545 fprintf(stdout, ", %d, %d", nb_attributes, nb_defaulted); 1546 if (attributes != NULL) { 1547 for (i = 0;i < nb_attributes * 5;i += 5) { 1548 if (attributes[i + 1] != NULL) 1549 fprintf(stdout, ", %s:%s='", attributes[i + 1], attributes[i]); 1550 else 1551 fprintf(stdout, ", %s='", attributes[i]); 1552 fprintf(stdout, "%.4s...', %d", attributes[i + 3], 1553 (int)(attributes[i + 4] - attributes[i + 3])); 1554 } 1555 } 1556 fprintf(stdout, ")\n"); 1557 } 1558 1559 /** 1560 * endElementDebug: 1561 * @ctxt: An XML parser context 1562 * @name: The element name 1563 * 1564 * called when the end of an element has been detected. 1565 */ 1566 static void 1567 endElementNsDebug(void *ctx ATTRIBUTE_UNUSED, 1568 const xmlChar *localname, 1569 const xmlChar *prefix, 1570 const xmlChar *URI) 1571 { 1572 callbacks++; 1573 if (noout) 1574 return; 1575 fprintf(stdout, "SAX.endElementNs(%s", (char *) localname); 1576 if (prefix == NULL) 1577 fprintf(stdout, ", NULL"); 1578 else 1579 fprintf(stdout, ", %s", (char *) prefix); 1580 if (URI == NULL) 1581 fprintf(stdout, ", NULL)\n"); 1582 else 1583 fprintf(stdout, ", '%s')\n", (char *) URI); 1584 } 1585 1586 static xmlSAXHandler debugSAX2HandlerStruct = { 1587 internalSubsetDebug, 1588 isStandaloneDebug, 1589 hasInternalSubsetDebug, 1590 hasExternalSubsetDebug, 1591 resolveEntityDebug, 1592 getEntityDebug, 1593 entityDeclDebug, 1594 notationDeclDebug, 1595 attributeDeclDebug, 1596 elementDeclDebug, 1597 unparsedEntityDeclDebug, 1598 setDocumentLocatorDebug, 1599 startDocumentDebug, 1600 endDocumentDebug, 1601 NULL, 1602 NULL, 1603 referenceDebug, 1604 charactersDebug, 1605 ignorableWhitespaceDebug, 1606 processingInstructionDebug, 1607 commentDebug, 1608 warningDebug, 1609 errorDebug, 1610 fatalErrorDebug, 1611 getParameterEntityDebug, 1612 cdataBlockDebug, 1613 externalSubsetDebug, 1614 XML_SAX2_MAGIC, 1615 NULL, 1616 startElementNsDebug, 1617 endElementNsDebug, 1618 NULL 1619 }; 1620 1621 static xmlSAXHandlerPtr debugSAX2Handler = &debugSAX2HandlerStruct; 1622 1623 static void 1624 testSAX(const char *filename) { 1625 xmlSAXHandlerPtr handler; 1626 const char *user_data = "user_data"; /* mostly for debugging */ 1627 xmlParserInputBufferPtr buf = NULL; 1628 xmlParserInputPtr inputStream; 1629 xmlParserCtxtPtr ctxt = NULL; 1630 xmlSAXHandlerPtr old_sax = NULL; 1631 1632 callbacks = 0; 1633 1634 if (noout) { 1635 handler = emptySAXHandler; 1636 #ifdef LIBXML_SAX1_ENABLED 1637 } else if (sax1) { 1638 handler = debugSAXHandler; 1639 #endif 1640 } else { 1641 handler = debugSAX2Handler; 1642 } 1643 1644 /* 1645 * it's not the simplest code but the most generic in term of I/O 1646 */ 1647 buf = xmlParserInputBufferCreateFilename(filename, XML_CHAR_ENCODING_NONE); 1648 if (buf == NULL) { 1649 goto error; 1650 } 1651 1652 #ifdef LIBXML_SCHEMAS_ENABLED 1653 if (wxschemas != NULL) { 1654 int ret; 1655 xmlSchemaValidCtxtPtr vctxt; 1656 1657 vctxt = xmlSchemaNewValidCtxt(wxschemas); 1658 xmlSchemaSetValidErrors(vctxt, 1659 (xmlSchemaValidityErrorFunc) fprintf, 1660 (xmlSchemaValidityWarningFunc) fprintf, 1661 stderr); 1662 1663 ret = xmlSchemaValidateStream(vctxt, buf, 0, handler, 1664 (void *)user_data); 1665 if (repeat == 0) { 1666 if (ret == 0) { 1667 fprintf(stderr, "%s validates\n", filename); 1668 } else if (ret > 0) { 1669 fprintf(stderr, "%s fails to validate\n", filename); 1670 progresult = XMLLINT_ERR_VALID; 1671 } else { 1672 fprintf(stderr, "%s validation generated an internal error\n", 1673 filename); 1674 progresult = XMLLINT_ERR_VALID; 1675 } 1676 } 1677 xmlSchemaFreeValidCtxt(vctxt); 1678 } else 1679 #endif 1680 { 1681 /* 1682 * Create the parser context amd hook the input 1683 */ 1684 ctxt = xmlNewParserCtxt(); 1685 if (ctxt == NULL) { 1686 xmlFreeParserInputBuffer(buf); 1687 goto error; 1688 } 1689 old_sax = ctxt->sax; 1690 ctxt->sax = handler; 1691 ctxt->userData = (void *) user_data; 1692 inputStream = xmlNewIOInputStream(ctxt, buf, XML_CHAR_ENCODING_NONE); 1693 if (inputStream == NULL) { 1694 xmlFreeParserInputBuffer(buf); 1695 goto error; 1696 } 1697 inputPush(ctxt, inputStream); 1698 1699 /* do the parsing */ 1700 xmlParseDocument(ctxt); 1701 1702 if (ctxt->myDoc != NULL) { 1703 fprintf(stderr, "SAX generated a doc !\n"); 1704 xmlFreeDoc(ctxt->myDoc); 1705 ctxt->myDoc = NULL; 1706 } 1707 } 1708 1709 error: 1710 if (ctxt != NULL) { 1711 ctxt->sax = old_sax; 1712 xmlFreeParserCtxt(ctxt); 1713 } 1714 } 1715 1716 /************************************************************************ 1717 * * 1718 * Stream Test processing * 1719 * * 1720 ************************************************************************/ 1721 #ifdef LIBXML_READER_ENABLED 1722 static void processNode(xmlTextReaderPtr reader) { 1723 const xmlChar *name, *value; 1724 int type, empty; 1725 1726 type = xmlTextReaderNodeType(reader); 1727 empty = xmlTextReaderIsEmptyElement(reader); 1728 1729 if (debug) { 1730 name = xmlTextReaderConstName(reader); 1731 if (name == NULL) 1732 name = BAD_CAST "--"; 1733 1734 value = xmlTextReaderConstValue(reader); 1735 1736 1737 printf("%d %d %s %d %d", 1738 xmlTextReaderDepth(reader), 1739 type, 1740 name, 1741 empty, 1742 xmlTextReaderHasValue(reader)); 1743 if (value == NULL) 1744 printf("\n"); 1745 else { 1746 printf(" %s\n", value); 1747 } 1748 } 1749 #ifdef LIBXML_PATTERN_ENABLED 1750 if (patternc) { 1751 xmlChar *path = NULL; 1752 int match = -1; 1753 1754 if (type == XML_READER_TYPE_ELEMENT) { 1755 /* do the check only on element start */ 1756 match = xmlPatternMatch(patternc, xmlTextReaderCurrentNode(reader)); 1757 1758 if (match) { 1759 path = xmlGetNodePath(xmlTextReaderCurrentNode(reader)); 1760 printf("Node %s matches pattern %s\n", path, pattern); 1761 } 1762 } 1763 if (patstream != NULL) { 1764 int ret; 1765 1766 if (type == XML_READER_TYPE_ELEMENT) { 1767 ret = xmlStreamPush(patstream, 1768 xmlTextReaderConstLocalName(reader), 1769 xmlTextReaderConstNamespaceUri(reader)); 1770 if (ret < 0) { 1771 fprintf(stderr, "xmlStreamPush() failure\n"); 1772 xmlFreeStreamCtxt(patstream); 1773 patstream = NULL; 1774 } else if (ret != match) { 1775 if (path == NULL) { 1776 path = xmlGetNodePath( 1777 xmlTextReaderCurrentNode(reader)); 1778 } 1779 fprintf(stderr, 1780 "xmlPatternMatch and xmlStreamPush disagree\n"); 1781 fprintf(stderr, 1782 " pattern %s node %s\n", 1783 pattern, path); 1784 } 1785 1786 1787 } 1788 if ((type == XML_READER_TYPE_END_ELEMENT) || 1789 ((type == XML_READER_TYPE_ELEMENT) && (empty))) { 1790 ret = xmlStreamPop(patstream); 1791 if (ret < 0) { 1792 fprintf(stderr, "xmlStreamPop() failure\n"); 1793 xmlFreeStreamCtxt(patstream); 1794 patstream = NULL; 1795 } 1796 } 1797 } 1798 if (path != NULL) 1799 xmlFree(path); 1800 } 1801 #endif 1802 } 1803 1804 static void streamFile(char *filename) { 1805 xmlTextReaderPtr reader; 1806 int ret; 1807 #ifdef HAVE_SYS_MMAN_H 1808 int fd = -1; 1809 struct stat info; 1810 const char *base = NULL; 1811 xmlParserInputBufferPtr input = NULL; 1812 1813 if (memory) { 1814 if (stat(filename, &info) < 0) 1815 return; 1816 if ((fd = open(filename, O_RDONLY)) < 0) 1817 return; 1818 base = mmap(NULL, info.st_size, PROT_READ, MAP_SHARED, fd, 0) ; 1819 if (base == (void *) MAP_FAILED) 1820 return; 1821 1822 reader = xmlReaderForMemory(base, info.st_size, filename, 1823 NULL, options); 1824 } else 1825 #endif 1826 reader = xmlReaderForFile(filename, NULL, options); 1827 #ifdef LIBXML_PATTERN_ENABLED 1828 if (pattern != NULL) { 1829 patternc = xmlPatterncompile((const xmlChar *) pattern, NULL, 0, NULL); 1830 if (patternc == NULL) { 1831 xmlGenericError(xmlGenericErrorContext, 1832 "Pattern %s failed to compile\n", pattern); 1833 progresult = XMLLINT_ERR_SCHEMAPAT; 1834 pattern = NULL; 1835 } 1836 } 1837 if (patternc != NULL) { 1838 patstream = xmlPatternGetStreamCtxt(patternc); 1839 if (patstream != NULL) { 1840 ret = xmlStreamPush(patstream, NULL, NULL); 1841 if (ret < 0) { 1842 fprintf(stderr, "xmlStreamPush() failure\n"); 1843 xmlFreeStreamCtxt(patstream); 1844 patstream = NULL; 1845 } 1846 } 1847 } 1848 #endif 1849 1850 1851 if (reader != NULL) { 1852 #ifdef LIBXML_VALID_ENABLED 1853 if (valid) 1854 xmlTextReaderSetParserProp(reader, XML_PARSER_VALIDATE, 1); 1855 else 1856 #endif /* LIBXML_VALID_ENABLED */ 1857 xmlTextReaderSetParserProp(reader, XML_PARSER_LOADDTD, 1); 1858 #ifdef LIBXML_SCHEMAS_ENABLED 1859 if (relaxng != NULL) { 1860 if ((timing) && (!repeat)) { 1861 startTimer(); 1862 } 1863 ret = xmlTextReaderRelaxNGValidate(reader, relaxng); 1864 if (ret < 0) { 1865 xmlGenericError(xmlGenericErrorContext, 1866 "Relax-NG schema %s failed to compile\n", relaxng); 1867 progresult = XMLLINT_ERR_SCHEMACOMP; 1868 relaxng = NULL; 1869 } 1870 if ((timing) && (!repeat)) { 1871 endTimer("Compiling the schemas"); 1872 } 1873 } 1874 if (schema != NULL) { 1875 if ((timing) && (!repeat)) { 1876 startTimer(); 1877 } 1878 ret = xmlTextReaderSchemaValidate(reader, schema); 1879 if (ret < 0) { 1880 xmlGenericError(xmlGenericErrorContext, 1881 "XSD schema %s failed to compile\n", schema); 1882 progresult = XMLLINT_ERR_SCHEMACOMP; 1883 schema = NULL; 1884 } 1885 if ((timing) && (!repeat)) { 1886 endTimer("Compiling the schemas"); 1887 } 1888 } 1889 #endif 1890 1891 /* 1892 * Process all nodes in sequence 1893 */ 1894 if ((timing) && (!repeat)) { 1895 startTimer(); 1896 } 1897 ret = xmlTextReaderRead(reader); 1898 while (ret == 1) { 1899 if ((debug) 1900 #ifdef LIBXML_PATTERN_ENABLED 1901 || (patternc) 1902 #endif 1903 ) 1904 processNode(reader); 1905 ret = xmlTextReaderRead(reader); 1906 } 1907 if ((timing) && (!repeat)) { 1908 #ifdef LIBXML_SCHEMAS_ENABLED 1909 if (relaxng != NULL) 1910 endTimer("Parsing and validating"); 1911 else 1912 #endif 1913 #ifdef LIBXML_VALID_ENABLED 1914 if (valid) 1915 endTimer("Parsing and validating"); 1916 else 1917 #endif 1918 endTimer("Parsing"); 1919 } 1920 1921 #ifdef LIBXML_VALID_ENABLED 1922 if (valid) { 1923 if (xmlTextReaderIsValid(reader) != 1) { 1924 xmlGenericError(xmlGenericErrorContext, 1925 "Document %s does not validate\n", filename); 1926 progresult = XMLLINT_ERR_VALID; 1927 } 1928 } 1929 #endif /* LIBXML_VALID_ENABLED */ 1930 #ifdef LIBXML_SCHEMAS_ENABLED 1931 if ((relaxng != NULL) || (schema != NULL)) { 1932 if (xmlTextReaderIsValid(reader) != 1) { 1933 fprintf(stderr, "%s fails to validate\n", filename); 1934 progresult = XMLLINT_ERR_VALID; 1935 } else { 1936 fprintf(stderr, "%s validates\n", filename); 1937 } 1938 } 1939 #endif 1940 /* 1941 * Done, cleanup and status 1942 */ 1943 xmlFreeTextReader(reader); 1944 if (ret != 0) { 1945 fprintf(stderr, "%s : failed to parse\n", filename); 1946 progresult = XMLLINT_ERR_UNCLASS; 1947 } 1948 } else { 1949 fprintf(stderr, "Unable to open %s\n", filename); 1950 progresult = XMLLINT_ERR_UNCLASS; 1951 } 1952 #ifdef LIBXML_PATTERN_ENABLED 1953 if (patstream != NULL) { 1954 xmlFreeStreamCtxt(patstream); 1955 patstream = NULL; 1956 } 1957 #endif 1958 #ifdef HAVE_SYS_MMAN_H 1959 if (memory) { 1960 xmlFreeParserInputBuffer(input); 1961 munmap((char *) base, info.st_size); 1962 close(fd); 1963 } 1964 #endif 1965 } 1966 1967 static void walkDoc(xmlDocPtr doc) { 1968 xmlTextReaderPtr reader; 1969 int ret; 1970 1971 #ifdef LIBXML_PATTERN_ENABLED 1972 xmlNodePtr root; 1973 const xmlChar *namespaces[22]; 1974 int i; 1975 xmlNsPtr ns; 1976 1977 root = xmlDocGetRootElement(doc); 1978 for (ns = root->nsDef, i = 0;ns != NULL && i < 20;ns=ns->next) { 1979 namespaces[i++] = ns->href; 1980 namespaces[i++] = ns->prefix; 1981 } 1982 namespaces[i++] = NULL; 1983 namespaces[i++] = NULL; 1984 1985 if (pattern != NULL) { 1986 patternc = xmlPatterncompile((const xmlChar *) pattern, doc->dict, 1987 0, &namespaces[0]); 1988 if (patternc == NULL) { 1989 xmlGenericError(xmlGenericErrorContext, 1990 "Pattern %s failed to compile\n", pattern); 1991 progresult = XMLLINT_ERR_SCHEMAPAT; 1992 pattern = NULL; 1993 } 1994 } 1995 if (patternc != NULL) { 1996 patstream = xmlPatternGetStreamCtxt(patternc); 1997 if (patstream != NULL) { 1998 ret = xmlStreamPush(patstream, NULL, NULL); 1999 if (ret < 0) { 2000 fprintf(stderr, "xmlStreamPush() failure\n"); 2001 xmlFreeStreamCtxt(patstream); 2002 patstream = NULL; 2003 } 2004 } 2005 } 2006 #endif /* LIBXML_PATTERN_ENABLED */ 2007 reader = xmlReaderWalker(doc); 2008 if (reader != NULL) { 2009 if ((timing) && (!repeat)) { 2010 startTimer(); 2011 } 2012 ret = xmlTextReaderRead(reader); 2013 while (ret == 1) { 2014 if ((debug) 2015 #ifdef LIBXML_PATTERN_ENABLED 2016 || (patternc) 2017 #endif 2018 ) 2019 processNode(reader); 2020 ret = xmlTextReaderRead(reader); 2021 } 2022 if ((timing) && (!repeat)) { 2023 endTimer("walking through the doc"); 2024 } 2025 xmlFreeTextReader(reader); 2026 if (ret != 0) { 2027 fprintf(stderr, "failed to walk through the doc\n"); 2028 progresult = XMLLINT_ERR_UNCLASS; 2029 } 2030 } else { 2031 fprintf(stderr, "Failed to crate a reader from the document\n"); 2032 progresult = XMLLINT_ERR_UNCLASS; 2033 } 2034 #ifdef LIBXML_PATTERN_ENABLED 2035 if (patstream != NULL) { 2036 xmlFreeStreamCtxt(patstream); 2037 patstream = NULL; 2038 } 2039 #endif 2040 } 2041 #endif /* LIBXML_READER_ENABLED */ 2042 2043 /************************************************************************ 2044 * * 2045 * Tree Test processing * 2046 * * 2047 ************************************************************************/ 2048 static void parseAndPrintFile(char *filename, xmlParserCtxtPtr rectxt) { 2049 xmlDocPtr doc = NULL; 2050 #ifdef LIBXML_TREE_ENABLED 2051 xmlDocPtr tmp; 2052 #endif /* LIBXML_TREE_ENABLED */ 2053 2054 if ((timing) && (!repeat)) 2055 startTimer(); 2056 2057 2058 #ifdef LIBXML_TREE_ENABLED 2059 if (filename == NULL) { 2060 if (generate) { 2061 xmlNodePtr n; 2062 2063 doc = xmlNewDoc(BAD_CAST "1.0"); 2064 n = xmlNewDocNode(doc, NULL, BAD_CAST "info", NULL); 2065 xmlNodeSetContent(n, BAD_CAST "abc"); 2066 xmlDocSetRootElement(doc, n); 2067 } 2068 } 2069 #endif /* LIBXML_TREE_ENABLED */ 2070 #ifdef LIBXML_HTML_ENABLED 2071 #ifdef LIBXML_PUSH_ENABLED 2072 else if ((html) && (push)) { 2073 FILE *f; 2074 2075 #if defined(_WIN32) || defined (__DJGPP__) && !defined (__CYGWIN__) 2076 f = fopen(filename, "rb"); 2077 #else 2078 f = fopen(filename, "r"); 2079 #endif 2080 if (f != NULL) { 2081 int res, size = 3; 2082 char chars[4096]; 2083 htmlParserCtxtPtr ctxt; 2084 2085 /* if (repeat) */ 2086 size = 4096; 2087 res = fread(chars, 1, 4, f); 2088 if (res > 0) { 2089 ctxt = htmlCreatePushParserCtxt(NULL, NULL, 2090 chars, res, filename, XML_CHAR_ENCODING_NONE); 2091 while ((res = fread(chars, 1, size, f)) > 0) { 2092 htmlParseChunk(ctxt, chars, res, 0); 2093 } 2094 htmlParseChunk(ctxt, chars, 0, 1); 2095 doc = ctxt->myDoc; 2096 htmlFreeParserCtxt(ctxt); 2097 } 2098 fclose(f); 2099 } 2100 } 2101 #endif /* LIBXML_PUSH_ENABLED */ 2102 #ifdef HAVE_SYS_MMAN_H 2103 else if ((html) && (memory)) { 2104 int fd; 2105 struct stat info; 2106 const char *base; 2107 if (stat(filename, &info) < 0) 2108 return; 2109 if ((fd = open(filename, O_RDONLY)) < 0) 2110 return; 2111 base = mmap(NULL, info.st_size, PROT_READ, MAP_SHARED, fd, 0) ; 2112 if (base == (void *) MAP_FAILED) 2113 return; 2114 2115 doc = htmlReadMemory((char *) base, info.st_size, filename, 2116 NULL, options); 2117 2118 munmap((char *) base, info.st_size); 2119 close(fd); 2120 } 2121 #endif 2122 else if (html) { 2123 doc = htmlReadFile(filename, NULL, options); 2124 } 2125 #endif /* LIBXML_HTML_ENABLED */ 2126 else { 2127 #ifdef LIBXML_PUSH_ENABLED 2128 /* 2129 * build an XML tree from a string; 2130 */ 2131 if (push) { 2132 FILE *f; 2133 2134 /* '-' Usually means stdin -<sven (at) zen.org> */ 2135 if ((filename[0] == '-') && (filename[1] == 0)) { 2136 f = stdin; 2137 } else { 2138 #if defined(_WIN32) || defined (__DJGPP__) && !defined (__CYGWIN__) 2139 f = fopen(filename, "rb"); 2140 #else 2141 f = fopen(filename, "r"); 2142 #endif 2143 } 2144 if (f != NULL) { 2145 int ret; 2146 int res, size = 1024; 2147 char chars[1024]; 2148 xmlParserCtxtPtr ctxt; 2149 2150 /* if (repeat) size = 1024; */ 2151 res = fread(chars, 1, 4, f); 2152 if (res > 0) { 2153 ctxt = xmlCreatePushParserCtxt(NULL, NULL, 2154 chars, res, filename); 2155 xmlCtxtUseOptions(ctxt, options); 2156 while ((res = fread(chars, 1, size, f)) > 0) { 2157 xmlParseChunk(ctxt, chars, res, 0); 2158 } 2159 xmlParseChunk(ctxt, chars, 0, 1); 2160 doc = ctxt->myDoc; 2161 ret = ctxt->wellFormed; 2162 xmlFreeParserCtxt(ctxt); 2163 if (!ret) { 2164 xmlFreeDoc(doc); 2165 doc = NULL; 2166 } 2167 } 2168 } 2169 } else 2170 #endif /* LIBXML_PUSH_ENABLED */ 2171 if (testIO) { 2172 if ((filename[0] == '-') && (filename[1] == 0)) { 2173 doc = xmlReadFd(0, NULL, NULL, options); 2174 } else { 2175 FILE *f; 2176 2177 #if defined(_WIN32) || defined (__DJGPP__) && !defined (__CYGWIN__) 2178 f = fopen(filename, "rb"); 2179 #else 2180 f = fopen(filename, "r"); 2181 #endif 2182 if (f != NULL) { 2183 if (rectxt == NULL) 2184 doc = xmlReadIO((xmlInputReadCallback) myRead, 2185 (xmlInputCloseCallback) myClose, f, 2186 filename, NULL, options); 2187 else 2188 doc = xmlCtxtReadIO(rectxt, 2189 (xmlInputReadCallback) myRead, 2190 (xmlInputCloseCallback) myClose, f, 2191 filename, NULL, options); 2192 } else 2193 doc = NULL; 2194 } 2195 } else if (htmlout) { 2196 xmlParserCtxtPtr ctxt; 2197 2198 if (rectxt == NULL) 2199 ctxt = xmlNewParserCtxt(); 2200 else 2201 ctxt = rectxt; 2202 if (ctxt == NULL) { 2203 doc = NULL; 2204 } else { 2205 ctxt->sax->error = xmlHTMLError; 2206 ctxt->sax->warning = xmlHTMLWarning; 2207 ctxt->vctxt.error = xmlHTMLValidityError; 2208 ctxt->vctxt.warning = xmlHTMLValidityWarning; 2209 2210 doc = xmlCtxtReadFile(ctxt, filename, NULL, options); 2211 2212 if (rectxt == NULL) 2213 xmlFreeParserCtxt(ctxt); 2214 } 2215 #ifdef HAVE_SYS_MMAN_H 2216 } else if (memory) { 2217 int fd; 2218 struct stat info; 2219 const char *base; 2220 if (stat(filename, &info) < 0) 2221 return; 2222 if ((fd = open(filename, O_RDONLY)) < 0) 2223 return; 2224 base = mmap(NULL, info.st_size, PROT_READ, MAP_SHARED, fd, 0) ; 2225 if (base == (void *) MAP_FAILED) 2226 return; 2227 2228 if (rectxt == NULL) 2229 doc = xmlReadMemory((char *) base, info.st_size, 2230 filename, NULL, options); 2231 else 2232 doc = xmlCtxtReadMemory(rectxt, (char *) base, info.st_size, 2233 filename, NULL, options); 2234 2235 munmap((char *) base, info.st_size); 2236 close(fd); 2237 #endif 2238 #ifdef LIBXML_VALID_ENABLED 2239 } else if (valid) { 2240 xmlParserCtxtPtr ctxt = NULL; 2241 2242 if (rectxt == NULL) 2243 ctxt = xmlNewParserCtxt(); 2244 else 2245 ctxt = rectxt; 2246 if (ctxt == NULL) { 2247 doc = NULL; 2248 } else { 2249 doc = xmlCtxtReadFile(ctxt, filename, NULL, options); 2250 2251 if (ctxt->valid == 0) 2252 progresult = XMLLINT_ERR_RDFILE; 2253 if (rectxt == NULL) 2254 xmlFreeParserCtxt(ctxt); 2255 } 2256 #endif /* LIBXML_VALID_ENABLED */ 2257 } else { 2258 if (rectxt != NULL) 2259 doc = xmlCtxtReadFile(rectxt, filename, NULL, options); 2260 else { 2261 #ifdef LIBXML_SAX1_ENABLED 2262 if (sax1) 2263 doc = xmlParseFile(filename); 2264 else 2265 #endif /* LIBXML_SAX1_ENABLED */ 2266 doc = xmlReadFile(filename, NULL, options); 2267 } 2268 } 2269 } 2270 2271 /* 2272 * If we don't have a document we might as well give up. Do we 2273 * want an error message here? <sven (at) zen.org> */ 2274 if (doc == NULL) { 2275 progresult = XMLLINT_ERR_UNCLASS; 2276 return; 2277 } 2278 2279 if ((timing) && (!repeat)) { 2280 endTimer("Parsing"); 2281 } 2282 2283 /* 2284 * Remove DOCTYPE nodes 2285 */ 2286 if (dropdtd) { 2287 xmlDtdPtr dtd; 2288 2289 dtd = xmlGetIntSubset(doc); 2290 if (dtd != NULL) { 2291 xmlUnlinkNode((xmlNodePtr)dtd); 2292 xmlFreeDtd(dtd); 2293 } 2294 } 2295 2296 #ifdef LIBXML_XINCLUDE_ENABLED 2297 if (xinclude) { 2298 if ((timing) && (!repeat)) { 2299 startTimer(); 2300 } 2301 if (xmlXIncludeProcessFlags(doc, options) < 0) 2302 progresult = XMLLINT_ERR_UNCLASS; 2303 if ((timing) && (!repeat)) { 2304 endTimer("Xinclude processing"); 2305 } 2306 } 2307 #endif 2308 2309 #ifdef LIBXML_DEBUG_ENABLED 2310 #ifdef LIBXML_XPATH_ENABLED 2311 /* 2312 * shell interaction 2313 */ 2314 if (shell) { 2315 xmlXPathOrderDocElems(doc); 2316 xmlShell(doc, filename, xmlShellReadline, stdout); 2317 } 2318 #endif 2319 #endif 2320 2321 #ifdef LIBXML_TREE_ENABLED 2322 /* 2323 * test intermediate copy if needed. 2324 */ 2325 if (copy) { 2326 tmp = doc; 2327 if (timing) { 2328 startTimer(); 2329 } 2330 doc = xmlCopyDoc(doc, 1); 2331 if (timing) { 2332 endTimer("Copying"); 2333 } 2334 if (timing) { 2335 startTimer(); 2336 } 2337 xmlFreeDoc(tmp); 2338 if (timing) { 2339 endTimer("Freeing original"); 2340 } 2341 } 2342 #endif /* LIBXML_TREE_ENABLED */ 2343 2344 #ifdef LIBXML_VALID_ENABLED 2345 if ((insert) && (!html)) { 2346 const xmlChar* list[256]; 2347 int nb, i; 2348 xmlNodePtr node; 2349 2350 if (doc->children != NULL) { 2351 node = doc->children; 2352 while ((node != NULL) && (node->last == NULL)) node = node->next; 2353 if (node != NULL) { 2354 nb = xmlValidGetValidElements(node->last, NULL, list, 256); 2355 if (nb < 0) { 2356 fprintf(stderr, "could not get valid list of elements\n"); 2357 } else if (nb == 0) { 2358 fprintf(stderr, "No element can be inserted under root\n"); 2359 } else { 2360 fprintf(stderr, "%d element types can be inserted under root:\n", 2361 nb); 2362 for (i = 0;i < nb;i++) { 2363 fprintf(stderr, "%s\n", (char *) list[i]); 2364 } 2365 } 2366 } 2367 } 2368 }else 2369 #endif /* LIBXML_VALID_ENABLED */ 2370 #ifdef LIBXML_READER_ENABLED 2371 if (walker) { 2372 walkDoc(doc); 2373 } 2374 #endif /* LIBXML_READER_ENABLED */ 2375 #ifdef LIBXML_OUTPUT_ENABLED 2376 if (noout == 0) { 2377 int ret; 2378 2379 /* 2380 * print it. 2381 */ 2382 #ifdef LIBXML_DEBUG_ENABLED 2383 if (!debug) { 2384 #endif 2385 if ((timing) && (!repeat)) { 2386 startTimer(); 2387 } 2388 #ifdef LIBXML_HTML_ENABLED 2389 if ((html) && (!xmlout)) { 2390 if (compress) { 2391 htmlSaveFile(output ? output : "-", doc); 2392 } 2393 else if (encoding != NULL) { 2394 if ( format ) { 2395 htmlSaveFileFormat(output ? output : "-", doc, encoding, 1); 2396 } 2397 else { 2398 htmlSaveFileFormat(output ? output : "-", doc, encoding, 0); 2399 } 2400 } 2401 else if (format) { 2402 htmlSaveFileFormat(output ? output : "-", doc, NULL, 1); 2403 } 2404 else { 2405 FILE *out; 2406 if (output == NULL) 2407 out = stdout; 2408 else { 2409 out = fopen(output,"wb"); 2410 } 2411 if (out != NULL) { 2412 if (htmlDocDump(out, doc) < 0) 2413 progresult = XMLLINT_ERR_OUT; 2414 2415 if (output != NULL) 2416 fclose(out); 2417 } else { 2418 fprintf(stderr, "failed to open %s\n", output); 2419 progresult = XMLLINT_ERR_OUT; 2420 } 2421 } 2422 if ((timing) && (!repeat)) { 2423 endTimer("Saving"); 2424 } 2425 } else 2426 #endif 2427 #ifdef LIBXML_C14N_ENABLED 2428 if (canonical) { 2429 xmlChar *result = NULL; 2430 int size; 2431 2432 size = xmlC14NDocDumpMemory(doc, NULL, 0, NULL, 1, &result); 2433 if (size >= 0) { 2434 write(1, result, size); 2435 xmlFree(result); 2436 } else { 2437 fprintf(stderr, "Failed to canonicalize\n"); 2438 progresult = XMLLINT_ERR_OUT; 2439 } 2440 } else 2441 if (exc_canonical) { 2442 xmlChar *result = NULL; 2443 int size; 2444 2445 size = xmlC14NDocDumpMemory(doc, NULL, 1, NULL, 1, &result); 2446 if (size >= 0) { 2447 write(1, result, size); 2448 xmlFree(result); 2449 } else { 2450 fprintf(stderr, "Failed to canonicalize\n"); 2451 progresult = XMLLINT_ERR_OUT; 2452 } 2453 } else 2454 #endif 2455 #ifdef HAVE_SYS_MMAN_H 2456 if (memory) { 2457 xmlChar *result; 2458 int len; 2459 2460 if (encoding != NULL) { 2461 if ( format ) { 2462 xmlDocDumpFormatMemoryEnc(doc, &result, &len, encoding, 1); 2463 } else { 2464 xmlDocDumpMemoryEnc(doc, &result, &len, encoding); 2465 } 2466 } else { 2467 if (format) 2468 xmlDocDumpFormatMemory(doc, &result, &len, 1); 2469 else 2470 xmlDocDumpMemory(doc, &result, &len); 2471 } 2472 if (result == NULL) { 2473 fprintf(stderr, "Failed to save\n"); 2474 progresult = XMLLINT_ERR_OUT; 2475 } else { 2476 write(1, result, len); 2477 xmlFree(result); 2478 } 2479 2480 } else 2481 #endif /* HAVE_SYS_MMAN_H */ 2482 if (compress) { 2483 xmlSaveFile(output ? output : "-", doc); 2484 } else if (oldout) { 2485 if (encoding != NULL) { 2486 if ( format ) { 2487 ret = xmlSaveFormatFileEnc(output ? output : "-", doc, 2488 encoding, 1); 2489 } 2490 else { 2491 ret = xmlSaveFileEnc(output ? output : "-", doc, 2492 encoding); 2493 } 2494 if (ret < 0) { 2495 fprintf(stderr, "failed save to %s\n", 2496 output ? output : "-"); 2497 progresult = XMLLINT_ERR_OUT; 2498 } 2499 } else if (format) { 2500 ret = xmlSaveFormatFile(output ? output : "-", doc, 1); 2501 if (ret < 0) { 2502 fprintf(stderr, "failed save to %s\n", 2503 output ? output : "-"); 2504 progresult = XMLLINT_ERR_OUT; 2505 } 2506 } else { 2507 FILE *out; 2508 if (output == NULL) 2509 out = stdout; 2510 else { 2511 out = fopen(output,"wb"); 2512 } 2513 if (out != NULL) { 2514 if (xmlDocDump(out, doc) < 0) 2515 progresult = XMLLINT_ERR_OUT; 2516 2517 if (output != NULL) 2518 fclose(out); 2519 } else { 2520 fprintf(stderr, "failed to open %s\n", output); 2521 progresult = XMLLINT_ERR_OUT; 2522 } 2523 } 2524 } else { 2525 xmlSaveCtxtPtr ctxt; 2526 int saveOpts = 0; 2527 2528 if (format) 2529 saveOpts |= XML_SAVE_FORMAT; 2530 2531 if (output == NULL) 2532 ctxt = xmlSaveToFd(1, encoding, saveOpts); 2533 else 2534 ctxt = xmlSaveToFilename(output, encoding, saveOpts); 2535 2536 if (ctxt != NULL) { 2537 if (xmlSaveDoc(ctxt, doc) < 0) { 2538 fprintf(stderr, "failed save to %s\n", 2539 output ? output : "-"); 2540 progresult = XMLLINT_ERR_OUT; 2541 } 2542 xmlSaveClose(ctxt); 2543 } else { 2544 progresult = XMLLINT_ERR_OUT; 2545 } 2546 } 2547 if ((timing) && (!repeat)) { 2548 endTimer("Saving"); 2549 } 2550 #ifdef LIBXML_DEBUG_ENABLED 2551 } else { 2552 FILE *out; 2553 if (output == NULL) 2554 out = stdout; 2555 else { 2556 out = fopen(output,"wb"); 2557 } 2558 if (out != NULL) { 2559 xmlDebugDumpDocument(out, doc); 2560 2561 if (output != NULL) 2562 fclose(out); 2563 } else { 2564 fprintf(stderr, "failed to open %s\n", output); 2565 progresult = XMLLINT_ERR_OUT; 2566 } 2567 } 2568 #endif 2569 } 2570 #endif /* LIBXML_OUTPUT_ENABLED */ 2571 2572 #ifdef LIBXML_VALID_ENABLED 2573 /* 2574 * A posteriori validation test 2575 */ 2576 if ((dtdvalid != NULL) || (dtdvalidfpi != NULL)) { 2577 xmlDtdPtr dtd; 2578 2579 if ((timing) && (!repeat)) { 2580 startTimer(); 2581 } 2582 if (dtdvalid != NULL) 2583 dtd = xmlParseDTD(NULL, (const xmlChar *)dtdvalid); 2584 else 2585 dtd = xmlParseDTD((const xmlChar *)dtdvalidfpi, NULL); 2586 if ((timing) && (!repeat)) { 2587 endTimer("Parsing DTD"); 2588 } 2589 if (dtd == NULL) { 2590 if (dtdvalid != NULL) 2591 xmlGenericError(xmlGenericErrorContext, 2592 "Could not parse DTD %s\n", dtdvalid); 2593 else 2594 xmlGenericError(xmlGenericErrorContext, 2595 "Could not parse DTD %s\n", dtdvalidfpi); 2596 progresult = XMLLINT_ERR_DTD; 2597 } else { 2598 xmlValidCtxtPtr cvp; 2599 2600 if ((cvp = xmlNewValidCtxt()) == NULL) { 2601 xmlGenericError(xmlGenericErrorContext, 2602 "Couldn't allocate validation context\n"); 2603 exit(-1); 2604 } 2605 cvp->userData = (void *) stderr; 2606 cvp->error = (xmlValidityErrorFunc) fprintf; 2607 cvp->warning = (xmlValidityWarningFunc) fprintf; 2608 2609 if ((timing) && (!repeat)) { 2610 startTimer(); 2611 } 2612 if (!xmlValidateDtd(cvp, doc, dtd)) { 2613 if (dtdvalid != NULL) 2614 xmlGenericError(xmlGenericErrorContext, 2615 "Document %s does not validate against %s\n", 2616 filename, dtdvalid); 2617 else 2618 xmlGenericError(xmlGenericErrorContext, 2619 "Document %s does not validate against %s\n", 2620 filename, dtdvalidfpi); 2621 progresult = XMLLINT_ERR_VALID; 2622 } 2623 if ((timing) && (!repeat)) { 2624 endTimer("Validating against DTD"); 2625 } 2626 xmlFreeValidCtxt(cvp); 2627 xmlFreeDtd(dtd); 2628 } 2629 } else if (postvalid) { 2630 xmlValidCtxtPtr cvp; 2631 2632 if ((cvp = xmlNewValidCtxt()) == NULL) { 2633 xmlGenericError(xmlGenericErrorContext, 2634 "Couldn't allocate validation context\n"); 2635 exit(-1); 2636 } 2637 2638 if ((timing) && (!repeat)) { 2639 startTimer(); 2640 } 2641 cvp->userData = (void *) stderr; 2642 cvp->error = (xmlValidityErrorFunc) fprintf; 2643 cvp->warning = (xmlValidityWarningFunc) fprintf; 2644 if (!xmlValidateDocument(cvp, doc)) { 2645 xmlGenericError(xmlGenericErrorContext, 2646 "Document %s does not validate\n", filename); 2647 progresult = XMLLINT_ERR_VALID; 2648 } 2649 if ((timing) && (!repeat)) { 2650 endTimer("Validating"); 2651 } 2652 xmlFreeValidCtxt(cvp); 2653 } 2654 #endif /* LIBXML_VALID_ENABLED */ 2655 #ifdef LIBXML_SCHEMATRON_ENABLED 2656 if (wxschematron != NULL) { 2657 xmlSchematronValidCtxtPtr ctxt; 2658 int ret; 2659 int flag; 2660 2661 if ((timing) && (!repeat)) { 2662 startTimer(); 2663 } 2664 2665 if (debug) 2666 flag = XML_SCHEMATRON_OUT_XML; 2667 else 2668 flag = XML_SCHEMATRON_OUT_TEXT; 2669 if (noout) 2670 flag |= XML_SCHEMATRON_OUT_QUIET; 2671 ctxt = xmlSchematronNewValidCtxt(wxschematron, flag); 2672 #if 0 2673 xmlSchematronSetValidErrors(ctxt, 2674 (xmlSchematronValidityErrorFunc) fprintf, 2675 (xmlSchematronValidityWarningFunc) fprintf, 2676 stderr); 2677 #endif 2678 ret = xmlSchematronValidateDoc(ctxt, doc); 2679 if (ret == 0) { 2680 fprintf(stderr, "%s validates\n", filename); 2681 } else if (ret > 0) { 2682 fprintf(stderr, "%s fails to validate\n", filename); 2683 progresult = XMLLINT_ERR_VALID; 2684 } else { 2685 fprintf(stderr, "%s validation generated an internal error\n", 2686 filename); 2687 progresult = XMLLINT_ERR_VALID; 2688 } 2689 xmlSchematronFreeValidCtxt(ctxt); 2690 if ((timing) && (!repeat)) { 2691 endTimer("Validating"); 2692 } 2693 } 2694 #endif 2695 #ifdef LIBXML_SCHEMAS_ENABLED 2696 if (relaxngschemas != NULL) { 2697 xmlRelaxNGValidCtxtPtr ctxt; 2698 int ret; 2699 2700 if ((timing) && (!repeat)) { 2701 startTimer(); 2702 } 2703 2704 ctxt = xmlRelaxNGNewValidCtxt(relaxngschemas); 2705 xmlRelaxNGSetValidErrors(ctxt, 2706 (xmlRelaxNGValidityErrorFunc) fprintf, 2707 (xmlRelaxNGValidityWarningFunc) fprintf, 2708 stderr); 2709 ret = xmlRelaxNGValidateDoc(ctxt, doc); 2710 if (ret == 0) { 2711 fprintf(stderr, "%s validates\n", filename); 2712 } else if (ret > 0) { 2713 fprintf(stderr, "%s fails to validate\n", filename); 2714 progresult = XMLLINT_ERR_VALID; 2715 } else { 2716 fprintf(stderr, "%s validation generated an internal error\n", 2717 filename); 2718 progresult = XMLLINT_ERR_VALID; 2719 } 2720 xmlRelaxNGFreeValidCtxt(ctxt); 2721 if ((timing) && (!repeat)) { 2722 endTimer("Validating"); 2723 } 2724 } else if (wxschemas != NULL) { 2725 xmlSchemaValidCtxtPtr ctxt; 2726 int ret; 2727 2728 if ((timing) && (!repeat)) { 2729 startTimer(); 2730 } 2731 2732 ctxt = xmlSchemaNewValidCtxt(wxschemas); 2733 xmlSchemaSetValidErrors(ctxt, 2734 (xmlSchemaValidityErrorFunc) fprintf, 2735 (xmlSchemaValidityWarningFunc) fprintf, 2736 stderr); 2737 ret = xmlSchemaValidateDoc(ctxt, doc); 2738 if (ret == 0) { 2739 fprintf(stderr, "%s validates\n", filename); 2740 } else if (ret > 0) { 2741 fprintf(stderr, "%s fails to validate\n", filename); 2742 progresult = XMLLINT_ERR_VALID; 2743 } else { 2744 fprintf(stderr, "%s validation generated an internal error\n", 2745 filename); 2746 progresult = XMLLINT_ERR_VALID; 2747 } 2748 xmlSchemaFreeValidCtxt(ctxt); 2749 if ((timing) && (!repeat)) { 2750 endTimer("Validating"); 2751 } 2752 } 2753 #endif 2754 2755 #ifdef LIBXML_DEBUG_ENABLED 2756 #if defined(LIBXML_HTML_ENABLED) || defined(LIBXML_VALID_ENABLED) 2757 if ((debugent) && (!html)) 2758 xmlDebugDumpEntities(stderr, doc); 2759 #endif 2760 #endif 2761 2762 /* 2763 * free it. 2764 */ 2765 if ((timing) && (!repeat)) { 2766 startTimer(); 2767 } 2768 xmlFreeDoc(doc); 2769 if ((timing) && (!repeat)) { 2770 endTimer("Freeing"); 2771 } 2772 } 2773 2774 /************************************************************************ 2775 * * 2776 * Usage and Main * 2777 * * 2778 ************************************************************************/ 2779 2780 static void showVersion(const char *name) { 2781 fprintf(stderr, "%s: using libxml version %s\n", name, xmlParserVersion); 2782 fprintf(stderr, " compiled with: "); 2783 if (xmlHasFeature(XML_WITH_THREAD)) fprintf(stderr, "Threads "); 2784 if (xmlHasFeature(XML_WITH_TREE)) fprintf(stderr, "Tree "); 2785 if (xmlHasFeature(XML_WITH_OUTPUT)) fprintf(stderr, "Output "); 2786 if (xmlHasFeature(XML_WITH_PUSH)) fprintf(stderr, "Push "); 2787 if (xmlHasFeature(XML_WITH_READER)) fprintf(stderr, "Reader "); 2788 if (xmlHasFeature(XML_WITH_PATTERN)) fprintf(stderr, "Patterns "); 2789 if (xmlHasFeature(XML_WITH_WRITER)) fprintf(stderr, "Writer "); 2790 if (xmlHasFeature(XML_WITH_SAX1)) fprintf(stderr, "SAXv1 "); 2791 if (xmlHasFeature(XML_WITH_FTP)) fprintf(stderr, "FTP "); 2792 if (xmlHasFeature(XML_WITH_HTTP)) fprintf(stderr, "HTTP "); 2793 if (xmlHasFeature(XML_WITH_VALID)) fprintf(stderr, "DTDValid "); 2794 if (xmlHasFeature(XML_WITH_HTML)) fprintf(stderr, "HTML "); 2795 if (xmlHasFeature(XML_WITH_LEGACY)) fprintf(stderr, "Legacy "); 2796 if (xmlHasFeature(XML_WITH_C14N)) fprintf(stderr, "C14N "); 2797 if (xmlHasFeature(XML_WITH_CATALOG)) fprintf(stderr, "Catalog "); 2798 if (xmlHasFeature(XML_WITH_XPATH)) fprintf(stderr, "XPath "); 2799 if (xmlHasFeature(XML_WITH_XPTR)) fprintf(stderr, "XPointer "); 2800 if (xmlHasFeature(XML_WITH_XINCLUDE)) fprintf(stderr, "XInclude "); 2801 if (xmlHasFeature(XML_WITH_ICONV)) fprintf(stderr, "Iconv "); 2802 if (xmlHasFeature(XML_WITH_ISO8859X)) fprintf(stderr, "ISO8859X "); 2803 if (xmlHasFeature(XML_WITH_UNICODE)) fprintf(stderr, "Unicode "); 2804 if (xmlHasFeature(XML_WITH_REGEXP)) fprintf(stderr, "Regexps "); 2805 if (xmlHasFeature(XML_WITH_AUTOMATA)) fprintf(stderr, "Automata "); 2806 if (xmlHasFeature(XML_WITH_EXPR)) fprintf(stderr, "Expr "); 2807 if (xmlHasFeature(XML_WITH_SCHEMAS)) fprintf(stderr, "Schemas "); 2808 if (xmlHasFeature(XML_WITH_SCHEMATRON)) fprintf(stderr, "Schematron "); 2809 if (xmlHasFeature(XML_WITH_MODULES)) fprintf(stderr, "Modules "); 2810 if (xmlHasFeature(XML_WITH_DEBUG)) fprintf(stderr, "Debug "); 2811 if (xmlHasFeature(XML_WITH_DEBUG_MEM)) fprintf(stderr, "MemDebug "); 2812 if (xmlHasFeature(XML_WITH_DEBUG_RUN)) fprintf(stderr, "RunDebug "); 2813 if (xmlHasFeature(XML_WITH_ZLIB)) fprintf(stderr, "Zlib "); 2814 fprintf(stderr, "\n"); 2815 } 2816 2817 static void usage(const char *name) { 2818 printf("Usage : %s [options] XMLfiles ...\n", name); 2819 #ifdef LIBXML_OUTPUT_ENABLED 2820 printf("\tParse the XML files and output the result of the parsing\n"); 2821 #else 2822 printf("\tParse the XML files\n"); 2823 #endif /* LIBXML_OUTPUT_ENABLED */ 2824 printf("\t--version : display the version of the XML library used\n"); 2825 #ifdef LIBXML_DEBUG_ENABLED 2826 printf("\t--debug : dump a debug tree of the in-memory document\n"); 2827 printf("\t--shell : run a navigating shell\n"); 2828 printf("\t--debugent : debug the entities defined in the document\n"); 2829 #else 2830 #ifdef LIBXML_READER_ENABLED 2831 printf("\t--debug : dump the nodes content when using --stream\n"); 2832 #endif /* LIBXML_READER_ENABLED */ 2833 #endif 2834 #ifdef LIBXML_TREE_ENABLED 2835 printf("\t--copy : used to test the internal copy implementation\n"); 2836 #endif /* LIBXML_TREE_ENABLED */ 2837 printf("\t--recover : output what was parsable on broken XML documents\n"); 2838 printf("\t--huge : remove any internal arbitrary parser limits\n"); 2839 printf("\t--noent : substitute entity references by their value\n"); 2840 printf("\t--noout : don't output the result tree\n"); 2841 printf("\t--path 'paths': provide a set of paths for resources\n"); 2842 printf("\t--load-trace : print trace of all external entites loaded\n"); 2843 printf("\t--nonet : refuse to fetch DTDs or entities over network\n"); 2844 printf("\t--nocompact : do not generate compact text nodes\n"); 2845 printf("\t--htmlout : output results as HTML\n"); 2846 printf("\t--nowrap : do not put HTML doc wrapper\n"); 2847 #ifdef LIBXML_VALID_ENABLED 2848 printf("\t--valid : validate the document in addition to std well-formed check\n"); 2849 printf("\t--postvalid : do a posteriori validation, i.e after parsing\n"); 2850 printf("\t--dtdvalid URL : do a posteriori validation against a given DTD\n"); 2851 printf("\t--dtdvalidfpi FPI : same but name the DTD with a Public Identifier\n"); 2852 #endif /* LIBXML_VALID_ENABLED */ 2853 printf("\t--timing : print some timings\n"); 2854 printf("\t--output file or -o file: save to a given file\n"); 2855 printf("\t--repeat : repeat 100 times, for timing or profiling\n"); 2856 printf("\t--insert : ad-hoc test for valid insertions\n"); 2857 #ifdef LIBXML_OUTPUT_ENABLED 2858 #ifdef HAVE_ZLIB_H 2859 printf("\t--compress : turn on gzip compression of output\n"); 2860 #endif 2861 #endif /* LIBXML_OUTPUT_ENABLED */ 2862 #ifdef LIBXML_HTML_ENABLED 2863 printf("\t--html : use the HTML parser\n"); 2864 printf("\t--xmlout : force to use the XML serializer when using --html\n"); 2865 #endif 2866 #ifdef LIBXML_PUSH_ENABLED 2867 printf("\t--push : use the push mode of the parser\n"); 2868 #endif /* LIBXML_PUSH_ENABLED */ 2869 #ifdef HAVE_SYS_MMAN_H 2870 printf("\t--memory : parse from memory\n"); 2871 #endif 2872 printf("\t--maxmem nbbytes : limits memory allocation to nbbytes bytes\n"); 2873 printf("\t--nowarning : do not emit warnings from parser/validator\n"); 2874 printf("\t--noblanks : drop (ignorable?) blanks spaces\n"); 2875 printf("\t--nocdata : replace cdata section with text nodes\n"); 2876 #ifdef LIBXML_OUTPUT_ENABLED 2877 printf("\t--format : reformat/reindent the input\n"); 2878 printf("\t--encode encoding : output in the given encoding\n"); 2879 printf("\t--dropdtd : remove the DOCTYPE of the input docs\n"); 2880 #endif /* LIBXML_OUTPUT_ENABLED */ 2881 printf("\t--c14n : save in W3C canonical format (with comments)\n"); 2882 printf("\t--exc-c14n : save in W3C exclusive canonical format (with comments)\n"); 2883 #ifdef LIBXML_C14N_ENABLED 2884 #endif /* LIBXML_C14N_ENABLED */ 2885 printf("\t--nsclean : remove redundant namespace declarations\n"); 2886 printf("\t--testIO : test user I/O support\n"); 2887 #ifdef LIBXML_CATALOG_ENABLED 2888 printf("\t--catalogs : use SGML catalogs from $SGML_CATALOG_FILES\n"); 2889 printf("\t otherwise XML Catalogs starting from \n"); 2890 printf("\t %s are activated by default\n", XML_XML_DEFAULT_CATALOG); 2891 printf("\t--nocatalogs: deactivate all catalogs\n"); 2892 #endif 2893 printf("\t--auto : generate a small doc on the fly\n"); 2894 #ifdef LIBXML_XINCLUDE_ENABLED 2895 printf("\t--xinclude : do XInclude processing\n"); 2896 printf("\t--noxincludenode : same but do not generate XInclude nodes\n"); 2897 printf("\t--nofixup-base-uris : do not fixup xml:base uris\n"); 2898 #endif 2899 printf("\t--loaddtd : fetch external DTD\n"); 2900 printf("\t--dtdattr : loaddtd + populate the tree with inherited attributes \n"); 2901 #ifdef LIBXML_READER_ENABLED 2902 printf("\t--stream : use the streaming interface to process very large files\n"); 2903 printf("\t--walker : create a reader and walk though the resulting doc\n"); 2904 #endif /* LIBXML_READER_ENABLED */ 2905 #ifdef LIBXML_PATTERN_ENABLED 2906 printf("\t--pattern pattern_value : test the pattern support\n"); 2907 #endif 2908 printf("\t--chkregister : verify the node registration code\n"); 2909 #ifdef LIBXML_SCHEMAS_ENABLED 2910 printf("\t--relaxng schema : do RelaxNG validation against the schema\n"); 2911 printf("\t--schema schema : do validation against the WXS schema\n"); 2912 #endif 2913 #ifdef LIBXML_SCHEMATRON_ENABLED 2914 printf("\t--schematron schema : do validation against a schematron\n"); 2915 #endif 2916 #ifdef LIBXML_SAX1_ENABLED 2917 printf("\t--sax1: use the old SAX1 interfaces for processing\n"); 2918 #endif 2919 printf("\t--sax: do not build a tree but work just at the SAX level\n"); 2920 printf("\t--oldxml10: use XML-1.0 parsing rules before the 5th edition\n"); 2921 2922 printf("\nLibxml project home page: http://xmlsoft.org/\n"); 2923 printf("To report bugs or get some help check: http://xmlsoft.org/bugs.html\n"); 2924 } 2925 2926 static void registerNode(xmlNodePtr node) 2927 { 2928 node->_private = malloc(sizeof(long)); 2929 *(long*)node->_private = (long) 0x81726354; 2930 nbregister++; 2931 } 2932 2933 static void deregisterNode(xmlNodePtr node) 2934 { 2935 assert(node->_private != NULL); 2936 assert(*(long*)node->_private == (long) 0x81726354); 2937 free(node->_private); 2938 nbregister--; 2939 } 2940 2941 int 2942 main(int argc, char **argv) { 2943 int i, acount; 2944 int files = 0; 2945 int version = 0; 2946 const char* indent; 2947 2948 if (argc <= 1) { 2949 usage(argv[0]); 2950 return(1); 2951 } 2952 LIBXML_TEST_VERSION 2953 for (i = 1; i < argc ; i++) { 2954 if (!strcmp(argv[i], "-")) 2955 break; 2956 2957 if (argv[i][0] != '-') 2958 continue; 2959 if ((!strcmp(argv[i], "-debug")) || (!strcmp(argv[i], "--debug"))) 2960 debug++; 2961 else 2962 #ifdef LIBXML_DEBUG_ENABLED 2963 if ((!strcmp(argv[i], "-shell")) || 2964 (!strcmp(argv[i], "--shell"))) { 2965 shell++; 2966 noout = 1; 2967 } else 2968 #endif 2969 #ifdef LIBXML_TREE_ENABLED 2970 if ((!strcmp(argv[i], "-copy")) || (!strcmp(argv[i], "--copy"))) 2971 copy++; 2972 else 2973 #endif /* LIBXML_TREE_ENABLED */ 2974 if ((!strcmp(argv[i], "-recover")) || 2975 (!strcmp(argv[i], "--recover"))) { 2976 recovery++; 2977 options |= XML_PARSE_RECOVER; 2978 } else if ((!strcmp(argv[i], "-huge")) || 2979 (!strcmp(argv[i], "--huge"))) { 2980 options |= XML_PARSE_HUGE; 2981 } else if ((!strcmp(argv[i], "-noent")) || 2982 (!strcmp(argv[i], "--noent"))) { 2983 noent++; 2984 options |= XML_PARSE_NOENT; 2985 } else if ((!strcmp(argv[i], "-nsclean")) || 2986 (!strcmp(argv[i], "--nsclean"))) { 2987 options |= XML_PARSE_NSCLEAN; 2988 } else if ((!strcmp(argv[i], "-nocdata")) || 2989 (!strcmp(argv[i], "--nocdata"))) { 2990 options |= XML_PARSE_NOCDATA; 2991 } else if ((!strcmp(argv[i], "-nodict")) || 2992 (!strcmp(argv[i], "--nodict"))) { 2993 options |= XML_PARSE_NODICT; 2994 } else if ((!strcmp(argv[i], "-version")) || 2995 (!strcmp(argv[i], "--version"))) { 2996 showVersion(argv[0]); 2997 version = 1; 2998 } else if ((!strcmp(argv[i], "-noout")) || 2999 (!strcmp(argv[i], "--noout"))) 3000 noout++; 3001 #ifdef LIBXML_OUTPUT_ENABLED 3002 else if ((!strcmp(argv[i], "-o")) || 3003 (!strcmp(argv[i], "-output")) || 3004 (!strcmp(argv[i], "--output"))) { 3005 i++; 3006 output = argv[i]; 3007 } 3008 #endif /* LIBXML_OUTPUT_ENABLED */ 3009 else if ((!strcmp(argv[i], "-htmlout")) || 3010 (!strcmp(argv[i], "--htmlout"))) 3011 htmlout++; 3012 else if ((!strcmp(argv[i], "-nowrap")) || 3013 (!strcmp(argv[i], "--nowrap"))) 3014 nowrap++; 3015 #ifdef LIBXML_HTML_ENABLED 3016 else if ((!strcmp(argv[i], "-html")) || 3017 (!strcmp(argv[i], "--html"))) { 3018 html++; 3019 } 3020 else if ((!strcmp(argv[i], "-xmlout")) || 3021 (!strcmp(argv[i], "--xmlout"))) { 3022 xmlout++; 3023 } 3024 #endif /* LIBXML_HTML_ENABLED */ 3025 else if ((!strcmp(argv[i], "-loaddtd")) || 3026 (!strcmp(argv[i], "--loaddtd"))) { 3027 loaddtd++; 3028 options |= XML_PARSE_DTDLOAD; 3029 } else if ((!strcmp(argv[i], "-dtdattr")) || 3030 (!strcmp(argv[i], "--dtdattr"))) { 3031 loaddtd++; 3032 dtdattrs++; 3033 options |= XML_PARSE_DTDATTR; 3034 } 3035 #ifdef LIBXML_VALID_ENABLED 3036 else if ((!strcmp(argv[i], "-valid")) || 3037 (!strcmp(argv[i], "--valid"))) { 3038 valid++; 3039 options |= XML_PARSE_DTDVALID; 3040 } else if ((!strcmp(argv[i], "-postvalid")) || 3041 (!strcmp(argv[i], "--postvalid"))) { 3042 postvalid++; 3043 loaddtd++; 3044 options |= XML_PARSE_DTDLOAD; 3045 } else if ((!strcmp(argv[i], "-dtdvalid")) || 3046 (!strcmp(argv[i], "--dtdvalid"))) { 3047 i++; 3048 dtdvalid = argv[i]; 3049 loaddtd++; 3050 options |= XML_PARSE_DTDLOAD; 3051 } else if ((!strcmp(argv[i], "-dtdvalidfpi")) || 3052 (!strcmp(argv[i], "--dtdvalidfpi"))) { 3053 i++; 3054 dtdvalidfpi = argv[i]; 3055 loaddtd++; 3056 options |= XML_PARSE_DTDLOAD; 3057 } 3058 #endif /* LIBXML_VALID_ENABLED */ 3059 else if ((!strcmp(argv[i], "-dropdtd")) || 3060 (!strcmp(argv[i], "--dropdtd"))) 3061 dropdtd++; 3062 else if ((!strcmp(argv[i], "-insert")) || 3063 (!strcmp(argv[i], "--insert"))) 3064 insert++; 3065 else if ((!strcmp(argv[i], "-timing")) || 3066 (!strcmp(argv[i], "--timing"))) 3067 timing++; 3068 else if ((!strcmp(argv[i], "-auto")) || 3069 (!strcmp(argv[i], "--auto"))) 3070 generate++; 3071 else if ((!strcmp(argv[i], "-repeat")) || 3072 (!strcmp(argv[i], "--repeat"))) { 3073 if (repeat) 3074 repeat *= 10; 3075 else 3076 repeat = 100; 3077 } 3078 #ifdef LIBXML_PUSH_ENABLED 3079 else if ((!strcmp(argv[i], "-push")) || 3080 (!strcmp(argv[i], "--push"))) 3081 push++; 3082 #endif /* LIBXML_PUSH_ENABLED */ 3083 #ifdef HAVE_SYS_MMAN_H 3084 else if ((!strcmp(argv[i], "-memory")) || 3085 (!strcmp(argv[i], "--memory"))) 3086 memory++; 3087 #endif 3088 else if ((!strcmp(argv[i], "-testIO")) || 3089 (!strcmp(argv[i], "--testIO"))) 3090 testIO++; 3091 #ifdef LIBXML_XINCLUDE_ENABLED 3092 else if ((!strcmp(argv[i], "-xinclude")) || 3093 (!strcmp(argv[i], "--xinclude"))) { 3094 xinclude++; 3095 options |= XML_PARSE_XINCLUDE; 3096 } 3097 else if ((!strcmp(argv[i], "-noxincludenode")) || 3098 (!strcmp(argv[i], "--noxincludenode"))) { 3099 xinclude++; 3100 options |= XML_PARSE_XINCLUDE; 3101 options |= XML_PARSE_NOXINCNODE; 3102 } 3103 else if ((!strcmp(argv[i], "-nofixup-base-uris")) || 3104 (!strcmp(argv[i], "--nofixup-base-uris"))) { 3105 xinclude++; 3106 options |= XML_PARSE_XINCLUDE; 3107 options |= XML_PARSE_NOBASEFIX; 3108 } 3109 #endif 3110 #ifdef LIBXML_OUTPUT_ENABLED 3111 #ifdef HAVE_ZLIB_H 3112 else if ((!strcmp(argv[i], "-compress")) || 3113 (!strcmp(argv[i], "--compress"))) { 3114 compress++; 3115 xmlSetCompressMode(9); 3116 } 3117 #endif 3118 #endif /* LIBXML_OUTPUT_ENABLED */ 3119 else if ((!strcmp(argv[i], "-nowarning")) || 3120 (!strcmp(argv[i], "--nowarning"))) { 3121 xmlGetWarningsDefaultValue = 0; 3122 xmlPedanticParserDefault(0); 3123 options |= XML_PARSE_NOWARNING; 3124 } 3125 else if ((!strcmp(argv[i], "-pedantic")) || 3126 (!strcmp(argv[i], "--pedantic"))) { 3127 xmlGetWarningsDefaultValue = 1; 3128 xmlPedanticParserDefault(1); 3129 options |= XML_PARSE_PEDANTIC; 3130 } 3131 #ifdef LIBXML_DEBUG_ENABLED 3132 else if ((!strcmp(argv[i], "-debugent")) || 3133 (!strcmp(argv[i], "--debugent"))) { 3134 debugent++; 3135 xmlParserDebugEntities = 1; 3136 } 3137 #endif 3138 #ifdef LIBXML_C14N_ENABLED 3139 else if ((!strcmp(argv[i], "-c14n")) || 3140 (!strcmp(argv[i], "--c14n"))) { 3141 canonical++; 3142 options |= XML_PARSE_NOENT | XML_PARSE_DTDATTR | XML_PARSE_DTDLOAD; 3143 } 3144 else if ((!strcmp(argv[i], "-exc-c14n")) || 3145 (!strcmp(argv[i], "--exc-c14n"))) { 3146 exc_canonical++; 3147 options |= XML_PARSE_NOENT | XML_PARSE_DTDATTR | XML_PARSE_DTDLOAD; 3148 } 3149 #endif 3150 #ifdef LIBXML_CATALOG_ENABLED 3151 else if ((!strcmp(argv[i], "-catalogs")) || 3152 (!strcmp(argv[i], "--catalogs"))) { 3153 catalogs++; 3154 } else if ((!strcmp(argv[i], "-nocatalogs")) || 3155 (!strcmp(argv[i], "--nocatalogs"))) { 3156 nocatalogs++; 3157 } 3158 #endif 3159 else if ((!strcmp(argv[i], "-encode")) || 3160 (!strcmp(argv[i], "--encode"))) { 3161 i++; 3162 encoding = argv[i]; 3163 /* 3164 * OK it's for testing purposes 3165 */ 3166 xmlAddEncodingAlias("UTF-8", "DVEnc"); 3167 } 3168 else if ((!strcmp(argv[i], "-noblanks")) || 3169 (!strcmp(argv[i], "--noblanks"))) { 3170 noblanks++; 3171 xmlKeepBlanksDefault(0); 3172 } 3173 else if ((!strcmp(argv[i], "-maxmem")) || 3174 (!strcmp(argv[i], "--maxmem"))) { 3175 i++; 3176 if (sscanf(argv[i], "%d", &maxmem) == 1) { 3177 xmlMemSetup(myFreeFunc, myMallocFunc, myReallocFunc, 3178 myStrdupFunc); 3179 } else { 3180 maxmem = 0; 3181 } 3182 } 3183 else if ((!strcmp(argv[i], "-format")) || 3184 (!strcmp(argv[i], "--format"))) { 3185 noblanks++; 3186 #ifdef LIBXML_OUTPUT_ENABLED 3187 format++; 3188 #endif /* LIBXML_OUTPUT_ENABLED */ 3189 xmlKeepBlanksDefault(0); 3190 } 3191 #ifdef LIBXML_READER_ENABLED 3192 else if ((!strcmp(argv[i], "-stream")) || 3193 (!strcmp(argv[i], "--stream"))) { 3194 stream++; 3195 } 3196 else if ((!strcmp(argv[i], "-walker")) || 3197 (!strcmp(argv[i], "--walker"))) { 3198 walker++; 3199 noout++; 3200 } 3201 #endif /* LIBXML_READER_ENABLED */ 3202 #ifdef LIBXML_SAX1_ENABLED 3203 else if ((!strcmp(argv[i], "-sax1")) || 3204 (!strcmp(argv[i], "--sax1"))) { 3205 sax1++; 3206 } 3207 #endif /* LIBXML_SAX1_ENABLED */ 3208 else if ((!strcmp(argv[i], "-sax")) || 3209 (!strcmp(argv[i], "--sax"))) { 3210 sax++; 3211 } 3212 else if ((!strcmp(argv[i], "-chkregister")) || 3213 (!strcmp(argv[i], "--chkregister"))) { 3214 chkregister++; 3215 #ifdef LIBXML_SCHEMAS_ENABLED 3216 } else if ((!strcmp(argv[i], "-relaxng")) || 3217 (!strcmp(argv[i], "--relaxng"))) { 3218 i++; 3219 relaxng = argv[i]; 3220 noent++; 3221 options |= XML_PARSE_NOENT; 3222 } else if ((!strcmp(argv[i], "-schema")) || 3223 (!strcmp(argv[i], "--schema"))) { 3224 i++; 3225 schema = argv[i]; 3226 noent++; 3227 #endif 3228 #ifdef LIBXML_SCHEMATRON_ENABLED 3229 } else if ((!strcmp(argv[i], "-schematron")) || 3230 (!strcmp(argv[i], "--schematron"))) { 3231 i++; 3232 schematron = argv[i]; 3233 noent++; 3234 #endif 3235 } else if ((!strcmp(argv[i], "-nonet")) || 3236 (!strcmp(argv[i], "--nonet"))) { 3237 options |= XML_PARSE_NONET; 3238 xmlSetExternalEntityLoader(xmlNoNetExternalEntityLoader); 3239 } else if ((!strcmp(argv[i], "-nocompact")) || 3240 (!strcmp(argv[i], "--nocompact"))) { 3241 options &= ~XML_PARSE_COMPACT; 3242 } else if ((!strcmp(argv[i], "-load-trace")) || 3243 (!strcmp(argv[i], "--load-trace"))) { 3244 load_trace++; 3245 } else if ((!strcmp(argv[i], "-path")) || 3246 (!strcmp(argv[i], "--path"))) { 3247 i++; 3248 parsePath(BAD_CAST argv[i]); 3249 #ifdef LIBXML_PATTERN_ENABLED 3250 } else if ((!strcmp(argv[i], "-pattern")) || 3251 (!strcmp(argv[i], "--pattern"))) { 3252 i++; 3253 pattern = argv[i]; 3254 #endif 3255 } else if ((!strcmp(argv[i], "-oldxml10")) || 3256 (!strcmp(argv[i], "--oldxml10"))) { 3257 oldxml10++; 3258 options |= XML_PARSE_OLD10; 3259 } else { 3260 fprintf(stderr, "Unknown option %s\n", argv[i]); 3261 usage(argv[0]); 3262 return(1); 3263 } 3264 } 3265 3266 #ifdef LIBXML_CATALOG_ENABLED 3267 if (nocatalogs == 0) { 3268 if (catalogs) { 3269 const char *catal; 3270 3271 catal = getenv("SGML_CATALOG_FILES"); 3272 if (catal != NULL) { 3273 xmlLoadCatalogs(catal); 3274 } else { 3275 fprintf(stderr, "Variable $SGML_CATALOG_FILES not set\n"); 3276 } 3277 } 3278 } 3279 #endif 3280 3281 #ifdef LIBXML_SAX1_ENABLED 3282 if (sax1) 3283 xmlSAXDefaultVersion(1); 3284 else 3285 xmlSAXDefaultVersion(2); 3286 #endif /* LIBXML_SAX1_ENABLED */ 3287 3288 if (chkregister) { 3289 xmlRegisterNodeDefault(registerNode); 3290 xmlDeregisterNodeDefault(deregisterNode); 3291 } 3292 3293 indent = getenv("XMLLINT_INDENT"); 3294 if(indent != NULL) { 3295 xmlTreeIndentString = indent; 3296 } 3297 3298 3299 defaultEntityLoader = xmlGetExternalEntityLoader(); 3300 xmlSetExternalEntityLoader(xmllintExternalEntityLoader); 3301 3302 xmlLineNumbersDefault(1); 3303 if (loaddtd != 0) 3304 xmlLoadExtDtdDefaultValue |= XML_DETECT_IDS; 3305 if (dtdattrs) 3306 xmlLoadExtDtdDefaultValue |= XML_COMPLETE_ATTRS; 3307 if (noent != 0) xmlSubstituteEntitiesDefault(1); 3308 #ifdef LIBXML_VALID_ENABLED 3309 if (valid != 0) xmlDoValidityCheckingDefaultValue = 1; 3310 #endif /* LIBXML_VALID_ENABLED */ 3311 if ((htmlout) && (!nowrap)) { 3312 xmlGenericError(xmlGenericErrorContext, 3313 "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.0 Transitional//EN\"\n"); 3314 xmlGenericError(xmlGenericErrorContext, 3315 "\t\"http://www.w3.org/TR/REC-html40/loose.dtd\">\n"); 3316 xmlGenericError(xmlGenericErrorContext, 3317 "<html><head><title>%s output</title></head>\n", 3318 argv[0]); 3319 xmlGenericError(xmlGenericErrorContext, 3320 "<body bgcolor=\"#ffffff\"><h1 align=\"center\">%s output</h1>\n", 3321 argv[0]); 3322 } 3323 3324 #ifdef LIBXML_SCHEMATRON_ENABLED 3325 if ((schematron != NULL) && (sax == 0) 3326 #ifdef LIBXML_READER_ENABLED 3327 && (stream == 0) 3328 #endif /* LIBXML_READER_ENABLED */ 3329 ) { 3330 xmlSchematronParserCtxtPtr ctxt; 3331 3332 /* forces loading the DTDs */ 3333 xmlLoadExtDtdDefaultValue |= 1; 3334 options |= XML_PARSE_DTDLOAD; 3335 if (timing) { 3336 startTimer(); 3337 } 3338 ctxt = xmlSchematronNewParserCtxt(schematron); 3339 #if 0 3340 xmlSchematronSetParserErrors(ctxt, 3341 (xmlSchematronValidityErrorFunc) fprintf, 3342 (xmlSchematronValidityWarningFunc) fprintf, 3343 stderr); 3344 #endif 3345 wxschematron = xmlSchematronParse(ctxt); 3346 if (wxschematron == NULL) { 3347 xmlGenericError(xmlGenericErrorContext, 3348 "Schematron schema %s failed to compile\n", schematron); 3349 progresult = XMLLINT_ERR_SCHEMACOMP; 3350 schematron = NULL; 3351 } 3352 xmlSchematronFreeParserCtxt(ctxt); 3353 if (timing) { 3354 endTimer("Compiling the schemas"); 3355 } 3356 } 3357 #endif 3358 #ifdef LIBXML_SCHEMAS_ENABLED 3359 if ((relaxng != NULL) && (sax == 0) 3360 #ifdef LIBXML_READER_ENABLED 3361 && (stream == 0) 3362 #endif /* LIBXML_READER_ENABLED */ 3363 ) { 3364 xmlRelaxNGParserCtxtPtr ctxt; 3365 3366 /* forces loading the DTDs */ 3367 xmlLoadExtDtdDefaultValue |= 1; 3368 options |= XML_PARSE_DTDLOAD; 3369 if (timing) { 3370 startTimer(); 3371 } 3372 ctxt = xmlRelaxNGNewParserCtxt(relaxng); 3373 xmlRelaxNGSetParserErrors(ctxt, 3374 (xmlRelaxNGValidityErrorFunc) fprintf, 3375 (xmlRelaxNGValidityWarningFunc) fprintf, 3376 stderr); 3377 relaxngschemas = xmlRelaxNGParse(ctxt); 3378 if (relaxngschemas == NULL) { 3379 xmlGenericError(xmlGenericErrorContext, 3380 "Relax-NG schema %s failed to compile\n", relaxng); 3381 progresult = XMLLINT_ERR_SCHEMACOMP; 3382 relaxng = NULL; 3383 } 3384 xmlRelaxNGFreeParserCtxt(ctxt); 3385 if (timing) { 3386 endTimer("Compiling the schemas"); 3387 } 3388 } else if ((schema != NULL) 3389 #ifdef LIBXML_READER_ENABLED 3390 && (stream == 0) 3391 #endif 3392 ) { 3393 xmlSchemaParserCtxtPtr ctxt; 3394 3395 if (timing) { 3396 startTimer(); 3397 } 3398 ctxt = xmlSchemaNewParserCtxt(schema); 3399 xmlSchemaSetParserErrors(ctxt, 3400 (xmlSchemaValidityErrorFunc) fprintf, 3401 (xmlSchemaValidityWarningFunc) fprintf, 3402 stderr); 3403 wxschemas = xmlSchemaParse(ctxt); 3404 if (wxschemas == NULL) { 3405 xmlGenericError(xmlGenericErrorContext, 3406 "WXS schema %s failed to compile\n", schema); 3407 progresult = XMLLINT_ERR_SCHEMACOMP; 3408 schema = NULL; 3409 } 3410 xmlSchemaFreeParserCtxt(ctxt); 3411 if (timing) { 3412 endTimer("Compiling the schemas"); 3413 } 3414 } 3415 #endif /* LIBXML_SCHEMAS_ENABLED */ 3416 #ifdef LIBXML_PATTERN_ENABLED 3417 if ((pattern != NULL) 3418 #ifdef LIBXML_READER_ENABLED 3419 && (walker == 0) 3420 #endif 3421 ) { 3422 patternc = xmlPatterncompile((const xmlChar *) pattern, NULL, 0, NULL); 3423 if (patternc == NULL) { 3424 xmlGenericError(xmlGenericErrorContext, 3425 "Pattern %s failed to compile\n", pattern); 3426 progresult = XMLLINT_ERR_SCHEMAPAT; 3427 pattern = NULL; 3428 } 3429 } 3430 #endif /* LIBXML_PATTERN_ENABLED */ 3431 for (i = 1; i < argc ; i++) { 3432 if ((!strcmp(argv[i], "-encode")) || 3433 (!strcmp(argv[i], "--encode"))) { 3434 i++; 3435 continue; 3436 } else if ((!strcmp(argv[i], "-o")) || 3437 (!strcmp(argv[i], "-output")) || 3438 (!strcmp(argv[i], "--output"))) { 3439 i++; 3440 continue; 3441 } 3442 #ifdef LIBXML_VALID_ENABLED 3443 if ((!strcmp(argv[i], "-dtdvalid")) || 3444 (!strcmp(argv[i], "--dtdvalid"))) { 3445 i++; 3446 continue; 3447 } 3448 if ((!strcmp(argv[i], "-path")) || 3449 (!strcmp(argv[i], "--path"))) { 3450 i++; 3451 continue; 3452 } 3453 if ((!strcmp(argv[i], "-dtdvalidfpi")) || 3454 (!strcmp(argv[i], "--dtdvalidfpi"))) { 3455 i++; 3456 continue; 3457 } 3458 #endif /* LIBXML_VALID_ENABLED */ 3459 if ((!strcmp(argv[i], "-relaxng")) || 3460 (!strcmp(argv[i], "--relaxng"))) { 3461 i++; 3462 continue; 3463 } 3464 if ((!strcmp(argv[i], "-maxmem")) || 3465 (!strcmp(argv[i], "--maxmem"))) { 3466 i++; 3467 continue; 3468 } 3469 if ((!strcmp(argv[i], "-schema")) || 3470 (!strcmp(argv[i], "--schema"))) { 3471 i++; 3472 continue; 3473 } 3474 if ((!strcmp(argv[i], "-schematron")) || 3475 (!strcmp(argv[i], "--schematron"))) { 3476 i++; 3477 continue; 3478 } 3479 #ifdef LIBXML_PATTERN_ENABLED 3480 if ((!strcmp(argv[i], "-pattern")) || 3481 (!strcmp(argv[i], "--pattern"))) { 3482 i++; 3483 continue; 3484 } 3485 #endif 3486 if ((timing) && (repeat)) 3487 startTimer(); 3488 /* Remember file names. "-" means stdin. <sven (at) zen.org> */ 3489 if ((argv[i][0] != '-') || (strcmp(argv[i], "-") == 0)) { 3490 if (repeat) { 3491 xmlParserCtxtPtr ctxt = NULL; 3492 3493 for (acount = 0;acount < repeat;acount++) { 3494 #ifdef LIBXML_READER_ENABLED 3495 if (stream != 0) { 3496 streamFile(argv[i]); 3497 } else { 3498 #endif /* LIBXML_READER_ENABLED */ 3499 if (sax) { 3500 testSAX(argv[i]); 3501 } else { 3502 if (ctxt == NULL) 3503 ctxt = xmlNewParserCtxt(); 3504 parseAndPrintFile(argv[i], ctxt); 3505 } 3506 #ifdef LIBXML_READER_ENABLED 3507 } 3508 #endif /* LIBXML_READER_ENABLED */ 3509 } 3510 if (ctxt != NULL) 3511 xmlFreeParserCtxt(ctxt); 3512 } else { 3513 nbregister = 0; 3514 3515 #ifdef LIBXML_READER_ENABLED 3516 if (stream != 0) 3517 streamFile(argv[i]); 3518 else 3519 #endif /* LIBXML_READER_ENABLED */ 3520 if (sax) { 3521 testSAX(argv[i]); 3522 } else { 3523 parseAndPrintFile(argv[i], NULL); 3524 } 3525 3526 if ((chkregister) && (nbregister != 0)) { 3527 fprintf(stderr, "Registration count off: %d\n", nbregister); 3528 progresult = XMLLINT_ERR_RDREGIS; 3529 } 3530 } 3531 files ++; 3532 if ((timing) && (repeat)) { 3533 endTimer("%d iterations", repeat); 3534 } 3535 } 3536 } 3537 if (generate) 3538 parseAndPrintFile(NULL, NULL); 3539 if ((htmlout) && (!nowrap)) { 3540 xmlGenericError(xmlGenericErrorContext, "</body></html>\n"); 3541 } 3542 if ((files == 0) && (!generate) && (version == 0)) { 3543 usage(argv[0]); 3544 } 3545 #ifdef LIBXML_SCHEMATRON_ENABLED 3546 if (wxschematron != NULL) 3547 xmlSchematronFree(wxschematron); 3548 #endif 3549 #ifdef LIBXML_SCHEMAS_ENABLED 3550 if (relaxngschemas != NULL) 3551 xmlRelaxNGFree(relaxngschemas); 3552 if (wxschemas != NULL) 3553 xmlSchemaFree(wxschemas); 3554 xmlRelaxNGCleanupTypes(); 3555 #endif 3556 #ifdef LIBXML_PATTERN_ENABLED 3557 if (patternc != NULL) 3558 xmlFreePattern(patternc); 3559 #endif 3560 xmlCleanupParser(); 3561 xmlMemoryDump(); 3562 3563 return(progresult); 3564 } 3565 3566