| 1 57 58 package com.sun.org.apache.xerces.internal.impl.xs.traversers; 59 60 import java.io.IOException ; 61 import java.util.Hashtable ; 62 import java.util.Stack ; 63 import java.util.Vector ; 64 65 import javax.xml.transform.Source ; 66 import javax.xml.transform.Transformer ; 67 import javax.xml.transform.TransformerException ; 68 import javax.xml.transform.TransformerFactory ; 69 import javax.xml.transform.dom.DOMSource ; 70 import javax.xml.transform.sax.SAXSource ; 71 import javax.xml.transform.sax.SAXResult ; 72 import javax.xml.transform.stream.StreamSource ; 73 74 import com.sun.org.apache.xerces.internal.impl.Constants; 75 import com.sun.org.apache.xerces.internal.impl.XMLEntityManager; 76 import com.sun.org.apache.xerces.internal.impl.XMLErrorReporter; 77 import com.sun.org.apache.xerces.internal.impl.xs.SchemaGrammar; 78 import com.sun.org.apache.xerces.internal.impl.xs.SchemaNamespaceSupport; 79 import com.sun.org.apache.xerces.internal.impl.xs.SchemaSymbols; 80 import com.sun.org.apache.xerces.internal.impl.xs.XMLSchemaException; 81 import com.sun.org.apache.xerces.internal.impl.xs.XMLSchemaLoader; 82 import com.sun.org.apache.xerces.internal.impl.xs.XSComplexTypeDecl; 83 import com.sun.org.apache.xerces.internal.impl.xs.XSDDescription; 84 import com.sun.org.apache.xerces.internal.impl.xs.XSDeclarationPool; 85 import com.sun.org.apache.xerces.internal.impl.xs.XSElementDecl; 86 import com.sun.org.apache.xerces.internal.impl.xs.XSGrammarBucket; 87 import com.sun.org.apache.xerces.internal.impl.xs.XSGroupDecl; 88 import com.sun.org.apache.xerces.internal.impl.xs.XSMessageFormatter; 89 import com.sun.org.apache.xerces.internal.impl.xs.XSModelGroupImpl; 90 import com.sun.org.apache.xerces.internal.impl.xs.XSParticleDecl; 91 import com.sun.org.apache.xerces.internal.impl.xs.opti.ElementImpl; 92 import com.sun.org.apache.xerces.internal.impl.xs.opti.SchemaDOM; 93 import com.sun.org.apache.xerces.internal.impl.xs.opti.SchemaDOMParser; 94 import com.sun.org.apache.xerces.internal.impl.xs.opti.SchemaParsingConfig; 95 import com.sun.org.apache.xerces.internal.impl.xs.util.SimpleLocator; 96 import com.sun.org.apache.xerces.internal.parsers.SAXParser; 97 import com.sun.org.apache.xerces.internal.util.DOMUtil; 98 import com.sun.org.apache.xerces.internal.util.SecurityManager; 99 import com.sun.org.apache.xerces.internal.util.SAX2XNI; 100 import com.sun.org.apache.xerces.internal.util.SymbolTable; 101 import com.sun.org.apache.xerces.internal.util.XMLInputSourceAdaptor; 102 import com.sun.org.apache.xerces.internal.util.XMLSymbols; 103 import com.sun.org.apache.xerces.internal.xni.QName; 104 import com.sun.org.apache.xerces.internal.xni.grammars.XMLGrammarPool; 105 import com.sun.org.apache.xerces.internal.xni.parser.XMLComponentManager; 106 import com.sun.org.apache.xerces.internal.xni.parser.XMLConfigurationException; 107 import com.sun.org.apache.xerces.internal.xni.parser.XMLEntityResolver; 108 import com.sun.org.apache.xerces.internal.xni.parser.XMLErrorHandler; 109 import com.sun.org.apache.xerces.internal.xni.parser.XMLInputSource; 110 import com.sun.org.apache.xerces.internal.xs.XSObject; 111 import org.w3c.dom.Document ; 112 import org.w3c.dom.Element ; 113 import org.w3c.dom.Node ; 114 import org.xml.sax.XMLReader ; 115 import org.xml.sax.SAXException ; 116 117 129 public class XSDHandler { 130 131 132 protected static final String ALLOW_JAVA_ENCODINGS = 133 Constants.XERCES_FEATURE_PREFIX + Constants.ALLOW_JAVA_ENCODINGS_FEATURE; 134 135 136 protected static final String CONTINUE_AFTER_FATAL_ERROR = 137 Constants.XERCES_FEATURE_PREFIX + Constants.CONTINUE_AFTER_FATAL_ERROR_FEATURE; 138 139 140 protected static final String STANDARD_URI_CONFORMANT_FEATURE = 141 Constants.XERCES_FEATURE_PREFIX + Constants.STANDARD_URI_CONFORMANT_FEATURE; 142 143 144 protected static final String DISALLOW_DOCTYPE = 145 Constants.XERCES_FEATURE_PREFIX + Constants.DISALLOW_DOCTYPE_DECL_FEATURE; 146 147 148 protected static final String ERROR_HANDLER = 149 Constants.XERCES_PROPERTY_PREFIX + Constants.ERROR_HANDLER_PROPERTY; 150 151 152 protected static final String JAXP_SCHEMA_SOURCE = 153 Constants.JAXP_PROPERTY_PREFIX + Constants.SCHEMA_SOURCE; 154 155 156 public static final String ENTITY_RESOLVER = 157 Constants.XERCES_PROPERTY_PREFIX + Constants.ENTITY_RESOLVER_PROPERTY; 158 159 private static final String SECURE_PROCESSING = 160 Constants.XERCES_PROPERTY_PREFIX + Constants.SECURITY_MANAGER_PROPERTY; 161 162 163 protected static final String ENTITY_MANAGER = 164 Constants.XERCES_PROPERTY_PREFIX + Constants.ENTITY_MANAGER_PROPERTY; 165 166 167 public static final String ERROR_REPORTER = 168 Constants.XERCES_PROPERTY_PREFIX + Constants.ERROR_REPORTER_PROPERTY; 169 170 171 public static final String XMLGRAMMAR_POOL = 172 Constants.XERCES_PROPERTY_PREFIX + Constants.XMLGRAMMAR_POOL_PROPERTY; 173 174 175 public static final String SYMBOL_TABLE = 176 Constants.XERCES_PROPERTY_PREFIX + Constants.SYMBOL_TABLE_PROPERTY; 177 178 protected static final String SECURITY_MANAGER = 179 Constants.XERCES_PROPERTY_PREFIX + Constants.SECURITY_MANAGER_PROPERTY; 180 181 184 protected static final boolean DEBUG_NODE_POOL = false; 185 186 188 final static int ATTRIBUTE_TYPE = 1; 191 final static int ATTRIBUTEGROUP_TYPE = 2; 192 final static int ELEMENT_TYPE = 3; 193 final static int GROUP_TYPE = 4; 194 final static int IDENTITYCONSTRAINT_TYPE = 5; 195 final static int NOTATION_TYPE = 6; 196 final static int TYPEDECL_TYPE = 7; 197 198 public final static String REDEF_IDENTIFIER = "_fn3dktizrknc9pi"; 201 202 protected Hashtable fNotationRegistry = new Hashtable (); 206 207 protected XSDeclarationPool fDeclPool = null; 208 209 private boolean fAllowJavaEncodings = false; 211 212 private boolean fStrictURI = false; 214 215 220 protected SecurityManager fSecureProcessing = null; 221 222 private Hashtable fUnparsedAttributeRegistry = new Hashtable (); 230 private Hashtable fUnparsedAttributeGroupRegistry = new Hashtable (); 231 private Hashtable fUnparsedElementRegistry = new Hashtable (); 232 private Hashtable fUnparsedGroupRegistry = new Hashtable (); 233 private Hashtable fUnparsedIdentityConstraintRegistry = new Hashtable (); 234 private Hashtable fUnparsedNotationRegistry = new Hashtable (); 235 private Hashtable fUnparsedTypeRegistry = new Hashtable (); 236 private Hashtable fXSDocumentInfoRegistry = new Hashtable (); 243 244 private Hashtable fDependencyMap = new Hashtable (); 248 249 private Hashtable fImportMap = new Hashtable (); 254 private Vector fAllTNSs = new Vector (); 258 private Hashtable fLocationPairs = null; 260 261 private String null2EmptyString(String ns) { 263 return ns == null ? XMLSymbols.EMPTY_STRING : ns; 264 } 265 private String emptyString2Null(String ns) { 266 return ns == XMLSymbols.EMPTY_STRING ? null : ns; 267 } 268 269 private Hashtable fTraversed = new Hashtable (); 275 276 private Hashtable fDoc2SystemId = new Hashtable (); 279 280 private XSDocumentInfo fRoot = null; 282 283 private Hashtable fDoc2XSDocumentMap = new Hashtable (); 287 288 private Hashtable fRedefine2XSDMap = new Hashtable (); 291 292 private Hashtable fRedefine2NSSupport = new Hashtable (); 294 295 private Hashtable fRedefinedRestrictedAttributeGroupRegistry = new Hashtable (); 301 private Hashtable fRedefinedRestrictedGroupRegistry = new Hashtable (); 302 303 private boolean fLastSchemaWasDuplicate; 306 307 private XMLErrorReporter fErrorReporter; 309 private XMLEntityResolver fEntityResolver; 310 311 private XSAttributeChecker fAttributeChecker; 313 314 private SymbolTable fSymbolTable; 316 317 private XSGrammarBucket fGrammarBucket; 319 320 private XSDDescription fSchemaGrammarDescription; 322 323 private XMLGrammarPool fGrammarPool; 325 326 XSDAttributeGroupTraverser fAttributeGroupTraverser; 328 XSDAttributeTraverser fAttributeTraverser; 329 XSDComplexTypeTraverser fComplexTypeTraverser; 330 XSDElementTraverser fElementTraverser; 331 XSDGroupTraverser fGroupTraverser; 332 XSDKeyrefTraverser fKeyrefTraverser; 333 XSDNotationTraverser fNotationTraverser; 334 XSDSimpleTypeTraverser fSimpleTypeTraverser; 335 XSDUniqueOrKeyTraverser fUniqueOrKeyTraverser; 336 XSDWildcardTraverser fWildCardTraverser; 337 338 SchemaParsingConfig fSchemaParser; 340 341 344 private static final int INIT_STACK_SIZE = 30; 346 private static final int INC_STACK_SIZE = 10; 348 private int fLocalElemStackPos = 0; 350 351 private XSParticleDecl[] fParticle = new XSParticleDecl[INIT_STACK_SIZE]; 352 private Element [] fLocalElementDecl = new Element [INIT_STACK_SIZE]; 353 private int[] fAllContext = new int[INIT_STACK_SIZE]; 354 private XSObject[] fParent = new XSObject[INIT_STACK_SIZE]; 355 private String [][] fLocalElemNamespaceContext = new String [INIT_STACK_SIZE][1]; 356 357 360 private static final int INIT_KEYREF_STACK = 2; 362 private static final int INC_KEYREF_STACK_AMOUNT = 2; 364 private int fKeyrefStackPos = 0; 366 367 private Element [] fKeyrefs = new Element [INIT_KEYREF_STACK]; 368 private XSElementDecl [] fKeyrefElems = new XSElementDecl [INIT_KEYREF_STACK]; 369 private String [][] fKeyrefNamespaceContext = new String [INIT_KEYREF_STACK][1]; 370 371 public XSDHandler(){ 373 fSchemaParser = new SchemaParsingConfig(); 374 } 375 376 public XSDHandler (XSGrammarBucket gBucket) { 380 this(); 381 fGrammarBucket = gBucket; 382 383 fSchemaGrammarDescription = new XSDDescription(); 387 } 389 390 391 392 403 public SchemaGrammar parseSchema(Source source, XSDDescription desc, 404 Hashtable locationPairs) 405 throws IOException { 406 fLocationPairs = locationPairs; 407 408 if (fSchemaParser != null) { 409 fSchemaParser.resetNodePool(); 410 } 411 412 SchemaGrammar grammar = null; 413 String schemaNamespace = null; 414 short referType = desc.getContextType(); 415 if (referType != XSDDescription.CONTEXT_PREPARSE){ 422 grammar = findGrammar(desc); 424 if (grammar != null) 425 return grammar; 426 schemaNamespace = desc.getTargetNamespace(); 427 if (schemaNamespace != null) { 429 schemaNamespace = fSymbolTable.addSymbol(schemaNamespace); 430 } 431 } 432 433 prepareForParse(); 436 437 Document schemaRoot = getSchema(schemaNamespace, source, 439 referType == XSDDescription.CONTEXT_PREPARSE, 440 referType, null); 441 if (schemaRoot == null) { 442 return null; 444 } 445 if ( referType == XSDDescription.CONTEXT_PREPARSE) { 446 Element schemaElem = DOMUtil.getRoot(schemaRoot); 447 schemaNamespace = DOMUtil.getAttrValue(schemaElem, SchemaSymbols.ATT_TARGETNAMESPACE); 448 if(schemaNamespace != null && schemaNamespace.length() > 0) { 449 schemaNamespace = fSymbolTable.addSymbol(schemaNamespace); 452 desc.setTargetNamespace(schemaNamespace); 453 } 454 else { 455 schemaNamespace = null; 456 } 457 grammar = findGrammar(desc); 458 if (grammar != null) 459 return grammar; 460 String schemaId = source.getSystemId(); 461 XSDKey key = new XSDKey(schemaId, referType, schemaNamespace); 462 fTraversed.put(key, schemaRoot ); 463 if (schemaId != null) { 464 fDoc2SystemId.put(schemaRoot, schemaId ); 465 } 466 } 467 468 prepareForTraverse(); 471 472 fRoot = constructTrees(schemaRoot, source.getSystemId(), desc); 473 if (fRoot == null) { 474 return null; 475 } 476 477 buildGlobalNameRegistries(); 479 480 traverseSchemas(); 482 483 traverseLocalElements(); 485 486 resolveKeyRefs(); 488 489 493 for (int i = fAllTNSs.size() - 1; i >= 0; i--) { 496 String tns = (String )fAllTNSs.elementAt(i); 498 Vector ins = (Vector )fImportMap.get(tns); 500 SchemaGrammar sg = fGrammarBucket.getGrammar(emptyString2Null(tns)); 502 if (sg == null) 503 continue; 504 SchemaGrammar isg; 505 int count = 0; 507 for (int j = 0; j < ins.size(); j++) { 508 isg = fGrammarBucket.getGrammar((String )ins.elementAt(j)); 510 if (isg != null) 512 ins.setElementAt(isg, count++); 513 } 514 ins.setSize(count); 515 sg.setImportedGrammars(ins); 517 } 518 519 return fGrammarBucket.getGrammar(fRoot.fTargetNamespace); 521 } 523 527 SchemaGrammar getGrammar(String tns) { 528 return fGrammarBucket.getGrammar(tns); 529 } 530 531 536 protected SchemaGrammar findGrammar(XSDDescription desc) { 537 SchemaGrammar sg = fGrammarBucket.getGrammar(desc.getTargetNamespace()); 538 if (sg == null) { 539 if (fGrammarPool != null) { 540 sg = (SchemaGrammar)fGrammarPool.retrieveGrammar(desc); 541 if (sg != null) { 542 if (!fGrammarBucket.putGrammar(sg, true)) { 545 reportSchemaWarning("GrammarConflict", null, null); 548 sg = null; 549 } 550 } 551 } 552 } 553 return sg; 554 } 555 556 559 private static final String [][] NS_ERROR_CODES = { 560 {"src-include.2.1", "src-include.2.1"}, 561 {"src-redefine.3.1", "src-redefine.3.1"}, 562 {"src-import.3.1", "src-import.3.2"}, 563 null, 564 {"TargetNamespace.1", "TargetNamespace.2"}, 565 {"TargetNamespace.1", "TargetNamespace.2"}, 566 {"TargetNamespace.1", "TargetNamespace.2"}, 567 {"TargetNamespace.1", "TargetNamespace.2"} 568 }; 569 570 private static final String [] ELE_ERROR_CODES = { 571 "src-include.1", "src-redefine.2", "src-import.2", "schema_reference.4", 572 "schema_reference.4", "schema_reference.4", "schema_reference.4", "schema_reference.4" 573 }; 574 575 protected XSDocumentInfo constructTrees(Document schemaRoot, String locationHint, XSDDescription desc) { 586 if (schemaRoot == null) return null; 587 String callerTNS = desc.getTargetNamespace(); 588 short referType = desc.getContextType(); 589 590 XSDocumentInfo currSchemaInfo = null; 591 try { 592 currSchemaInfo = new XSDocumentInfo(schemaRoot, fAttributeChecker, fSymbolTable); 594 } catch (XMLSchemaException se) { 595 reportSchemaError(ELE_ERROR_CODES[referType], 596 new Object []{locationHint}, 597 DOMUtil.getRoot(schemaRoot)); 598 return null; 599 } 600 if (currSchemaInfo.fTargetNamespace != null && 602 currSchemaInfo.fTargetNamespace.length() == 0) { 603 reportSchemaWarning("EmptyTargetNamespace", 604 new Object []{locationHint}, 605 DOMUtil.getRoot(schemaRoot)); 606 currSchemaInfo.fTargetNamespace = null; 607 } 608 609 if (callerTNS != null) { 610 int secondIdx = 0; 613 if (referType == XSDDescription.CONTEXT_INCLUDE || 615 referType == XSDDescription.CONTEXT_REDEFINE) { 616 if (currSchemaInfo.fTargetNamespace == null) { 619 currSchemaInfo.fTargetNamespace = callerTNS; 620 currSchemaInfo.fIsChameleonSchema = true; 621 } 622 else if (callerTNS != currSchemaInfo.fTargetNamespace) { 625 reportSchemaError(NS_ERROR_CODES[referType][secondIdx], 626 new Object [] {callerTNS, currSchemaInfo.fTargetNamespace}, 627 DOMUtil.getRoot(schemaRoot)); 628 return null; 629 } 630 } 631 else if (referType != XSDDescription.CONTEXT_PREPARSE && callerTNS != currSchemaInfo.fTargetNamespace) { 633 reportSchemaError(NS_ERROR_CODES[referType][secondIdx], 634 new Object [] {callerTNS, currSchemaInfo.fTargetNamespace}, 635 DOMUtil.getRoot(schemaRoot)); 636 return null; 637 } 638 } 639 else if (currSchemaInfo.fTargetNamespace != null) { 642 if (referType == XSDDescription.CONTEXT_PREPARSE) { 644 desc.setTargetNamespace(currSchemaInfo.fTargetNamespace); 645 callerTNS = currSchemaInfo.fTargetNamespace; 646 } 647 else { 648 int secondIdx = 1; 651 reportSchemaError(NS_ERROR_CODES[referType][secondIdx], 652 new Object [] {callerTNS, currSchemaInfo.fTargetNamespace}, 653 DOMUtil.getRoot(schemaRoot)); 654 return null; 655 } 656 } 657 660 currSchemaInfo.addAllowedNS(currSchemaInfo.fTargetNamespace); 662 663 SchemaGrammar sg = null; 664 665 if (referType == XSDDescription.CONTEXT_INCLUDE || 666 referType == XSDDescription.CONTEXT_REDEFINE) { 667 sg = fGrammarBucket.getGrammar(currSchemaInfo.fTargetNamespace); 668 } 669 else { 670 sg = new SchemaGrammar(currSchemaInfo.fTargetNamespace, desc.makeClone(), fSymbolTable); 671 fGrammarBucket.putGrammar(sg); 672 } 673 674 sg.addDocument(null, (String )fDoc2SystemId.get(currSchemaInfo.fSchemaDoc)); 678 679 fDoc2XSDocumentMap.put(schemaRoot, currSchemaInfo); 680 681 Vector dependencies = new Vector (); 682 Element rootNode = DOMUtil.getRoot(schemaRoot); 683 684 Document newSchemaRoot = null; 685 for (Element child = DOMUtil.getFirstChildElement(rootNode); 686 child != null; 687 child = DOMUtil.getNextSiblingElement(child)) { 688 String schemaNamespace=null; 689 String schemaHint=null; 690 String localName = DOMUtil.getLocalName(child); 691 692 short refType = -1; 693 694 if (localName.equals(SchemaSymbols.ELT_ANNOTATION)) 695 continue; 696 else if (localName.equals(SchemaSymbols.ELT_IMPORT)) { 697 refType = XSDDescription.CONTEXT_IMPORT; 698
|