|  |  | 
|  |  | 
|  |  */ | 
|  | /* | 
|  |  * Licensed to the Apache Software Foundation (ASF) under one or more | 
|  |  * contributor license agreements.  See the NOTICE file distributed with | 
|  |  * this work for additional information regarding copyright ownership. | 
|  |  * The ASF licenses this file to You under the Apache License, Version 2.0 | 
|  |  * (the "License"); you may not use this file except in compliance with | 
|  |  * the License.  You may obtain a copy of the License at | 
|  |  * | 
|  |  *      http://www.apache.org/licenses/LICENSE-2.0 | 
|  |  * | 
|  |  * Unless required by applicable law or agreed to in writing, software | 
|  |  * distributed under the License is distributed on an "AS IS" BASIS, | 
|  |  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | 
|  |  * See the License for the specific language governing permissions and | 
|  |  * limitations under the License. | 
|  |  */ | 
|  |  | 
|  | package com.sun.org.apache.xerces.internal.impl.dtd; | 
|  |  | 
|  | import com.sun.org.apache.xerces.internal.impl.Constants; | 
|  | import com.sun.org.apache.xerces.internal.impl.XMLErrorReporter; | 
|  | import com.sun.org.apache.xerces.internal.impl.msg.XMLMessageFormatter; | 
|  | import com.sun.org.apache.xerces.internal.util.SymbolTable; | 
|  | import com.sun.org.apache.xerces.internal.util.XMLChar; | 
|  | import com.sun.org.apache.xerces.internal.util.XMLSymbols; | 
|  | import com.sun.org.apache.xerces.internal.xni.Augmentations; | 
|  | import com.sun.org.apache.xerces.internal.xni.XMLDTDContentModelHandler; | 
|  | import com.sun.org.apache.xerces.internal.xni.XMLDTDHandler; | 
|  | import com.sun.org.apache.xerces.internal.xni.XMLLocator; | 
|  | import com.sun.org.apache.xerces.internal.xni.XMLResourceIdentifier; | 
|  | import com.sun.org.apache.xerces.internal.xni.XMLString; | 
|  | import com.sun.org.apache.xerces.internal.xni.XNIException; | 
|  | import com.sun.org.apache.xerces.internal.xni.grammars.Grammar; | 
|  | import com.sun.org.apache.xerces.internal.xni.grammars.XMLGrammarDescription; | 
|  | import com.sun.org.apache.xerces.internal.xni.grammars.XMLGrammarPool; | 
|  | import com.sun.org.apache.xerces.internal.xni.parser.XMLComponent; | 
|  | import com.sun.org.apache.xerces.internal.xni.parser.XMLComponentManager; | 
|  | import com.sun.org.apache.xerces.internal.xni.parser.XMLConfigurationException; | 
|  | import com.sun.org.apache.xerces.internal.xni.parser.XMLDTDContentModelFilter; | 
|  | import com.sun.org.apache.xerces.internal.xni.parser.XMLDTDContentModelSource; | 
|  | import com.sun.org.apache.xerces.internal.xni.parser.XMLDTDFilter; | 
|  | import com.sun.org.apache.xerces.internal.xni.parser.XMLDTDSource; | 
|  | import java.util.ArrayList; | 
|  | import java.util.HashMap; | 
|  | import java.util.List; | 
|  | import java.util.Locale; | 
|  | import java.util.Map; | 
|  | import java.util.StringTokenizer; | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  */ | 
|  | public class XMLDTDProcessor | 
|  |         implements XMLComponent, XMLDTDFilter, XMLDTDContentModelFilter { | 
|  |  | 
|  |     // | 
|  |     // Constants | 
|  |     // | 
|  |  | 
|  |      | 
|  |     private static final int TOP_LEVEL_SCOPE = -1; | 
|  |  | 
|  |     // feature identifiers | 
|  |  | 
|  |      | 
|  |     protected static final String VALIDATION = | 
|  |         Constants.SAX_FEATURE_PREFIX + Constants.VALIDATION_FEATURE; | 
|  |  | 
|  |      | 
|  |     protected static final String NOTIFY_CHAR_REFS = | 
|  |         Constants.XERCES_FEATURE_PREFIX + Constants.NOTIFY_CHAR_REFS_FEATURE; | 
|  |  | 
|  |      | 
|  |     protected static final String WARN_ON_DUPLICATE_ATTDEF = | 
|  |         Constants.XERCES_FEATURE_PREFIX +Constants.WARN_ON_DUPLICATE_ATTDEF_FEATURE; | 
|  |  | 
|  |      | 
|  |     protected static final String WARN_ON_UNDECLARED_ELEMDEF = | 
|  |         Constants.XERCES_FEATURE_PREFIX + Constants.WARN_ON_UNDECLARED_ELEMDEF_FEATURE; | 
|  |  | 
|  |         protected static final String PARSER_SETTINGS = | 
|  |         Constants.XERCES_FEATURE_PREFIX + Constants.PARSER_SETTINGS; | 
|  |  | 
|  |     // property identifiers | 
|  |  | 
|  |      | 
|  |     protected static final String SYMBOL_TABLE = | 
|  |         Constants.XERCES_PROPERTY_PREFIX + Constants.SYMBOL_TABLE_PROPERTY; | 
|  |  | 
|  |      | 
|  |     protected static final String ERROR_REPORTER = | 
|  |         Constants.XERCES_PROPERTY_PREFIX + Constants.ERROR_REPORTER_PROPERTY; | 
|  |  | 
|  |      | 
|  |     protected static final String GRAMMAR_POOL = | 
|  |         Constants.XERCES_PROPERTY_PREFIX + Constants.XMLGRAMMAR_POOL_PROPERTY; | 
|  |  | 
|  |      | 
|  |     protected static final String DTD_VALIDATOR = | 
|  |         Constants.XERCES_PROPERTY_PREFIX + Constants.DTD_VALIDATOR_PROPERTY; | 
|  |  | 
|  |     // recognized features and properties | 
|  |  | 
|  |      | 
|  |     private static final String[] RECOGNIZED_FEATURES = { | 
|  |         VALIDATION, | 
|  |         WARN_ON_DUPLICATE_ATTDEF, | 
|  |         WARN_ON_UNDECLARED_ELEMDEF, | 
|  |         NOTIFY_CHAR_REFS, | 
|  |     }; | 
|  |  | 
|  |      | 
|  |     private static final Boolean[] FEATURE_DEFAULTS = { | 
|  |         null, | 
|  |         Boolean.FALSE, | 
|  |         Boolean.FALSE, | 
|  |         null, | 
|  |     }; | 
|  |  | 
|  |      | 
|  |     private static final String[] RECOGNIZED_PROPERTIES = { | 
|  |         SYMBOL_TABLE, | 
|  |         ERROR_REPORTER, | 
|  |         GRAMMAR_POOL, | 
|  |         DTD_VALIDATOR, | 
|  |     }; | 
|  |  | 
|  |      | 
|  |     private static final Object[] PROPERTY_DEFAULTS = { | 
|  |         null, | 
|  |         null, | 
|  |         null, | 
|  |         null, | 
|  |     }; | 
|  |  | 
|  |     // debugging | 
|  |  | 
|  |     // | 
|  |     // Data | 
|  |     // | 
|  |  | 
|  |     // features | 
|  |  | 
|  |      | 
|  |     protected boolean fValidation; | 
|  |  | 
|  |      | 
|  |     protected boolean fDTDValidation; | 
|  |  | 
|  |      | 
|  |     protected boolean fWarnDuplicateAttdef; | 
|  |  | 
|  |      | 
|  |     protected boolean fWarnOnUndeclaredElemdef; | 
|  |  | 
|  |     // properties | 
|  |  | 
|  |      | 
|  |     protected SymbolTable fSymbolTable; | 
|  |  | 
|  |      | 
|  |     protected XMLErrorReporter fErrorReporter; | 
|  |  | 
|  |      | 
|  |     protected DTDGrammarBucket fGrammarBucket; | 
|  |  | 
|  |     // the validator to which we look for our grammar bucket (the | 
|  |     // validator needs to hold the bucket so that it can initialize | 
|  |      | 
|  |     protected XMLDTDValidator fValidator; | 
|  |  | 
|  |      | 
|  |     protected XMLGrammarPool fGrammarPool; | 
|  |  | 
|  |      | 
|  |     protected Locale fLocale; | 
|  |  | 
|  |     // handlers | 
|  |  | 
|  |      | 
|  |     protected XMLDTDHandler fDTDHandler; | 
|  |  | 
|  |      | 
|  |     protected XMLDTDSource fDTDSource; | 
|  |  | 
|  |      | 
|  |     protected XMLDTDContentModelHandler fDTDContentModelHandler; | 
|  |  | 
|  |      | 
|  |     protected XMLDTDContentModelSource fDTDContentModelSource; | 
|  |  | 
|  |     // grammars | 
|  |  | 
|  |      | 
|  |     protected DTDGrammar fDTDGrammar; | 
|  |  | 
|  |     // state | 
|  |  | 
|  |      | 
|  |     private boolean fPerformValidation; | 
|  |  | 
|  |      | 
|  |     protected boolean fInDTDIgnore; | 
|  |  | 
|  |     // information regarding the current element | 
|  |  | 
|  |     // validation states | 
|  |  | 
|  |      | 
|  |     private boolean fMixed; | 
|  |  | 
|  |     // temporary variables | 
|  |  | 
|  |      | 
|  |     private final XMLEntityDecl fEntityDecl = new XMLEntityDecl(); | 
|  |  | 
|  |      | 
|  |     private final Map<String, String> fNDataDeclNotations = new HashMap<>(); | 
|  |  | 
|  |      | 
|  |     private String fDTDElementDeclName = null; | 
|  |  | 
|  |      | 
|  |     private final List<String> fMixedElementTypes = new ArrayList<>(); | 
|  |  | 
|  |      | 
|  |     private final List<String> fDTDElementDecls = new ArrayList<>(); | 
|  |  | 
|  |     // to check for duplicate ID or ANNOTATION attribute declare in | 
|  |     // ATTLIST, and misc VCs | 
|  |  | 
|  |      | 
|  |     private Map<String, String> fTableOfIDAttributeNames; | 
|  |  | 
|  |      | 
|  |     private Map<String, String> fTableOfNOTATIONAttributeNames; | 
|  |  | 
|  |      | 
|  |     private Map<String, String> fNotationEnumVals; | 
|  |  | 
|  |     // | 
|  |     // Constructors | 
|  |     // | 
|  |  | 
|  |      | 
|  |     public XMLDTDProcessor() { | 
|  |  | 
|  |         // initialize data | 
|  |  | 
|  |     } // <init>() | 
|  |  | 
|  |     // | 
|  |     // XMLComponent methods | 
|  |     // | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void reset(XMLComponentManager componentManager) throws XMLConfigurationException { | 
|  |  | 
|  |         boolean parser_settings = componentManager.getFeature(PARSER_SETTINGS, true); | 
|  |  | 
|  |         if (!parser_settings) { | 
|  |              | 
|  |             reset(); | 
|  |             return; | 
|  |         } | 
|  |  | 
|  |          | 
|  |         fValidation = componentManager.getFeature(VALIDATION, false); | 
|  |  | 
|  |         fDTDValidation = | 
|  |                 !(componentManager | 
|  |                     .getFeature( | 
|  |                         Constants.XERCES_FEATURE_PREFIX + Constants.SCHEMA_VALIDATION_FEATURE, false)); | 
|  |  | 
|  |         // Xerces features | 
|  |  | 
|  |         fWarnDuplicateAttdef = componentManager.getFeature(WARN_ON_DUPLICATE_ATTDEF, false); | 
|  |         fWarnOnUndeclaredElemdef = componentManager.getFeature(WARN_ON_UNDECLARED_ELEMDEF, false); | 
|  |  | 
|  |          | 
|  |         fErrorReporter = | 
|  |             (XMLErrorReporter) componentManager.getProperty( | 
|  |                 Constants.XERCES_PROPERTY_PREFIX + Constants.ERROR_REPORTER_PROPERTY); | 
|  |         fSymbolTable = | 
|  |             (SymbolTable) componentManager.getProperty( | 
|  |                 Constants.XERCES_PROPERTY_PREFIX + Constants.SYMBOL_TABLE_PROPERTY); | 
|  |  | 
|  |         fGrammarPool = (XMLGrammarPool) componentManager.getProperty(GRAMMAR_POOL, null); | 
|  |  | 
|  |         try { | 
|  |             fValidator = (XMLDTDValidator) componentManager.getProperty(DTD_VALIDATOR, null); | 
|  |         } catch (ClassCastException e) { | 
|  |             fValidator = null; | 
|  |         } | 
|  |          | 
|  |         if (fValidator != null) { | 
|  |             fGrammarBucket = fValidator.getGrammarBucket(); | 
|  |         } else { | 
|  |             fGrammarBucket = null; | 
|  |         } | 
|  |         reset(); | 
|  |  | 
|  |     } // reset(XMLComponentManager) | 
|  |  | 
|  |     protected void reset() { | 
|  |          | 
|  |         fDTDGrammar = null; | 
|  |          | 
|  |         fInDTDIgnore = false; | 
|  |  | 
|  |         fNDataDeclNotations.clear(); | 
|  |  | 
|  |          | 
|  |         if (fValidation) { | 
|  |  | 
|  |             if (fNotationEnumVals == null) { | 
|  |                 fNotationEnumVals = new HashMap<>(); | 
|  |             } | 
|  |             fNotationEnumVals.clear(); | 
|  |  | 
|  |             fTableOfIDAttributeNames = new HashMap<>(); | 
|  |             fTableOfNOTATIONAttributeNames = new HashMap<>(); | 
|  |         } | 
|  |  | 
|  |     } | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public String[] getRecognizedFeatures() { | 
|  |         return RECOGNIZED_FEATURES.clone(); | 
|  |     } // getRecognizedFeatures():String[] | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void setFeature(String featureId, boolean state) | 
|  |             throws XMLConfigurationException { | 
|  |     } // setFeature(String,boolean) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public String[] getRecognizedProperties() { | 
|  |         return RECOGNIZED_PROPERTIES.clone(); | 
|  |     } // getRecognizedProperties():String[] | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void setProperty(String propertyId, Object value) | 
|  |             throws XMLConfigurationException { | 
|  |     } // setProperty(String,Object) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public Boolean getFeatureDefault(String featureId) { | 
|  |         for (int i = 0; i < RECOGNIZED_FEATURES.length; i++) { | 
|  |             if (RECOGNIZED_FEATURES[i].equals(featureId)) { | 
|  |                 return FEATURE_DEFAULTS[i]; | 
|  |             } | 
|  |         } | 
|  |         return null; | 
|  |     } // getFeatureDefault(String):Boolean | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public Object getPropertyDefault(String propertyId) { | 
|  |         for (int i = 0; i < RECOGNIZED_PROPERTIES.length; i++) { | 
|  |             if (RECOGNIZED_PROPERTIES[i].equals(propertyId)) { | 
|  |                 return PROPERTY_DEFAULTS[i]; | 
|  |             } | 
|  |         } | 
|  |         return null; | 
|  |     } // getPropertyDefault(String):Object | 
|  |  | 
|  |     // | 
|  |     // XMLDTDSource methods | 
|  |     // | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void setDTDHandler(XMLDTDHandler dtdHandler) { | 
|  |         fDTDHandler = dtdHandler; | 
|  |     } // setDTDHandler(XMLDTDHandler) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public XMLDTDHandler getDTDHandler() { | 
|  |         return fDTDHandler; | 
|  |     } // getDTDHandler():  XMLDTDHandler | 
|  |  | 
|  |     // | 
|  |     // XMLDTDContentModelSource methods | 
|  |     // | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void setDTDContentModelHandler(XMLDTDContentModelHandler dtdContentModelHandler) { | 
|  |         fDTDContentModelHandler = dtdContentModelHandler; | 
|  |     } // setDTDContentModelHandler(XMLDTDContentModelHandler) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public XMLDTDContentModelHandler getDTDContentModelHandler() { | 
|  |         return fDTDContentModelHandler; | 
|  |     } // getDTDContentModelHandler():  XMLDTDContentModelHandler | 
|  |  | 
|  |     // | 
|  |     // XMLDTDContentModelHandler and XMLDTDHandler methods | 
|  |     // | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void startExternalSubset(XMLResourceIdentifier identifier, | 
|  |                                     Augmentations augs) throws XNIException { | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.startExternalSubset(identifier, augs); | 
|  |         if(fDTDHandler != null){ | 
|  |             fDTDHandler.startExternalSubset(identifier, augs); | 
|  |         } | 
|  |     } | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void endExternalSubset(Augmentations augs) throws XNIException { | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.endExternalSubset(augs); | 
|  |         if(fDTDHandler != null){ | 
|  |             fDTDHandler.endExternalSubset(augs); | 
|  |         } | 
|  |     } | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     protected static void checkStandaloneEntityRef(String name, DTDGrammar grammar, | 
|  |                     XMLEntityDecl tempEntityDecl, XMLErrorReporter errorReporter) throws XNIException { | 
|  |          | 
|  |         int entIndex = grammar.getEntityDeclIndex(name); | 
|  |         if (entIndex > -1) { | 
|  |             grammar.getEntityDecl(entIndex, tempEntityDecl); | 
|  |             if (tempEntityDecl.inExternal) { | 
|  |                 errorReporter.reportError( XMLMessageFormatter.XML_DOMAIN, | 
|  |                                             "MSG_REFERENCE_TO_EXTERNALLY_DECLARED_ENTITY_WHEN_STANDALONE", | 
|  |                                             new Object[]{name}, XMLErrorReporter.SEVERITY_ERROR); | 
|  |             } | 
|  |         } | 
|  |     } | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void comment(XMLString text, Augmentations augs) throws XNIException { | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.comment(text, augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.comment(text, augs); | 
|  |         } | 
|  |  | 
|  |     } // comment(XMLString) | 
|  |  | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void processingInstruction(String target, XMLString data, Augmentations augs) | 
|  |     throws XNIException { | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.processingInstruction(target, data, augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.processingInstruction(target, data, augs); | 
|  |         } | 
|  |     } // processingInstruction(String,XMLString) | 
|  |  | 
|  |     // | 
|  |     // XMLDTDHandler methods | 
|  |     // | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void startDTD(XMLLocator locator, Augmentations augs) throws XNIException { | 
|  |  | 
|  |  | 
|  |          | 
|  |         fNDataDeclNotations.clear(); | 
|  |         fDTDElementDecls.clear(); | 
|  |  | 
|  |         // the grammar bucket's DTDGrammar will now be the | 
|  |         // one we want, whether we're constructing it or not. | 
|  |         // if we're not constructing it, then we should not have a reference | 
|  |          | 
|  |        if( !fGrammarBucket.getActiveGrammar().isImmutable()) { | 
|  |             fDTDGrammar = fGrammarBucket.getActiveGrammar(); | 
|  |         } | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null ) | 
|  |             fDTDGrammar.startDTD(locator, augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.startDTD(locator, augs); | 
|  |         } | 
|  |  | 
|  |     } // startDTD(XMLLocator) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void ignoredCharacters(XMLString text, Augmentations augs) throws XNIException { | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null ) | 
|  |             fDTDGrammar.ignoredCharacters(text, augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.ignoredCharacters(text, augs); | 
|  |         } | 
|  |     } | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void textDecl(String version, String encoding, Augmentations augs) throws XNIException { | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null ) | 
|  |             fDTDGrammar.textDecl(version, encoding, augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.textDecl(version, encoding, augs); | 
|  |         } | 
|  |     } | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void startParameterEntity(String name, | 
|  |                                      XMLResourceIdentifier identifier, | 
|  |                                      String encoding, | 
|  |                                      Augmentations augs) throws XNIException { | 
|  |  | 
|  |         if (fPerformValidation && fDTDGrammar != null && | 
|  |                 fGrammarBucket.getStandalone()) { | 
|  |             checkStandaloneEntityRef(name, fDTDGrammar, fEntityDecl, fErrorReporter); | 
|  |         } | 
|  |          | 
|  |         if(fDTDGrammar != null ) | 
|  |             fDTDGrammar.startParameterEntity(name, identifier, encoding, augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.startParameterEntity(name, identifier, encoding, augs); | 
|  |         } | 
|  |     } | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void endParameterEntity(String name, Augmentations augs) throws XNIException { | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null ) | 
|  |             fDTDGrammar.endParameterEntity(name, augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.endParameterEntity(name, augs); | 
|  |         } | 
|  |     } | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void elementDecl(String name, String contentModel, Augmentations augs) | 
|  |     throws XNIException { | 
|  |  | 
|  |          | 
|  |         if (fValidation) { | 
|  |             if (fDTDElementDecls.contains(name)) { | 
|  |                 fErrorReporter.reportError(XMLMessageFormatter.XML_DOMAIN, | 
|  |                                            "MSG_ELEMENT_ALREADY_DECLARED", | 
|  |                                            new Object[]{ name}, | 
|  |                                            XMLErrorReporter.SEVERITY_ERROR); | 
|  |             } | 
|  |             else { | 
|  |                 fDTDElementDecls.add(name); | 
|  |             } | 
|  |         } | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null ) | 
|  |             fDTDGrammar.elementDecl(name, contentModel, augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.elementDecl(name, contentModel, augs); | 
|  |         } | 
|  |  | 
|  |     } // elementDecl(String,String) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void startAttlist(String elementName, Augmentations augs) | 
|  |         throws XNIException { | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null ) | 
|  |             fDTDGrammar.startAttlist(elementName, augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.startAttlist(elementName, augs); | 
|  |         } | 
|  |  | 
|  |     } // startAttlist(String) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void attributeDecl(String elementName, String attributeName, | 
|  |                               String type, String[] enumeration, | 
|  |                               String defaultType, XMLString defaultValue, | 
|  |                               XMLString nonNormalizedDefaultValue, Augmentations augs) throws XNIException { | 
|  |  | 
|  |         if (type != XMLSymbols.fCDATASymbol && defaultValue != null) { | 
|  |             normalizeDefaultAttrValue(defaultValue); | 
|  |         } | 
|  |  | 
|  |         if (fValidation) { | 
|  |  | 
|  |                 boolean duplicateAttributeDef = false ; | 
|  |  | 
|  |                  | 
|  |                 DTDGrammar grammar = (fDTDGrammar != null? fDTDGrammar:fGrammarBucket.getActiveGrammar()); | 
|  |                 int elementIndex       = grammar.getElementDeclIndex( elementName); | 
|  |                 if (grammar.getAttributeDeclIndex(elementIndex, attributeName) != -1) { | 
|  |                      | 
|  |                     duplicateAttributeDef = true ; | 
|  |  | 
|  |                      | 
|  |                     if(fWarnDuplicateAttdef){ | 
|  |                         fErrorReporter.reportError(XMLMessageFormatter.XML_DOMAIN, | 
|  |                                                  "MSG_DUPLICATE_ATTRIBUTE_DEFINITION", | 
|  |                                                  new Object[]{ elementName, attributeName }, | 
|  |                                                  XMLErrorReporter.SEVERITY_WARNING ); | 
|  |                     } | 
|  |                 } | 
|  |  | 
|  |  | 
|  |             // | 
|  |             // a) VC: One ID per Element Type, If duplicate ID attribute | 
|  |             // b) VC: ID attribute Default. if there is a declareared attribute | 
|  |              | 
|  |             if (type == XMLSymbols.fIDSymbol) { | 
|  |                 if (defaultValue != null && defaultValue.length != 0) { | 
|  |                     if (defaultType == null || | 
|  |                         !(defaultType == XMLSymbols.fIMPLIEDSymbol || | 
|  |                           defaultType == XMLSymbols.fREQUIREDSymbol)) { | 
|  |                         fErrorReporter.reportError(XMLMessageFormatter.XML_DOMAIN, | 
|  |                                                    "IDDefaultTypeInvalid", | 
|  |                                                    new Object[]{ attributeName}, | 
|  |                                                    XMLErrorReporter.SEVERITY_ERROR); | 
|  |                     } | 
|  |                 } | 
|  |  | 
|  |                 if (!fTableOfIDAttributeNames.containsKey(elementName)) { | 
|  |                     fTableOfIDAttributeNames.put(elementName, attributeName); | 
|  |                 } | 
|  |                 else { | 
|  |                         //we should not report an error, when there is duplicate attribute definition for given element type | 
|  |                         //according to XML 1.0 spec, When more than one definition is provided for the same attribute of a given | 
|  |                         //element type, the first declaration is binding and later declaration are *ignored*. So processor should | 
|  |                         //ignore the second declarations, however an application would be warned of the duplicate attribute defintion | 
|  |                         // if http://apache.org/xml/features/validation/warn-on-duplicate-attdef feature is set to true, | 
|  |                         // one typical case where this could be a  problem, when any XML file | 
|  |                         // provide the ID type information through internal subset so that it is available to the parser which read | 
|  |                         //only internal subset. Now that attribute declaration(ID Type) can again be part of external parsed entity | 
|  |                         //referenced. At that time if parser doesn't make this distinction it will throw an error for VC One ID per | 
|  |                         //Element Type, which (second defintion) actually should be ignored. Application behavior may differ on the | 
|  |                         //basis of error or warning thrown. - nb. | 
|  |  | 
|  |                         if(!duplicateAttributeDef){ | 
|  |                                 String previousIDAttributeName = fTableOfIDAttributeNames.get( elementName ); | 
|  |                                 fErrorReporter.reportError(XMLMessageFormatter.XML_DOMAIN, | 
|  |                                                "MSG_MORE_THAN_ONE_ID_ATTRIBUTE", | 
|  |                                                new Object[]{ elementName, previousIDAttributeName, attributeName}, | 
|  |                                                XMLErrorReporter.SEVERITY_ERROR); | 
|  |                         } | 
|  |                 } | 
|  |             } | 
|  |  | 
|  |             // | 
|  |             //  VC: One Notation Per Element Type, should check if there is a | 
|  |             //      duplicate NOTATION attribute | 
|  |  | 
|  |             if (type == XMLSymbols.fNOTATIONSymbol) { | 
|  |                 // VC: Notation Attributes: all notation names in the | 
|  |                  | 
|  |                 for (int i=0; i<enumeration.length; i++) { | 
|  |                     fNotationEnumVals.put(enumeration[i], attributeName); | 
|  |                 } | 
|  |  | 
|  |                 if (fTableOfNOTATIONAttributeNames.containsKey( elementName ) == false) { | 
|  |                     fTableOfNOTATIONAttributeNames.put( elementName, attributeName); | 
|  |                 } | 
|  |                 else { | 
|  |                     //we should not report an error, when there is duplicate attribute definition for given element type | 
|  |                     //according to XML 1.0 spec, When more than one definition is provided for the same attribute of a given | 
|  |                     //element type, the first declaration is binding and later declaration are *ignored*. So processor should | 
|  |                     //ignore the second declarations, however an application would be warned of the duplicate attribute definition | 
|  |                     // if http://apache.org/xml/features/validation/warn-on-duplicate-attdef feature is set to true, | 
|  |                     // Application behavior may differ on the basis of error or warning thrown. - nb. | 
|  |  | 
|  |                         if(!duplicateAttributeDef){ | 
|  |  | 
|  |                                 String previousNOTATIONAttributeName = fTableOfNOTATIONAttributeNames.get( elementName ); | 
|  |                                 fErrorReporter.reportError(XMLMessageFormatter.XML_DOMAIN, | 
|  |                                                "MSG_MORE_THAN_ONE_NOTATION_ATTRIBUTE", | 
|  |                                                new Object[]{ elementName, previousNOTATIONAttributeName, attributeName}, | 
|  |                                                XMLErrorReporter.SEVERITY_ERROR); | 
|  |                          } | 
|  |                 } | 
|  |             } | 
|  |  | 
|  |             // VC: No Duplicate Tokens | 
|  |              | 
|  |             if (type == XMLSymbols.fENUMERATIONSymbol || type == XMLSymbols.fNOTATIONSymbol) { | 
|  |                 outer: | 
|  |                     for (int i = 0; i < enumeration.length; ++i) { | 
|  |                         for (int j = i + 1; j < enumeration.length; ++j) { | 
|  |                             if (enumeration[i].equals(enumeration[j])) { | 
|  |                                 // Only report the first uniqueness violation. There could be others, | 
|  |                                 // but additional overhead would be incurred tracking unique tokens | 
|  |                                  | 
|  |                                 fErrorReporter.reportError(XMLMessageFormatter.XML_DOMAIN, | 
|  |                                                type == XMLSymbols.fENUMERATIONSymbol | 
|  |                                                    ? "MSG_DISTINCT_TOKENS_IN_ENUMERATION" | 
|  |                                                    : "MSG_DISTINCT_NOTATION_IN_ENUMERATION", | 
|  |                                                new Object[]{ elementName, enumeration[i], attributeName }, | 
|  |                                                XMLErrorReporter.SEVERITY_ERROR); | 
|  |                                 break outer; | 
|  |                             } | 
|  |                         } | 
|  |                     } | 
|  |             } | 
|  |  | 
|  |              | 
|  |             boolean ok = true; | 
|  |             if (defaultValue != null && | 
|  |                 (defaultType == null || | 
|  |                  (defaultType != null && defaultType == XMLSymbols.fFIXEDSymbol))) { | 
|  |  | 
|  |                 String value = defaultValue.toString(); | 
|  |                 if (type == XMLSymbols.fNMTOKENSSymbol || | 
|  |                     type == XMLSymbols.fENTITIESSymbol || | 
|  |                     type == XMLSymbols.fIDREFSSymbol) { | 
|  |  | 
|  |                     StringTokenizer tokenizer = new StringTokenizer(value," "); | 
|  |                     if (tokenizer.hasMoreTokens()) { | 
|  |                         while (true) { | 
|  |                             String nmtoken = tokenizer.nextToken(); | 
|  |                             if (type == XMLSymbols.fNMTOKENSSymbol) { | 
|  |                                 if (!isValidNmtoken(nmtoken)) { | 
|  |                                     ok = false; | 
|  |                                     break; | 
|  |                                 } | 
|  |                             } | 
|  |                             else if (type == XMLSymbols.fENTITIESSymbol || | 
|  |                                      type == XMLSymbols.fIDREFSSymbol) { | 
|  |                                 if (!isValidName(nmtoken)) { | 
|  |                                     ok = false; | 
|  |                                     break; | 
|  |                                 } | 
|  |                             } | 
|  |                             if (!tokenizer.hasMoreTokens()) { | 
|  |                                 break; | 
|  |                             } | 
|  |                         } | 
|  |                     } | 
|  |  | 
|  |                 } | 
|  |                 else { | 
|  |                     if (type == XMLSymbols.fENTITYSymbol || | 
|  |                         type == XMLSymbols.fIDSymbol || | 
|  |                         type == XMLSymbols.fIDREFSymbol || | 
|  |                         type == XMLSymbols.fNOTATIONSymbol) { | 
|  |  | 
|  |                         if (!isValidName(value)) { | 
|  |                             ok = false; | 
|  |                         } | 
|  |  | 
|  |                     } | 
|  |                     else if (type == XMLSymbols.fNMTOKENSymbol || | 
|  |                              type == XMLSymbols.fENUMERATIONSymbol) { | 
|  |  | 
|  |                         if (!isValidNmtoken(value)) { | 
|  |                             ok = false; | 
|  |                         } | 
|  |                     } | 
|  |  | 
|  |                     if (type == XMLSymbols.fNOTATIONSymbol || | 
|  |                         type == XMLSymbols.fENUMERATIONSymbol) { | 
|  |                         ok = false; | 
|  |                         for (int i=0; i<enumeration.length; i++) { | 
|  |                             if (defaultValue.equals(enumeration[i])) { | 
|  |                                 ok = true; | 
|  |                             } | 
|  |                         } | 
|  |                     } | 
|  |  | 
|  |                 } | 
|  |                 if (!ok) { | 
|  |                     fErrorReporter.reportError(XMLMessageFormatter.XML_DOMAIN, | 
|  |                                                "MSG_ATT_DEFAULT_INVALID", | 
|  |                                                new Object[]{attributeName, value}, | 
|  |                                                XMLErrorReporter.SEVERITY_ERROR); | 
|  |                 } | 
|  |             } | 
|  |         } | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.attributeDecl(elementName, attributeName, | 
|  |                                   type, enumeration, | 
|  |                                   defaultType, defaultValue, nonNormalizedDefaultValue, augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.attributeDecl(elementName, attributeName, | 
|  |                                       type, enumeration, | 
|  |                                       defaultType, defaultValue, nonNormalizedDefaultValue, augs); | 
|  |         } | 
|  |  | 
|  |     } // attributeDecl(String,String,String,String[],String,XMLString, XMLString, Augmentations) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void endAttlist(Augmentations augs) throws XNIException { | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.endAttlist(augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.endAttlist(augs); | 
|  |         } | 
|  |  | 
|  |     } // endAttlist() | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void internalEntityDecl(String name, XMLString text, | 
|  |                                    XMLString nonNormalizedText, | 
|  |                                    Augmentations augs) throws XNIException { | 
|  |  | 
|  |         DTDGrammar grammar = (fDTDGrammar != null? fDTDGrammar: fGrammarBucket.getActiveGrammar()); | 
|  |         int index = grammar.getEntityDeclIndex(name) ; | 
|  |  | 
|  |         //If the same entity is declared more than once, the first declaration | 
|  |         //encountered is binding, SAX requires only effective(first) declaration | 
|  |         //to be reported to the application | 
|  |  | 
|  |         //REVISIT: Does it make sense to pass duplicate Entity information across | 
|  |         //the pipeline -- nb? | 
|  |  | 
|  |          | 
|  |         if(index == -1){ | 
|  |              | 
|  |             if(fDTDGrammar != null) | 
|  |                 fDTDGrammar.internalEntityDecl(name, text, nonNormalizedText, augs); | 
|  |              | 
|  |             if (fDTDHandler != null) { | 
|  |                 fDTDHandler.internalEntityDecl(name, text, nonNormalizedText, augs); | 
|  |             } | 
|  |         } | 
|  |  | 
|  |     } // internalEntityDecl(String,XMLString,XMLString) | 
|  |  | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void externalEntityDecl(String name, XMLResourceIdentifier identifier, | 
|  |                                    Augmentations augs) throws XNIException { | 
|  |  | 
|  |         DTDGrammar grammar = (fDTDGrammar != null? fDTDGrammar:  fGrammarBucket.getActiveGrammar()); | 
|  |         int index = grammar.getEntityDeclIndex(name) ; | 
|  |  | 
|  |         //If the same entity is declared more than once, the first declaration | 
|  |         //encountered is binding, SAX requires only effective(first) declaration | 
|  |         //to be reported to the application | 
|  |  | 
|  |         //REVISIT: Does it make sense to pass duplicate entity information across | 
|  |         //the pipeline -- nb? | 
|  |  | 
|  |          | 
|  |         if(index == -1){ | 
|  |              | 
|  |             if(fDTDGrammar != null) | 
|  |                 fDTDGrammar.externalEntityDecl(name, identifier, augs); | 
|  |              | 
|  |             if (fDTDHandler != null) { | 
|  |                 fDTDHandler.externalEntityDecl(name, identifier, augs); | 
|  |             } | 
|  |         } | 
|  |  | 
|  |     } // externalEntityDecl(String,XMLResourceIdentifier, Augmentations) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void unparsedEntityDecl(String name, XMLResourceIdentifier identifier, | 
|  |                                    String notation, | 
|  |                                    Augmentations augs) throws XNIException { | 
|  |  | 
|  |          | 
|  |         if (fValidation) { | 
|  |             fNDataDeclNotations.put(name, notation); | 
|  |         } | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.unparsedEntityDecl(name, identifier, notation, augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.unparsedEntityDecl(name, identifier, notation, augs); | 
|  |         } | 
|  |  | 
|  |     } // unparsedEntityDecl(String,XMLResourceIdentifier,String,Augmentations) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void notationDecl(String name, XMLResourceIdentifier identifier, | 
|  |                              Augmentations augs) throws XNIException { | 
|  |  | 
|  |          | 
|  |         if (fValidation) { | 
|  |             DTDGrammar grammar = (fDTDGrammar != null ? fDTDGrammar : fGrammarBucket.getActiveGrammar()); | 
|  |             if (grammar.getNotationDeclIndex(name) != -1) { | 
|  |                 fErrorReporter.reportError(XMLMessageFormatter.XML_DOMAIN, | 
|  |                                            "UniqueNotationName", | 
|  |                                            new Object[]{name}, | 
|  |                                            XMLErrorReporter.SEVERITY_ERROR); | 
|  |             } | 
|  |         } | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.notationDecl(name, identifier, augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.notationDecl(name, identifier, augs); | 
|  |         } | 
|  |  | 
|  |     } // notationDecl(String,XMLResourceIdentifier, Augmentations) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void startConditional(short type, Augmentations augs) throws XNIException { | 
|  |  | 
|  |          | 
|  |         fInDTDIgnore = type == XMLDTDHandler.CONDITIONAL_IGNORE; | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.startConditional(type, augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.startConditional(type, augs); | 
|  |         } | 
|  |  | 
|  |     } // startConditional(short) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void endConditional(Augmentations augs) throws XNIException { | 
|  |  | 
|  |          | 
|  |         fInDTDIgnore = false; | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.endConditional(augs); | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.endConditional(augs); | 
|  |         } | 
|  |  | 
|  |     } // endConditional() | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void endDTD(Augmentations augs) throws XNIException { | 
|  |  | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) { | 
|  |             fDTDGrammar.endDTD(augs); | 
|  |             if(fGrammarPool != null) | 
|  |                 fGrammarPool.cacheGrammars(XMLGrammarDescription.XML_DTD, new Grammar[] {fDTDGrammar}); | 
|  |         } | 
|  |         if (fValidation) { | 
|  |             DTDGrammar grammar = (fDTDGrammar != null? fDTDGrammar: fGrammarBucket.getActiveGrammar()); | 
|  |  | 
|  |              | 
|  |             for (Map.Entry<String, String> entry : fNDataDeclNotations.entrySet()) { | 
|  |                 String notation = entry.getValue(); | 
|  |                 if (grammar.getNotationDeclIndex(notation) == -1) { | 
|  |                     String entity = entry.getKey(); | 
|  |                     fErrorReporter.reportError(XMLMessageFormatter.XML_DOMAIN, | 
|  |                             "MSG_NOTATION_NOT_DECLARED_FOR_UNPARSED_ENTITYDECL", | 
|  |                             new Object[]{entity, notation}, | 
|  |                             XMLErrorReporter.SEVERITY_ERROR); | 
|  |                 } | 
|  |             } | 
|  |  | 
|  |             for (Map.Entry<String, String> entry : fNotationEnumVals.entrySet()) { | 
|  |                 String notation = entry.getKey(); | 
|  |                 if (grammar.getNotationDeclIndex(notation) == -1) { | 
|  |                     String attributeName = entry.getValue(); | 
|  |                     fErrorReporter.reportError(XMLMessageFormatter.XML_DOMAIN, | 
|  |                             "MSG_NOTATION_NOT_DECLARED_FOR_NOTATIONTYPE_ATTRIBUTE", | 
|  |                             new Object[]{attributeName, notation}, | 
|  |                             XMLErrorReporter.SEVERITY_ERROR); | 
|  |                 } | 
|  |             } | 
|  |  | 
|  |             // VC: No Notation on Empty Element | 
|  |              | 
|  |             for (Map.Entry<String, String> entry : fTableOfNOTATIONAttributeNames.entrySet()) { | 
|  |                 String elementName = entry.getKey(); | 
|  |                 int elementIndex = grammar.getElementDeclIndex(elementName); | 
|  |                 if (grammar.getContentSpecType(elementIndex) == XMLElementDecl.TYPE_EMPTY) { | 
|  |                     String attributeName = entry.getValue(); | 
|  |                     fErrorReporter.reportError(XMLMessageFormatter.XML_DOMAIN, | 
|  |                                                "NoNotationOnEmptyElement", | 
|  |                                                new Object[]{elementName, attributeName}, | 
|  |                                                XMLErrorReporter.SEVERITY_ERROR); | 
|  |                 } | 
|  |             } | 
|  |  | 
|  |              | 
|  |             fTableOfIDAttributeNames = null; | 
|  |             fTableOfNOTATIONAttributeNames = null; | 
|  |  | 
|  |              | 
|  |             if (fWarnOnUndeclaredElemdef) { | 
|  |                 checkDeclaredElements(grammar); | 
|  |             } | 
|  |         } | 
|  |  | 
|  |          | 
|  |         if (fDTDHandler != null) { | 
|  |             fDTDHandler.endDTD(augs); | 
|  |         } | 
|  |  | 
|  |     } // endDTD() | 
|  |  | 
|  |      | 
|  |     public void setDTDSource(XMLDTDSource source ) { | 
|  |         fDTDSource = source; | 
|  |     } // setDTDSource(XMLDTDSource) | 
|  |  | 
|  |      | 
|  |     public XMLDTDSource getDTDSource() { | 
|  |         return fDTDSource; | 
|  |     } // getDTDSource():  XMLDTDSource | 
|  |  | 
|  |     // | 
|  |     // XMLDTDContentModelHandler methods | 
|  |     // | 
|  |  | 
|  |      | 
|  |     public void setDTDContentModelSource(XMLDTDContentModelSource source ) { | 
|  |         fDTDContentModelSource = source; | 
|  |     } // setDTDContentModelSource(XMLDTDContentModelSource) | 
|  |  | 
|  |      | 
|  |     public XMLDTDContentModelSource getDTDContentModelSource() { | 
|  |         return fDTDContentModelSource; | 
|  |     } // getDTDContentModelSource():  XMLDTDContentModelSource | 
|  |  | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void startContentModel(String elementName, Augmentations augs) | 
|  |         throws XNIException { | 
|  |  | 
|  |         if (fValidation) { | 
|  |             fDTDElementDeclName = elementName; | 
|  |             fMixedElementTypes.clear(); | 
|  |         } | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.startContentModel(elementName, augs); | 
|  |         if (fDTDContentModelHandler != null) { | 
|  |             fDTDContentModelHandler.startContentModel(elementName, augs); | 
|  |         } | 
|  |  | 
|  |     } // startContentModel(String) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void any(Augmentations augs) throws XNIException { | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.any(augs); | 
|  |         if (fDTDContentModelHandler != null) { | 
|  |             fDTDContentModelHandler.any(augs); | 
|  |         } | 
|  |     } // any() | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void empty(Augmentations augs) throws XNIException { | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.empty(augs); | 
|  |         if (fDTDContentModelHandler != null) { | 
|  |             fDTDContentModelHandler.empty(augs); | 
|  |         } | 
|  |     } // empty() | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void startGroup(Augmentations augs) throws XNIException { | 
|  |  | 
|  |         fMixed = false; | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.startGroup(augs); | 
|  |         if (fDTDContentModelHandler != null) { | 
|  |             fDTDContentModelHandler.startGroup(augs); | 
|  |         } | 
|  |  | 
|  |     } // startGroup() | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void pcdata(Augmentations augs) { | 
|  |         fMixed = true; | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.pcdata(augs); | 
|  |         if (fDTDContentModelHandler != null) { | 
|  |             fDTDContentModelHandler.pcdata(augs); | 
|  |         } | 
|  |     } // pcdata() | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void element(String elementName, Augmentations augs) throws XNIException { | 
|  |  | 
|  |          | 
|  |         if (fMixed && fValidation) { | 
|  |             if (fMixedElementTypes.contains(elementName)) { | 
|  |                 fErrorReporter.reportError(XMLMessageFormatter.XML_DOMAIN, | 
|  |                                            "DuplicateTypeInMixedContent", | 
|  |                                            new Object[]{fDTDElementDeclName, elementName}, | 
|  |                                            XMLErrorReporter.SEVERITY_ERROR); | 
|  |             } | 
|  |             else { | 
|  |                 fMixedElementTypes.add(elementName); | 
|  |             } | 
|  |         } | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.element(elementName, augs); | 
|  |         if (fDTDContentModelHandler != null) { | 
|  |             fDTDContentModelHandler.element(elementName, augs); | 
|  |         } | 
|  |  | 
|  |     } // childrenElement(String) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void separator(short separator, Augmentations augs) | 
|  |         throws XNIException { | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.separator(separator, augs); | 
|  |         if (fDTDContentModelHandler != null) { | 
|  |             fDTDContentModelHandler.separator(separator, augs); | 
|  |         } | 
|  |  | 
|  |     } // separator(short) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void occurrence(short occurrence, Augmentations augs) | 
|  |         throws XNIException { | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.occurrence(occurrence, augs); | 
|  |         if (fDTDContentModelHandler != null) { | 
|  |             fDTDContentModelHandler.occurrence(occurrence, augs); | 
|  |         } | 
|  |  | 
|  |     } // occurrence(short) | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void endGroup(Augmentations augs) throws XNIException { | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.endGroup(augs); | 
|  |         if (fDTDContentModelHandler != null) { | 
|  |             fDTDContentModelHandler.endGroup(augs); | 
|  |         } | 
|  |  | 
|  |     } // endGroup() | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     public void endContentModel(Augmentations augs) throws XNIException { | 
|  |  | 
|  |          | 
|  |         if(fDTDGrammar != null) | 
|  |             fDTDGrammar.endContentModel(augs); | 
|  |         if (fDTDContentModelHandler != null) { | 
|  |             fDTDContentModelHandler.endContentModel(augs); | 
|  |         } | 
|  |  | 
|  |     } // endContentModel() | 
|  |  | 
|  |     // | 
|  |     // Private methods | 
|  |     // | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     private boolean normalizeDefaultAttrValue(XMLString value) { | 
|  |  | 
|  |         boolean skipSpace = true;  | 
|  |         int current = value.offset; | 
|  |         int end = value.offset + value.length; | 
|  |         for (int i = value.offset; i < end; i++) { | 
|  |             if (value.ch[i] == ' ') { | 
|  |                 if (!skipSpace) { | 
|  |                      | 
|  |                     value.ch[current++] = ' '; | 
|  |                     skipSpace = true; | 
|  |                 } | 
|  |                 else { | 
|  |                     // just skip it. | 
|  |                 } | 
|  |             } | 
|  |             else { | 
|  |                  | 
|  |                 if (current != i) { | 
|  |                     value.ch[current] = value.ch[i]; | 
|  |                 } | 
|  |                 current++; | 
|  |                 skipSpace = false; | 
|  |             } | 
|  |         } | 
|  |         if (current != end) { | 
|  |             if (skipSpace) { | 
|  |                  | 
|  |                 current--; | 
|  |             } | 
|  |              | 
|  |             value.length = current - value.offset; | 
|  |             return true; | 
|  |         } | 
|  |         return false; | 
|  |     } | 
|  |  | 
|  |     protected boolean isValidNmtoken(String nmtoken) { | 
|  |         return XMLChar.isValidNmtoken(nmtoken); | 
|  |     } // isValidNmtoken(String):  boolean | 
|  |  | 
|  |     protected boolean isValidName(String name) { | 
|  |         return XMLChar.isValidName(name); | 
|  |     } // isValidName(String):  boolean | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     private void checkDeclaredElements(DTDGrammar grammar) { | 
|  |         int elementIndex = grammar.getFirstElementDeclIndex(); | 
|  |         XMLContentSpec contentSpec = new XMLContentSpec(); | 
|  |         while (elementIndex >= 0) { | 
|  |             int type = grammar.getContentSpecType(elementIndex); | 
|  |             if (type == XMLElementDecl.TYPE_CHILDREN || type == XMLElementDecl.TYPE_MIXED) { | 
|  |                 checkDeclaredElements(grammar, | 
|  |                         elementIndex, | 
|  |                         grammar.getContentSpecIndex(elementIndex), | 
|  |                         contentSpec); | 
|  |             } | 
|  |             elementIndex = grammar.getNextElementDeclIndex(elementIndex); | 
|  |         } | 
|  |     } | 
|  |  | 
|  |      | 
|  |  | 
|  |  | 
|  |  | 
|  |      */ | 
|  |     private void checkDeclaredElements(DTDGrammar grammar, int elementIndex, | 
|  |             int contentSpecIndex, XMLContentSpec contentSpec) { | 
|  |         grammar.getContentSpec(contentSpecIndex, contentSpec); | 
|  |         if (contentSpec.type == XMLContentSpec.CONTENTSPECNODE_LEAF) { | 
|  |             String value = (String) contentSpec.value; | 
|  |             if (value != null && grammar.getElementDeclIndex(value) == -1) { | 
|  |                 fErrorReporter.reportError(XMLMessageFormatter.XML_DOMAIN, | 
|  |                         "UndeclaredElementInContentSpec", | 
|  |                         new Object[]{grammar.getElementDeclName(elementIndex).rawname, value}, | 
|  |                         XMLErrorReporter.SEVERITY_WARNING); | 
|  |             } | 
|  |         } | 
|  |         // It's not a leaf, so we have to recurse its left and maybe right | 
|  |          | 
|  |         else if ((contentSpec.type == XMLContentSpec.CONTENTSPECNODE_CHOICE) | 
|  |                 || (contentSpec.type == XMLContentSpec.CONTENTSPECNODE_SEQ)) { | 
|  |             final int leftNode = ((int[])contentSpec.value)[0]; | 
|  |             final int rightNode = ((int[])contentSpec.otherValue)[0]; | 
|  |              | 
|  |             checkDeclaredElements(grammar, elementIndex, leftNode, contentSpec); | 
|  |             checkDeclaredElements(grammar, elementIndex, rightNode, contentSpec); | 
|  |         } | 
|  |         else if (contentSpec.type == XMLContentSpec.CONTENTSPECNODE_ZERO_OR_MORE | 
|  |                 || contentSpec.type == XMLContentSpec.CONTENTSPECNODE_ZERO_OR_ONE | 
|  |                 || contentSpec.type == XMLContentSpec.CONTENTSPECNODE_ONE_OR_MORE) { | 
|  |             final int leftNode = ((int[])contentSpec.value)[0]; | 
|  |             checkDeclaredElements(grammar, elementIndex, leftNode, contentSpec); | 
|  |         } | 
|  |     } | 
|  |  | 
|  | } // class XMLDTDProcessor |