File:  [ELWIX - Embedded LightWeight unIX -] / embedaddon / expat / xmlwf / xmlwf.c
Revision 1.1.1.2 (vendor branch): download - view: text, annotated - select for diffs - revision graph
Sun Jun 15 16:09:43 2014 UTC (10 years, 4 months ago) by misho
Branches: expat, MAIN
CVS tags: v2_1_0, HEAD
expat 2.1.0

    1: /* Copyright (c) 1998, 1999 Thai Open Source Software Center Ltd
    2:    See the file COPYING for copying permission.
    3: */
    4: 
    5: #include <stdio.h>
    6: #include <stdlib.h>
    7: #include <stddef.h>
    8: #include <string.h>
    9: 
   10: #include "expat.h"
   11: #include "codepage.h"
   12: #include "xmlfile.h"
   13: #include "xmltchar.h"
   14: 
   15: #ifdef _MSC_VER
   16: #include <crtdbg.h>
   17: #endif
   18: 
   19: #if defined(__amigaos__) && defined(__USE_INLINE__)
   20: #include <proto/expat.h>
   21: #endif
   22: 
   23: /* This ensures proper sorting. */
   24: 
   25: #define NSSEP T('\001')
   26: 
   27: static void XMLCALL
   28: characterData(void *userData, const XML_Char *s, int len)
   29: {
   30:   FILE *fp = (FILE *)userData;
   31:   for (; len > 0; --len, ++s) {
   32:     switch (*s) {
   33:     case T('&'):
   34:       fputts(T("&amp;"), fp);
   35:       break;
   36:     case T('<'):
   37:       fputts(T("&lt;"), fp);
   38:       break;
   39:     case T('>'):
   40:       fputts(T("&gt;"), fp);
   41:       break;
   42: #ifdef W3C14N
   43:     case 13:
   44:       fputts(T("&#xD;"), fp);
   45:       break;
   46: #else
   47:     case T('"'):
   48:       fputts(T("&quot;"), fp);
   49:       break;
   50:     case 9:
   51:     case 10:
   52:     case 13:
   53:       ftprintf(fp, T("&#%d;"), *s);
   54:       break;
   55: #endif
   56:     default:
   57:       puttc(*s, fp);
   58:       break;
   59:     }
   60:   }
   61: }
   62: 
   63: static void
   64: attributeValue(FILE *fp, const XML_Char *s)
   65: {
   66:   puttc(T('='), fp);
   67:   puttc(T('"'), fp);
   68:   for (;;) {
   69:     switch (*s) {
   70:     case 0:
   71:     case NSSEP:
   72:       puttc(T('"'), fp);
   73:       return;
   74:     case T('&'):
   75:       fputts(T("&amp;"), fp);
   76:       break;
   77:     case T('<'):
   78:       fputts(T("&lt;"), fp);
   79:       break;
   80:     case T('"'):
   81:       fputts(T("&quot;"), fp);
   82:       break;
   83: #ifdef W3C14N
   84:     case 9:
   85:       fputts(T("&#x9;"), fp);
   86:       break;
   87:     case 10:
   88:       fputts(T("&#xA;"), fp);
   89:       break;
   90:     case 13:
   91:       fputts(T("&#xD;"), fp);
   92:       break;
   93: #else
   94:     case T('>'):
   95:       fputts(T("&gt;"), fp);
   96:       break;
   97:     case 9:
   98:     case 10:
   99:     case 13:
  100:       ftprintf(fp, T("&#%d;"), *s);
  101:       break;
  102: #endif
  103:     default:
  104:       puttc(*s, fp);
  105:       break;
  106:     }
  107:     s++;
  108:   }
  109: }
  110: 
  111: /* Lexicographically comparing UTF-8 encoded attribute values,
  112: is equivalent to lexicographically comparing based on the character number. */
  113: 
  114: static int
  115: attcmp(const void *att1, const void *att2)
  116: {
  117:   return tcscmp(*(const XML_Char **)att1, *(const XML_Char **)att2);
  118: }
  119: 
  120: static void XMLCALL
  121: startElement(void *userData, const XML_Char *name, const XML_Char **atts)
  122: {
  123:   int nAtts;
  124:   const XML_Char **p;
  125:   FILE *fp = (FILE *)userData;
  126:   puttc(T('<'), fp);
  127:   fputts(name, fp);
  128: 
  129:   p = atts;
  130:   while (*p)
  131:     ++p;
  132:   nAtts = (int)((p - atts) >> 1);
  133:   if (nAtts > 1)
  134:     qsort((void *)atts, nAtts, sizeof(XML_Char *) * 2, attcmp);
  135:   while (*atts) {
  136:     puttc(T(' '), fp);
  137:     fputts(*atts++, fp);
  138:     attributeValue(fp, *atts);
  139:     atts++;
  140:   }
  141:   puttc(T('>'), fp);
  142: }
  143: 
  144: static void XMLCALL
  145: endElement(void *userData, const XML_Char *name)
  146: {
  147:   FILE *fp = (FILE *)userData;
  148:   puttc(T('<'), fp);
  149:   puttc(T('/'), fp);
  150:   fputts(name, fp);
  151:   puttc(T('>'), fp);
  152: }
  153: 
  154: static int
  155: nsattcmp(const void *p1, const void *p2)
  156: {
  157:   const XML_Char *att1 = *(const XML_Char **)p1;
  158:   const XML_Char *att2 = *(const XML_Char **)p2;
  159:   int sep1 = (tcsrchr(att1, NSSEP) != 0);
  160:   int sep2 = (tcsrchr(att1, NSSEP) != 0);
  161:   if (sep1 != sep2)
  162:     return sep1 - sep2;
  163:   return tcscmp(att1, att2);
  164: }
  165: 
  166: static void XMLCALL
  167: startElementNS(void *userData, const XML_Char *name, const XML_Char **atts)
  168: {
  169:   int nAtts;
  170:   int nsi;
  171:   const XML_Char **p;
  172:   FILE *fp = (FILE *)userData;
  173:   const XML_Char *sep;
  174:   puttc(T('<'), fp);
  175: 
  176:   sep = tcsrchr(name, NSSEP);
  177:   if (sep) {
  178:     fputts(T("n1:"), fp);
  179:     fputts(sep + 1, fp);
  180:     fputts(T(" xmlns:n1"), fp);
  181:     attributeValue(fp, name);
  182:     nsi = 2;
  183:   }
  184:   else {
  185:     fputts(name, fp);
  186:     nsi = 1;
  187:   }
  188: 
  189:   p = atts;
  190:   while (*p)
  191:     ++p;
  192:   nAtts = (int)((p - atts) >> 1);
  193:   if (nAtts > 1)
  194:     qsort((void *)atts, nAtts, sizeof(XML_Char *) * 2, nsattcmp);
  195:   while (*atts) {
  196:     name = *atts++;
  197:     sep = tcsrchr(name, NSSEP);
  198:     puttc(T(' '), fp);
  199:     if (sep) {
  200:       ftprintf(fp, T("n%d:"), nsi);
  201:       fputts(sep + 1, fp);
  202:     }
  203:     else
  204:       fputts(name, fp);
  205:     attributeValue(fp, *atts);
  206:     if (sep) {
  207:       ftprintf(fp, T(" xmlns:n%d"), nsi++);
  208:       attributeValue(fp, name);
  209:     }
  210:     atts++;
  211:   }
  212:   puttc(T('>'), fp);
  213: }
  214: 
  215: static void XMLCALL
  216: endElementNS(void *userData, const XML_Char *name)
  217: {
  218:   FILE *fp = (FILE *)userData;
  219:   const XML_Char *sep;
  220:   puttc(T('<'), fp);
  221:   puttc(T('/'), fp);
  222:   sep = tcsrchr(name, NSSEP);
  223:   if (sep) {
  224:     fputts(T("n1:"), fp);
  225:     fputts(sep + 1, fp);
  226:   }
  227:   else
  228:     fputts(name, fp);
  229:   puttc(T('>'), fp);
  230: }
  231: 
  232: #ifndef W3C14N
  233: 
  234: static void XMLCALL
  235: processingInstruction(void *userData, const XML_Char *target,
  236:                       const XML_Char *data)
  237: {
  238:   FILE *fp = (FILE *)userData;
  239:   puttc(T('<'), fp);
  240:   puttc(T('?'), fp);
  241:   fputts(target, fp);
  242:   puttc(T(' '), fp);
  243:   fputts(data, fp);
  244:   puttc(T('?'), fp);
  245:   puttc(T('>'), fp);
  246: }
  247: 
  248: #endif /* not W3C14N */
  249: 
  250: static void XMLCALL
  251: defaultCharacterData(void *userData, const XML_Char *s, int len)
  252: {
  253:   XML_DefaultCurrent((XML_Parser) userData);
  254: }
  255: 
  256: static void XMLCALL
  257: defaultStartElement(void *userData, const XML_Char *name,
  258:                     const XML_Char **atts)
  259: {
  260:   XML_DefaultCurrent((XML_Parser) userData);
  261: }
  262: 
  263: static void XMLCALL
  264: defaultEndElement(void *userData, const XML_Char *name)
  265: {
  266:   XML_DefaultCurrent((XML_Parser) userData);
  267: }
  268: 
  269: static void XMLCALL
  270: defaultProcessingInstruction(void *userData, const XML_Char *target,
  271:                              const XML_Char *data)
  272: {
  273:   XML_DefaultCurrent((XML_Parser) userData);
  274: }
  275: 
  276: static void XMLCALL
  277: nopCharacterData(void *userData, const XML_Char *s, int len)
  278: {
  279: }
  280: 
  281: static void XMLCALL
  282: nopStartElement(void *userData, const XML_Char *name, const XML_Char **atts)
  283: {
  284: }
  285: 
  286: static void XMLCALL
  287: nopEndElement(void *userData, const XML_Char *name)
  288: {
  289: }
  290: 
  291: static void XMLCALL
  292: nopProcessingInstruction(void *userData, const XML_Char *target,
  293:                          const XML_Char *data)
  294: {
  295: }
  296: 
  297: static void XMLCALL
  298: markup(void *userData, const XML_Char *s, int len)
  299: {
  300:   FILE *fp = (FILE *)XML_GetUserData((XML_Parser) userData);
  301:   for (; len > 0; --len, ++s)
  302:     puttc(*s, fp);
  303: }
  304: 
  305: static void
  306: metaLocation(XML_Parser parser)
  307: {
  308:   const XML_Char *uri = XML_GetBase(parser);
  309:   if (uri)
  310:     ftprintf((FILE *)XML_GetUserData(parser), T(" uri=\"%s\""), uri);
  311:   ftprintf((FILE *)XML_GetUserData(parser),
  312:            T(" byte=\"%" XML_FMT_INT_MOD "d\" nbytes=\"%d\" \
  313: 			 line=\"%" XML_FMT_INT_MOD "u\" col=\"%" XML_FMT_INT_MOD "u\""),
  314:            XML_GetCurrentByteIndex(parser),
  315:            XML_GetCurrentByteCount(parser),
  316:            XML_GetCurrentLineNumber(parser),
  317:            XML_GetCurrentColumnNumber(parser));
  318: }
  319: 
  320: static void
  321: metaStartDocument(void *userData)
  322: {
  323:   fputts(T("<document>\n"), (FILE *)XML_GetUserData((XML_Parser) userData));
  324: }
  325: 
  326: static void
  327: metaEndDocument(void *userData)
  328: {
  329:   fputts(T("</document>\n"), (FILE *)XML_GetUserData((XML_Parser) userData));
  330: }
  331: 
  332: static void XMLCALL
  333: metaStartElement(void *userData, const XML_Char *name,
  334:                  const XML_Char **atts)
  335: {
  336:   XML_Parser parser = (XML_Parser) userData;
  337:   FILE *fp = (FILE *)XML_GetUserData(parser);
  338:   const XML_Char **specifiedAttsEnd
  339:     = atts + XML_GetSpecifiedAttributeCount(parser);
  340:   const XML_Char **idAttPtr;
  341:   int idAttIndex = XML_GetIdAttributeIndex(parser);
  342:   if (idAttIndex < 0)
  343:     idAttPtr = 0;
  344:   else
  345:     idAttPtr = atts + idAttIndex;
  346:     
  347:   ftprintf(fp, T("<starttag name=\"%s\""), name);
  348:   metaLocation(parser);
  349:   if (*atts) {
  350:     fputts(T(">\n"), fp);
  351:     do {
  352:       ftprintf(fp, T("<attribute name=\"%s\" value=\""), atts[0]);
  353:       characterData(fp, atts[1], (int)tcslen(atts[1]));
  354:       if (atts >= specifiedAttsEnd)
  355:         fputts(T("\" defaulted=\"yes\"/>\n"), fp);
  356:       else if (atts == idAttPtr)
  357:         fputts(T("\" id=\"yes\"/>\n"), fp);
  358:       else
  359:         fputts(T("\"/>\n"), fp);
  360:     } while (*(atts += 2));
  361:     fputts(T("</starttag>\n"), fp);
  362:   }
  363:   else
  364:     fputts(T("/>\n"), fp);
  365: }
  366: 
  367: static void XMLCALL
  368: metaEndElement(void *userData, const XML_Char *name)
  369: {
  370:   XML_Parser parser = (XML_Parser) userData;
  371:   FILE *fp = (FILE *)XML_GetUserData(parser);
  372:   ftprintf(fp, T("<endtag name=\"%s\""), name);
  373:   metaLocation(parser);
  374:   fputts(T("/>\n"), fp);
  375: }
  376: 
  377: static void XMLCALL
  378: metaProcessingInstruction(void *userData, const XML_Char *target,
  379:                           const XML_Char *data)
  380: {
  381:   XML_Parser parser = (XML_Parser) userData;
  382:   FILE *fp = (FILE *)XML_GetUserData(parser);
  383:   ftprintf(fp, T("<pi target=\"%s\" data=\""), target);
  384:   characterData(fp, data, (int)tcslen(data));
  385:   puttc(T('"'), fp);
  386:   metaLocation(parser);
  387:   fputts(T("/>\n"), fp);
  388: }
  389: 
  390: static void XMLCALL
  391: metaComment(void *userData, const XML_Char *data)
  392: {
  393:   XML_Parser parser = (XML_Parser) userData;
  394:   FILE *fp = (FILE *)XML_GetUserData(parser);
  395:   fputts(T("<comment data=\""), fp);
  396:   characterData(fp, data, (int)tcslen(data));
  397:   puttc(T('"'), fp);
  398:   metaLocation(parser);
  399:   fputts(T("/>\n"), fp);
  400: }
  401: 
  402: static void XMLCALL
  403: metaStartCdataSection(void *userData)
  404: {
  405:   XML_Parser parser = (XML_Parser) userData;
  406:   FILE *fp = (FILE *)XML_GetUserData(parser);
  407:   fputts(T("<startcdata"), fp);
  408:   metaLocation(parser);
  409:   fputts(T("/>\n"), fp);
  410: }
  411: 
  412: static void XMLCALL
  413: metaEndCdataSection(void *userData)
  414: {
  415:   XML_Parser parser = (XML_Parser) userData;
  416:   FILE *fp = (FILE *)XML_GetUserData(parser);
  417:   fputts(T("<endcdata"), fp);
  418:   metaLocation(parser);
  419:   fputts(T("/>\n"), fp);
  420: }
  421: 
  422: static void XMLCALL
  423: metaCharacterData(void *userData, const XML_Char *s, int len)
  424: {
  425:   XML_Parser parser = (XML_Parser) userData;
  426:   FILE *fp = (FILE *)XML_GetUserData(parser);
  427:   fputts(T("<chars str=\""), fp);
  428:   characterData(fp, s, len);
  429:   puttc(T('"'), fp);
  430:   metaLocation(parser);
  431:   fputts(T("/>\n"), fp);
  432: }
  433: 
  434: static void XMLCALL
  435: metaStartDoctypeDecl(void *userData,
  436:                      const XML_Char *doctypeName,
  437:                      const XML_Char *sysid,
  438:                      const XML_Char *pubid,
  439:                      int has_internal_subset)
  440: {
  441:   XML_Parser parser = (XML_Parser) userData;
  442:   FILE *fp = (FILE *)XML_GetUserData(parser);
  443:   ftprintf(fp, T("<startdoctype name=\"%s\""), doctypeName);
  444:   metaLocation(parser);
  445:   fputts(T("/>\n"), fp);
  446: }
  447: 
  448: static void XMLCALL
  449: metaEndDoctypeDecl(void *userData)
  450: {
  451:   XML_Parser parser = (XML_Parser) userData;
  452:   FILE *fp = (FILE *)XML_GetUserData(parser);
  453:   fputts(T("<enddoctype"), fp);
  454:   metaLocation(parser);
  455:   fputts(T("/>\n"), fp);
  456: }
  457: 
  458: static void XMLCALL
  459: metaNotationDecl(void *userData,
  460:                  const XML_Char *notationName,
  461:                  const XML_Char *base,
  462:                  const XML_Char *systemId,
  463:                  const XML_Char *publicId)
  464: {
  465:   XML_Parser parser = (XML_Parser) userData;
  466:   FILE *fp = (FILE *)XML_GetUserData(parser);
  467:   ftprintf(fp, T("<notation name=\"%s\""), notationName);
  468:   if (publicId)
  469:     ftprintf(fp, T(" public=\"%s\""), publicId);
  470:   if (systemId) {
  471:     fputts(T(" system=\""), fp);
  472:     characterData(fp, systemId, (int)tcslen(systemId));
  473:     puttc(T('"'), fp);
  474:   }
  475:   metaLocation(parser);
  476:   fputts(T("/>\n"), fp);
  477: }
  478: 
  479: 
  480: static void XMLCALL
  481: metaEntityDecl(void *userData,
  482:                const XML_Char *entityName,
  483:                int  is_param,
  484:                const XML_Char *value,
  485:                int  value_length,
  486:                const XML_Char *base,
  487:                const XML_Char *systemId,
  488:                const XML_Char *publicId,
  489:                const XML_Char *notationName)
  490: {
  491:   XML_Parser parser = (XML_Parser) userData;
  492:   FILE *fp = (FILE *)XML_GetUserData(parser);
  493: 
  494:   if (value) {
  495:     ftprintf(fp, T("<entity name=\"%s\""), entityName);
  496:     metaLocation(parser);
  497:     puttc(T('>'), fp);
  498:     characterData(fp, value, value_length);
  499:     fputts(T("</entity/>\n"), fp);
  500:   }
  501:   else if (notationName) {
  502:     ftprintf(fp, T("<entity name=\"%s\""), entityName);
  503:     if (publicId)
  504:       ftprintf(fp, T(" public=\"%s\""), publicId);
  505:     fputts(T(" system=\""), fp);
  506:     characterData(fp, systemId, (int)tcslen(systemId));
  507:     puttc(T('"'), fp);
  508:     ftprintf(fp, T(" notation=\"%s\""), notationName);
  509:     metaLocation(parser);
  510:     fputts(T("/>\n"), fp);
  511:   }
  512:   else {
  513:     ftprintf(fp, T("<entity name=\"%s\""), entityName);
  514:     if (publicId)
  515:       ftprintf(fp, T(" public=\"%s\""), publicId);
  516:     fputts(T(" system=\""), fp);
  517:     characterData(fp, systemId, (int)tcslen(systemId));
  518:     puttc(T('"'), fp);
  519:     metaLocation(parser);
  520:     fputts(T("/>\n"), fp);
  521:   }
  522: }
  523: 
  524: static void XMLCALL
  525: metaStartNamespaceDecl(void *userData,
  526:                        const XML_Char *prefix,
  527:                        const XML_Char *uri)
  528: {
  529:   XML_Parser parser = (XML_Parser) userData;
  530:   FILE *fp = (FILE *)XML_GetUserData(parser);
  531:   fputts(T("<startns"), fp);
  532:   if (prefix)
  533:     ftprintf(fp, T(" prefix=\"%s\""), prefix);
  534:   if (uri) {
  535:     fputts(T(" ns=\""), fp);
  536:     characterData(fp, uri, (int)tcslen(uri));
  537:     fputts(T("\"/>\n"), fp);
  538:   }
  539:   else
  540:     fputts(T("/>\n"), fp);
  541: }
  542: 
  543: static void XMLCALL
  544: metaEndNamespaceDecl(void *userData, const XML_Char *prefix)
  545: {
  546:   XML_Parser parser = (XML_Parser) userData;
  547:   FILE *fp = (FILE *)XML_GetUserData(parser);
  548:   if (!prefix)
  549:     fputts(T("<endns/>\n"), fp);
  550:   else
  551:     ftprintf(fp, T("<endns prefix=\"%s\"/>\n"), prefix);
  552: }
  553: 
  554: static int XMLCALL
  555: unknownEncodingConvert(void *data, const char *p)
  556: {
  557:   return codepageConvert(*(int *)data, p);
  558: }
  559: 
  560: static int XMLCALL
  561: unknownEncoding(void *userData, const XML_Char *name, XML_Encoding *info)
  562: {
  563:   int cp;
  564:   static const XML_Char prefixL[] = T("windows-");
  565:   static const XML_Char prefixU[] = T("WINDOWS-");
  566:   int i;
  567: 
  568:   for (i = 0; prefixU[i]; i++)
  569:     if (name[i] != prefixU[i] && name[i] != prefixL[i])
  570:       return 0;
  571:   
  572:   cp = 0;
  573:   for (; name[i]; i++) {
  574:     static const XML_Char digits[] = T("0123456789");
  575:     const XML_Char *s = tcschr(digits, name[i]);
  576:     if (!s)
  577:       return 0;
  578:     cp *= 10;
  579:     cp += (int)(s - digits);
  580:     if (cp >= 0x10000)
  581:       return 0;
  582:   }
  583:   if (!codepageMap(cp, info->map))
  584:     return 0;
  585:   info->convert = unknownEncodingConvert;
  586:   /* We could just cast the code page integer to a void *,
  587:   and avoid the use of release. */
  588:   info->release = free;
  589:   info->data = malloc(sizeof(int));
  590:   if (!info->data)
  591:     return 0;
  592:   *(int *)info->data = cp;
  593:   return 1;
  594: }
  595: 
  596: static int XMLCALL
  597: notStandalone(void *userData)
  598: {
  599:   return 0;
  600: }
  601: 
  602: static void
  603: showVersion(XML_Char *prog)
  604: {
  605:   XML_Char *s = prog;
  606:   XML_Char ch;
  607:   const XML_Feature *features = XML_GetFeatureList();
  608:   while ((ch = *s) != 0) {
  609:     if (ch == '/'
  610: #if (defined(WIN32) || defined(__WATCOMC__))
  611:         || ch == '\\'
  612: #endif
  613:         )
  614:       prog = s + 1;
  615:     ++s;
  616:   }
  617:   ftprintf(stdout, T("%s using %s\n"), prog, XML_ExpatVersion());
  618:   if (features != NULL && features[0].feature != XML_FEATURE_END) {
  619:     int i = 1;
  620:     ftprintf(stdout, T("%s"), features[0].name);
  621:     if (features[0].value)
  622:       ftprintf(stdout, T("=%ld"), features[0].value);
  623:     while (features[i].feature != XML_FEATURE_END) {
  624:       ftprintf(stdout, T(", %s"), features[i].name);
  625:       if (features[i].value)
  626:         ftprintf(stdout, T("=%ld"), features[i].value);
  627:       ++i;
  628:     }
  629:     ftprintf(stdout, T("\n"));
  630:   }
  631: }
  632: 
  633: static void
  634: usage(const XML_Char *prog, int rc)
  635: {
  636:   ftprintf(stderr,
  637:            T("usage: %s [-n] [-p] [-r] [-s] [-w] [-x] [-d output-dir] "
  638:              "[-e encoding] file ...\n"), prog);
  639:   exit(rc);
  640: }
  641: 
  642: int
  643: tmain(int argc, XML_Char **argv)
  644: {
  645:   int i, j;
  646:   const XML_Char *outputDir = NULL;
  647:   const XML_Char *encoding = NULL;
  648:   unsigned processFlags = XML_MAP_FILE;
  649:   int windowsCodePages = 0;
  650:   int outputType = 0;
  651:   int useNamespaces = 0;
  652:   int requireStandalone = 0;
  653:   enum XML_ParamEntityParsing paramEntityParsing = 
  654:     XML_PARAM_ENTITY_PARSING_NEVER;
  655:   int useStdin = 0;
  656: 
  657: #ifdef _MSC_VER
  658:   _CrtSetDbgFlag(_CRTDBG_ALLOC_MEM_DF|_CRTDBG_LEAK_CHECK_DF);
  659: #endif
  660: 
  661:   i = 1;
  662:   j = 0;
  663:   while (i < argc) {
  664:     if (j == 0) {
  665:       if (argv[i][0] != T('-'))
  666:         break;
  667:       if (argv[i][1] == T('-') && argv[i][2] == T('\0')) {
  668:         i++;
  669:         break;
  670:       }
  671:       j++;
  672:     }
  673:     switch (argv[i][j]) {
  674:     case T('r'):
  675:       processFlags &= ~XML_MAP_FILE;
  676:       j++;
  677:       break;
  678:     case T('s'):
  679:       requireStandalone = 1;
  680:       j++;
  681:       break;
  682:     case T('n'):
  683:       useNamespaces = 1;
  684:       j++;
  685:       break;
  686:     case T('p'):
  687:       paramEntityParsing = XML_PARAM_ENTITY_PARSING_ALWAYS;
  688:       /* fall through */
  689:     case T('x'):
  690:       processFlags |= XML_EXTERNAL_ENTITIES;
  691:       j++;
  692:       break;
  693:     case T('w'):
  694:       windowsCodePages = 1;
  695:       j++;
  696:       break;
  697:     case T('m'):
  698:       outputType = 'm';
  699:       j++;
  700:       break;
  701:     case T('c'):
  702:       outputType = 'c';
  703:       useNamespaces = 0;
  704:       j++;
  705:       break;
  706:     case T('t'):
  707:       outputType = 't';
  708:       j++;
  709:       break;
  710:     case T('d'):
  711:       if (argv[i][j + 1] == T('\0')) {
  712:         if (++i == argc)
  713:           usage(argv[0], 2);
  714:         outputDir = argv[i];
  715:       }
  716:       else
  717:         outputDir = argv[i] + j + 1;
  718:       i++;
  719:       j = 0;
  720:       break;
  721:     case T('e'):
  722:       if (argv[i][j + 1] == T('\0')) {
  723:         if (++i == argc)
  724:           usage(argv[0], 2);
  725:         encoding = argv[i];
  726:       }
  727:       else
  728:         encoding = argv[i] + j + 1;
  729:       i++;
  730:       j = 0;
  731:       break;
  732:     case T('h'):
  733:       usage(argv[0], 0);
  734:       return 0;
  735:     case T('v'):
  736:       showVersion(argv[0]);
  737:       return 0;
  738:     case T('\0'):
  739:       if (j > 1) {
  740:         i++;
  741:         j = 0;
  742:         break;
  743:       }
  744:       /* fall through */
  745:     default:
  746:       usage(argv[0], 2);
  747:     }
  748:   }
  749:   if (i == argc) {
  750:     useStdin = 1;
  751:     processFlags &= ~XML_MAP_FILE;
  752:     i--;
  753:   }
  754:   for (; i < argc; i++) {
  755:     FILE *fp = 0;
  756:     XML_Char *outName = 0;
  757:     int result;
  758:     XML_Parser parser;
  759:     if (useNamespaces)
  760:       parser = XML_ParserCreateNS(encoding, NSSEP);
  761:     else
  762:       parser = XML_ParserCreate(encoding);
  763:     if (requireStandalone)
  764:       XML_SetNotStandaloneHandler(parser, notStandalone);
  765:     XML_SetParamEntityParsing(parser, paramEntityParsing);
  766:     if (outputType == 't') {
  767:       /* This is for doing timings; this gives a more realistic estimate of
  768:          the parsing time. */
  769:       outputDir = 0;
  770:       XML_SetElementHandler(parser, nopStartElement, nopEndElement);
  771:       XML_SetCharacterDataHandler(parser, nopCharacterData);
  772:       XML_SetProcessingInstructionHandler(parser, nopProcessingInstruction);
  773:     }
  774:     else if (outputDir) {
  775:       const XML_Char * delim = T("/");
  776:       const XML_Char *file = useStdin ? T("STDIN") : argv[i];
  777:       if (!useStdin) {
  778:         /* Jump after last (back)slash */
  779:         const XML_Char * lastDelim = tcsrchr(file, delim[0]);
  780:         if (lastDelim)
  781:           file = lastDelim + 1;
  782: #if (defined(WIN32) || defined(__WATCOMC__))
  783:         else {
  784:           const XML_Char * winDelim = T("\\");
  785:           lastDelim = tcsrchr(file, winDelim[0]);
  786:           if (lastDelim) {
  787:             file = lastDelim + 1;
  788:             delim = winDelim;
  789:           }
  790:         }
  791: #endif
  792:       }
  793:       outName = (XML_Char *)malloc((tcslen(outputDir) + tcslen(file) + 2)
  794:                        * sizeof(XML_Char));
  795:       tcscpy(outName, outputDir);
  796:       tcscat(outName, delim);
  797:       tcscat(outName, file);
  798:       fp = tfopen(outName, T("wb"));
  799:       if (!fp) {
  800:         tperror(outName);
  801:         exit(1);
  802:       }
  803:       setvbuf(fp, NULL, _IOFBF, 16384);
  804: #ifdef XML_UNICODE
  805:       puttc(0xFEFF, fp);
  806: #endif
  807:       XML_SetUserData(parser, fp);
  808:       switch (outputType) {
  809:       case 'm':
  810:         XML_UseParserAsHandlerArg(parser);
  811:         XML_SetElementHandler(parser, metaStartElement, metaEndElement);
  812:         XML_SetProcessingInstructionHandler(parser, metaProcessingInstruction);
  813:         XML_SetCommentHandler(parser, metaComment);
  814:         XML_SetCdataSectionHandler(parser, metaStartCdataSection,
  815:                                    metaEndCdataSection);
  816:         XML_SetCharacterDataHandler(parser, metaCharacterData);
  817:         XML_SetDoctypeDeclHandler(parser, metaStartDoctypeDecl,
  818:                                   metaEndDoctypeDecl);
  819:         XML_SetEntityDeclHandler(parser, metaEntityDecl);
  820:         XML_SetNotationDeclHandler(parser, metaNotationDecl);
  821:         XML_SetNamespaceDeclHandler(parser, metaStartNamespaceDecl,
  822:                                     metaEndNamespaceDecl);
  823:         metaStartDocument(parser);
  824:         break;
  825:       case 'c':
  826:         XML_UseParserAsHandlerArg(parser);
  827:         XML_SetDefaultHandler(parser, markup);
  828:         XML_SetElementHandler(parser, defaultStartElement, defaultEndElement);
  829:         XML_SetCharacterDataHandler(parser, defaultCharacterData);
  830:         XML_SetProcessingInstructionHandler(parser,
  831:                                             defaultProcessingInstruction);
  832:         break;
  833:       default:
  834:         if (useNamespaces)
  835:           XML_SetElementHandler(parser, startElementNS, endElementNS);
  836:         else
  837:           XML_SetElementHandler(parser, startElement, endElement);
  838:         XML_SetCharacterDataHandler(parser, characterData);
  839: #ifndef W3C14N
  840:         XML_SetProcessingInstructionHandler(parser, processingInstruction);
  841: #endif /* not W3C14N */
  842:         break;
  843:       }
  844:     }
  845:     if (windowsCodePages)
  846:       XML_SetUnknownEncodingHandler(parser, unknownEncoding, 0);
  847:     result = XML_ProcessFile(parser, useStdin ? NULL : argv[i], processFlags);
  848:     if (outputDir) {
  849:       if (outputType == 'm')
  850:         metaEndDocument(parser);
  851:       fclose(fp);
  852:       if (!result) {
  853:         tremove(outName);
  854:         exit(2);
  855:       }
  856:       free(outName);
  857:     }
  858:     XML_ParserFree(parser);
  859:   }
  860:   return 0;
  861: }

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>