XMLSCHEMA-56 - Element defined in a base type sometimes isn't visited by an XmlSchemaWalker's visitor. Thanks to kgi. This closes #4.

diff --git a/xmlschema-walker/src/main/java/org/apache/ws/commons/schema/walker/SchemasByNamespace.java b/xmlschema-walker/src/main/java/org/apache/ws/commons/schema/walker/SchemasByNamespace.java
new file mode 100644
index 0000000..b2b54a6
--- /dev/null
+++ b/xmlschema-walker/src/main/java/org/apache/ws/commons/schema/walker/SchemasByNamespace.java
@@ -0,0 +1,210 @@
+/**
+ * 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 org.apache.ws.commons.schema.walker;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import javax.xml.namespace.QName;
+
+import org.apache.ws.commons.schema.XmlSchema;
+import org.apache.ws.commons.schema.XmlSchemaAttribute;
+import org.apache.ws.commons.schema.XmlSchemaAttributeGroup;
+import org.apache.ws.commons.schema.XmlSchemaElement;
+import org.apache.ws.commons.schema.XmlSchemaGroup;
+import org.apache.ws.commons.schema.XmlSchemaType;
+
+/**
+ * A class that allows XmlSchemas to be stored, indexed by a String which is the schema's target namespace.
+ * Multiple schemas are allowed for each namespace.
+ * It provides methods that allow all schemas for a given namespace to be searched, for example when the caller
+ * wishes to find an xsd type defined for a particular namespace.
+ **/
+class SchemasByNamespace {
+
+    /**
+     * the map of namespaces to a list of XmlSchemas
+     */
+    private final Map<String, List<XmlSchema>> mData = new HashMap<String, List<XmlSchema>>();
+
+    /**
+     * Associates an XmlSchema with a namespace
+     * @param aNamespace the namespace in question
+     * @param aSchema a schema with aNamespace as its target
+     */
+    public void addSchema(String aNamespace, XmlSchema aSchema) {
+        if (aNamespace == null) {
+            aNamespace = "";
+        }
+        List<XmlSchema> value = mData.get(aNamespace);
+        if (value == null) {
+            value = new ArrayList<XmlSchema>();
+            mData.put(aNamespace, value);
+        }
+        value.add(aSchema);
+    }
+
+    /**
+     * Returns a List of XmlSchemas that have been associated with the given namespace using addSchema(...).
+     * @param aNamespace the namespace in question
+     * @return a List of XmlSchemas which target aNamespace
+     */
+    public XmlSchema[] getSchemas(String aNamespace) {
+        if (aNamespace == null) {
+            aNamespace = "";
+        }
+        List<XmlSchema> l = mData.get(aNamespace);
+        return l == null ? new XmlSchema[0] : l.toArray(new XmlSchema[l.size()]);
+    }
+
+    /**
+     * Returns an XmlSchemaType with the given QName.
+     * The namespace defined by the name is used to find the schema in which the type is defined, and thus the type itself.
+     * @param aTypeName the name of the type, which must return the correct value for aTypeName.getNamespaceURI().
+     * @return the XmlSchemaType with name aTypeName or null if no such type is found
+     */
+    public XmlSchemaType getTypeByName(QName aTypeName) {
+        XmlSchema[] schemas = getSchemas(aTypeName.getNamespaceURI());
+        for (XmlSchema s : schemas) {
+            XmlSchemaType t = s.getTypeByName(aTypeName);
+            if (t != null) {
+                return t;
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Returns an XmlSchemaGroup with the given QName.
+     * The namespace defined by the name is used to find the schema in which the group is defined, and thus the group itself.
+     * @param aGroupName the name of the group, which must return the correct value for aGroupName.getNamespaceURI().
+     * @return the XmlSchemaGroup with name aGroupName or null if no such group is found
+     */
+    public XmlSchemaGroup getGroupByName(QName aGroupName) {
+        XmlSchema[] schemas = getSchemas(aGroupName.getNamespaceURI());
+        for (XmlSchema s : schemas) {
+            XmlSchemaGroup g = s.getGroupByName(aGroupName);
+            if (g != null) {
+                return g;
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Returns an XmlSchemaAttribute with the given QName.
+     * The namespace defined by the name is used to find the schema in which the attribute is defined, and thus the attribute itself.
+     * @param aAttName the name of the attribute, which must return the correct value for aAttName.getNamespaceURI().
+     * @return the XmlSchemaAttribute with name aAttName or null if no such attribute is found
+     */
+    public XmlSchemaAttribute getAttributeByName(QName aAttName) {
+        XmlSchema[] schemas = getSchemas(aAttName.getNamespaceURI());
+        for (XmlSchema s : schemas) {
+            XmlSchemaAttribute a = s.getAttributeByName(aAttName);
+            if (a != null) {
+                return a;
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Returns an XmlSchemaAttributeGroup with the given QName.
+     * The namespace defined by the name is used to find the schema in which the attribute group is defined, and thus the attribute group itself.
+     * @param aAGName the name of the attribute group, which must return the correct value for aAGName.getNamespaceURI().
+     * @return the XmlSchemaAttributeGroup with name aAGName or null if no such attribute group is found
+     */
+    public XmlSchemaAttributeGroup getAttributeGroupByName(QName aAGName) {
+        XmlSchema[] schemas = getSchemas(aAGName.getNamespaceURI());
+        for (XmlSchema s : schemas) {
+            XmlSchemaAttributeGroup ag = s.getAttributeGroupByName(aAGName);
+            if (ag != null) {
+                return ag;
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Returns an XmlSchemaElement with the given QName.
+     * The namespace defined by the name is used to find the schema in which the element is defined, and thus the element itself.
+     * @param aElementName the name of the element, which must return the correct value for aElementName.getNamespaceURI().
+     * @return the XmlSchemaElement with name aElementName or null if no such element is found
+     */
+    public XmlSchemaElement getElementByName(QName aElementName) {
+        XmlSchema[] schemas = getSchemas(aElementName.getNamespaceURI());
+        for (XmlSchema s : schemas) {
+            XmlSchemaElement e = s.getElementByName(aElementName);
+            if (e != null) {
+                return e;
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Returns an XmlSchema which includes an element with the given QName.
+     * The namespace defined by the name is used to find the schema in which the element is defined.
+     * @param aElementName the name of the element, which must return the correct value for aElementName.getNamespaceURI().
+     * @return the XmlSchema which includes the element with name aElementName or null if no such schema is found
+     */
+    public XmlSchema getSchemaDefiningElement(QName aElementName) {
+        XmlSchema[] schemas = getSchemas(aElementName.getNamespaceURI());
+        for (XmlSchema s : schemas) {
+            XmlSchemaElement e = s.getElementByName(aElementName);
+            if (e != null) {
+                return s;
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Returns an XmlSchema which includes an attribute with the given QName.
+     * The namespace defined by the name is used to find the schema in which the attribute is defined.
+     * @param aAttName the name of the attribute, which must return the correct value for aAttName.getNamespaceURI().
+     * @return the XmlSchema which includes the attribute with name aAttName or null if no such schema is found
+     */
+    public XmlSchema getSchemaDefiningAttribute(QName aAttName) {
+        XmlSchema[] schemas = getSchemas(aAttName.getNamespaceURI());
+        for (XmlSchema s : schemas) {
+            XmlSchemaAttribute a = s.getAttributeByName(aAttName);
+            if (a != null) {
+                return s;
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Returns the first XmlSchema added with the given namespace, using addSchema(...)
+     * @param aNamespace the namespace in question
+     * @return the XmlSchema first added with aNamespace
+     */
+    public XmlSchema getFirstSchema(String aNamespace) {
+        XmlSchema[] schemas = getSchemas(aNamespace);
+        if (schemas.length > 0) {
+            return schemas[0];
+        } else {
+            return null;
+        }
+    }
+}
diff --git a/xmlschema-walker/src/main/java/org/apache/ws/commons/schema/walker/XmlSchemaScope.java b/xmlschema-walker/src/main/java/org/apache/ws/commons/schema/walker/XmlSchemaScope.java
index 34e0343..f87c1dc 100644
--- a/xmlschema-walker/src/main/java/org/apache/ws/commons/schema/walker/XmlSchemaScope.java
+++ b/xmlschema-walker/src/main/java/org/apache/ws/commons/schema/walker/XmlSchemaScope.java
@@ -63,7 +63,7 @@
  */
 final class XmlSchemaScope {
 
-    private Map<String, XmlSchema> schemasByNamespace;
+    private SchemasByNamespace schemasByNamespace;
     private Map<QName, XmlSchemaScope> scopeCache;
 
     private XmlSchemaTypeInfo typeInfo;
@@ -100,7 +100,7 @@
      * @param substitutions The master list of substitution groups to pull from.
      * @param userRecognizedTypes The set of types recognized by the caller.
      */
-    XmlSchemaScope(XmlSchemaType type, Map<String, XmlSchema> xmlSchemasByNamespace,
+    XmlSchemaScope(XmlSchemaType type, SchemasByNamespace xmlSchemasByNamespace,
                    Map<QName, XmlSchemaScope> scopeCache, Set<QName> userRecognizedTypes) {
 
         this();
@@ -169,9 +169,7 @@
             XmlSchemaSimpleTypeList list = (XmlSchemaSimpleTypeList)content;
             XmlSchemaSimpleType listType = list.getItemType();
             if (listType == null) {
-                XmlSchema schema = schemasByNamespace.get(list.getItemTypeName().getNamespaceURI());
-
-                listType = (XmlSchemaSimpleType)schema.getTypeByName(list.getItemTypeName());
+                listType = (XmlSchemaSimpleType)schemasByNamespace.getTypeByName(list.getItemTypeName());
             }
             if (listType == null) {
                 throw new IllegalArgumentException("Unrecognized schema type for list "
@@ -202,8 +200,7 @@
                 }
 
                 for (QName namedBaseType : namedBaseTypes) {
-                    XmlSchema schema = schemasByNamespace.get(namedBaseType.getNamespaceURI());
-                    XmlSchemaSimpleType baseType = (XmlSchemaSimpleType)schema.getTypeByName(namedBaseType);
+                    XmlSchemaSimpleType baseType = (XmlSchemaSimpleType)schemasByNamespace.getTypeByName(namedBaseType);
                     if (baseType != null) {
                         baseTypes.add(baseType);
                     }
@@ -247,8 +244,7 @@
             } else {
                 XmlSchemaSimpleType baseType = restr.getBaseType();
                 if (baseType == null) {
-                    XmlSchema schema = schemasByNamespace.get(restr.getBaseTypeName().getNamespaceURI());
-                    baseType = (XmlSchemaSimpleType)schema.getTypeByName(restr.getBaseTypeName());
+                    baseType = (XmlSchemaSimpleType)schemasByNamespace.getTypeByName(restr.getBaseTypeName());
                 }
 
                 if (baseType != null) {
@@ -323,8 +319,7 @@
         if (content instanceof XmlSchemaComplexContentExtension) {
             XmlSchemaComplexContentExtension ext = (XmlSchemaComplexContentExtension)content;
 
-            XmlSchema schema = schemasByNamespace.get(ext.getBaseTypeName().getNamespaceURI());
-            XmlSchemaType baseType = schema.getTypeByName(ext.getBaseTypeName());
+            XmlSchemaType baseType = schemasByNamespace.getTypeByName(ext.getBaseTypeName());
 
             XmlSchemaParticle baseParticle = null;
             XmlSchemaAnyAttribute baseAnyAttr = null;
@@ -418,9 +413,7 @@
         } else if (content instanceof XmlSchemaComplexContentRestriction) {
             final XmlSchemaComplexContentRestriction rstr = (XmlSchemaComplexContentRestriction)content;
 
-            final XmlSchema schema = schemasByNamespace.get(rstr.getBaseTypeName().getNamespaceURI());
-
-            final XmlSchemaType baseType = schema.getTypeByName(rstr.getBaseTypeName());
+            final XmlSchemaType baseType = schemasByNamespace.getTypeByName(rstr.getBaseTypeName());
 
             XmlSchemaScope parentScope = null;
             if (baseType != null) {
@@ -460,8 +453,7 @@
             XmlSchemaSimpleContentExtension ext = (XmlSchemaSimpleContentExtension)content;
             attributes = createAttributeMap(ext.getAttributes());
 
-            XmlSchema schema = schemasByNamespace.get(ext.getBaseTypeName().getNamespaceURI());
-            XmlSchemaType baseType = schema.getTypeByName(ext.getBaseTypeName());
+            XmlSchemaType baseType = schemasByNamespace.getTypeByName(ext.getBaseTypeName());
 
             if (baseType != null) {
                 final XmlSchemaScope parentScope = getScope(baseType);
@@ -484,8 +476,7 @@
             if (rstr.getBaseType() != null) {
                 baseType = rstr.getBaseType();
             } else {
-                XmlSchema schema = schemasByNamespace.get(rstr.getBaseTypeName().getNamespaceURI());
-                baseType = schema.getTypeByName(rstr.getBaseTypeName());
+                baseType = schemasByNamespace.getTypeByName(rstr.getBaseTypeName());
             }
 
             if (baseType != null) {
@@ -505,8 +496,7 @@
 
         XmlSchemaAttributeGroup attrGroup = groupRef.getRef().getTarget();
         if (attrGroup == null) {
-            XmlSchema schema = schemasByNamespace.get(groupRef.getTargetQName().getNamespaceURI());
-            attrGroup = schema.getAttributeGroupByName(groupRef.getTargetQName());
+            attrGroup = schemasByNamespace.getAttributeGroupByName(groupRef.getTargetQName());
         }
         return getAttributesOf(attrGroup);
     }
@@ -556,7 +546,6 @@
         } else {
             attrQName = attribute.getQName();
         }
-        final XmlSchema schema = schemasByNamespace.get(attrQName.getNamespaceURI());
 
         if (!attribute.isRef() && (forceCopy || (attribute.getSchemaType() == null))) {
             // If we are forcing a copy, there is no reference to follow.
@@ -565,7 +554,7 @@
             if (attribute.getRef().getTarget() != null) {
                 globalAttr = attribute.getRef().getTarget();
             } else {
-                globalAttr = schema.getAttributeByName(attrQName);
+                globalAttr = schemasByNamespace.getAttributeByName(attrQName);
             }
         }
 
@@ -573,8 +562,7 @@
         if (schemaType == null) {
             final QName typeQName = globalAttr.getSchemaTypeName();
             if (typeQName != null) {
-                XmlSchema typeSchema = schemasByNamespace.get(typeQName.getNamespaceURI());
-                schemaType = (XmlSchemaSimpleType) typeSchema.getTypeByName(typeQName);
+                schemaType = (XmlSchemaSimpleType) schemasByNamespace.getTypeByName(typeQName);
             }
         }
 
@@ -603,6 +591,12 @@
             attrUsage = XmlSchemaUse.OPTIONAL;
         }
 
+        XmlSchema schema = schemasByNamespace.getSchemaDefiningAttribute(attrQName);
+        if (schema == null) {
+            // TODO: is this correct? The previous code used whichever schema was stored in the schemasByNamespace HashMap
+            // for the attribute's namespace.
+            schema = attribute.getParent();
+        }
         final XmlSchemaAttribute copy = new XmlSchemaAttribute(schema, false);
         copy.setName(globalAttr.getName());
 
@@ -788,7 +782,7 @@
             return childFacets;
         }
 
-        HashMap<XmlSchemaRestriction.Type, List<XmlSchemaRestriction>> mergedFacets 
+        HashMap<XmlSchemaRestriction.Type, List<XmlSchemaRestriction>> mergedFacets
             = new HashMap<XmlSchemaRestriction.Type, List<XmlSchemaRestriction>>(parentFacets);
 
         // Child facets override parent facets
diff --git a/xmlschema-walker/src/main/java/org/apache/ws/commons/schema/walker/XmlSchemaWalker.java b/xmlschema-walker/src/main/java/org/apache/ws/commons/schema/walker/XmlSchemaWalker.java
index 1b790b0..3251687 100644
--- a/xmlschema-walker/src/main/java/org/apache/ws/commons/schema/walker/XmlSchemaWalker.java
+++ b/xmlschema-walker/src/main/java/org/apache/ws/commons/schema/walker/XmlSchemaWalker.java
@@ -53,9 +53,9 @@
     private Set<QName> userRecognizedTypes;
 
     private final XmlSchemaCollection schemas;
-    private final ArrayList<XmlSchemaVisitor> visitors;
+    private final List<XmlSchemaVisitor> visitors;
     private final Map<QName, List<XmlSchemaElement>> elemsBySubstGroup;
-    private final Map<String, XmlSchema> schemasByNamespace;
+    private final SchemasByNamespace schemasByNamespace;
     private final Map<QName, XmlSchemaScope> scopeCache;
     private final Set<QName> visitedElements;
 
@@ -72,11 +72,11 @@
         schemas = xmlSchemas;
         visitors = new ArrayList<XmlSchemaVisitor>(1);
 
-        schemasByNamespace = new HashMap<String, XmlSchema>();
+        schemasByNamespace = new SchemasByNamespace();
         elemsBySubstGroup = new HashMap<QName, List<XmlSchemaElement>>();
 
         for (XmlSchema schema : schemas.getXmlSchemas()) {
-            schemasByNamespace.put(schema.getTargetNamespace(), schema);
+            schemasByNamespace.addSchema(schema.getTargetNamespace(), schema);
 
             for (XmlSchemaElement elem : schema.getElements().values()) {
                 if (elem.getSubstitutionGroup() != null) {
@@ -211,8 +211,7 @@
         if (schemaType == null) {
             final QName typeQName = element.getSchemaTypeName();
             if (typeQName != null) {
-                XmlSchema schema = schemasByNamespace.get(typeQName.getNamespaceURI());
-                schemaType = schema.getTypeByName(typeQName);
+                schemaType = schemasByNamespace.getTypeByName(typeQName);
             }
         }
 
@@ -233,7 +232,7 @@
 
             // 2. for each visitor, call visitor.startElement(element, type);
             final boolean previouslyVisited = (!element.isAnonymous() && visitedElements.contains(element
-                .getQName()));
+                                                                                                  .getQName()));
 
             for (XmlSchemaVisitor visitor : visitors) {
                 visitor.onEnterElement(element, typeInfo, previouslyVisited);
@@ -308,7 +307,7 @@
 
         } else if (!element.isAbstract()) {
             throw new IllegalStateException("Element " + element.getQName()
-                                            + " is not abstract and has no type.");
+            + " is not abstract and has no type.");
         }
 
         // 8. Now handle substitute elements, if any.
@@ -328,9 +327,10 @@
             XmlSchemaGroupRef groupRef = (XmlSchemaGroupRef)particle;
             XmlSchemaGroupParticle group = groupRef.getParticle();
             if (group == null) {
-                XmlSchema schema = schemasByNamespace.get(groupRef.getRefName().getNamespaceURI());
-
-                group = schema.getGroupByName(groupRef.getRefName()).getParticle();
+                XmlSchemaGroup g = schemasByNamespace.getGroupByName(groupRef.getRefName());
+                if (g != null) {
+                    group = g.getParticle();
+                }
             }
             walk(group, groupRef.getMinOccurs(), groupRef.getMaxOccurs());
 
@@ -375,7 +375,7 @@
 
         } else {
             throw new IllegalArgumentException("Unrecognized XmlSchemaGroupParticle of type "
-                                               + group.getClass().getName());
+                + group.getClass().getName());
         }
 
         // 2. Make a copy if necessary.
@@ -515,7 +515,6 @@
         }
 
         final QName elemQName = getElementQName(element);
-        final XmlSchema schema = schemasByNamespace.get(elemQName.getNamespaceURI());
 
         XmlSchemaElement globalElem = null;
         if (!element.isRef()) {
@@ -523,7 +522,7 @@
         } else if (element.getRef().getTarget() != null) {
             globalElem = element.getRef().getTarget();
         } else {
-            globalElem = schema.getElementByName(elemQName);
+            globalElem = schemasByNamespace.getElementByName(elemQName);
         }
 
         /*
@@ -536,6 +535,13 @@
             id = globalElem.getId();
         }
 
+        XmlSchema schema = schemasByNamespace.getSchemaDefiningElement(elemQName);
+        if (schema == null) {
+            // TODO: is this correct? The previous code used whichever schema was stored in the schemasByNamespace HashMap
+            // for the element's namespace.
+            schema = element.getParent();
+        }
+
         final XmlSchemaElement copy = new XmlSchemaElement(schema, false);
         copy.setName(globalElem.getName());
         copy.setAbstract(globalElem.isAbstract());
diff --git a/xmlschema-walker/src/test/java/org/apache/ws/commons/schema/walker/TestMultipleFilesPerNamespace.java b/xmlschema-walker/src/test/java/org/apache/ws/commons/schema/walker/TestMultipleFilesPerNamespace.java
new file mode 100644
index 0000000..166fd58
--- /dev/null
+++ b/xmlschema-walker/src/test/java/org/apache/ws/commons/schema/walker/TestMultipleFilesPerNamespace.java
@@ -0,0 +1,207 @@
+/**
+ * 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 org.apache.ws.commons.schema.walker;
+
+import java.io.File;
+import java.io.FileReader;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.xml.transform.stream.StreamSource;
+
+import org.apache.ws.commons.schema.XmlSchema;
+import org.apache.ws.commons.schema.XmlSchemaAll;
+import org.apache.ws.commons.schema.XmlSchemaAny;
+import org.apache.ws.commons.schema.XmlSchemaAnyAttribute;
+import org.apache.ws.commons.schema.XmlSchemaChoice;
+import org.apache.ws.commons.schema.XmlSchemaCollection;
+import org.apache.ws.commons.schema.XmlSchemaElement;
+import org.apache.ws.commons.schema.XmlSchemaSequence;
+import org.apache.ws.commons.schema.testutils.UtilsForTests;
+import org.junit.Test;
+
+public class TestMultipleFilesPerNamespace {
+
+    @Test
+    public void testMultipleFilesPerNamespace() throws Exception {
+        List<String> expected = new ArrayList<String>();
+        expected.add("{http://avro.apache.org/AvroTest}root");
+        expected.add("{http://avro.apache.org/AvroTest}baseElement");
+        expected.add("{http://avro.apache.org/AvroTest}includedType");
+        expected.add("{http://avro.apache.org/AvroTest}includedElement");
+        expected.add("{http://avro.apache.org/AvroTest}differentNamespaceType");
+        expected.add("{http://avro.apache.org/AvroTest2}differentNamespaceElement");
+        expected.add("{http://avro.apache.org/AvroTest}noNamespaceType");
+        expected.add("noNSElement");
+
+        MyVisitor v = new MyVisitor(expected);
+
+        XmlSchemaCollection collection = null;
+        FileReader fileReader = null;
+        try {
+            File file = UtilsForTests.buildFile("src", "test", "resources", "test_multiple_files_per_namespace.xsd");
+            fileReader = new FileReader(file);
+
+            collection = new XmlSchemaCollection();
+            collection.read(new StreamSource(fileReader, file.getAbsolutePath()));
+
+        } finally {
+            if (fileReader != null) {
+                try {
+                    fileReader.close();
+                } catch (IOException ioe) {
+                    ioe.printStackTrace();
+                }
+            }
+        }
+
+        XmlSchemaElement elem = getElementOf(collection, "root");
+        XmlSchemaWalker walker = new XmlSchemaWalker(collection, v);
+        try {
+            walker.walk(elem);
+        } catch (Exception e) {
+            throw new IllegalStateException(e.getMessage());
+        }
+
+
+        int pos = v.getNextExpectedPosition();
+        if (pos != expected.size()) {
+            throw new IllegalStateException("expected a further element");
+        }
+    }
+
+    class MyVisitor implements XmlSchemaVisitor {
+        List<String> mExpectedElements = null;
+        int mListPos = 0;
+
+        public MyVisitor(List<String> aExpectedElements) {
+            mExpectedElements = aExpectedElements;
+        }
+
+        public int getNextExpectedPosition () {
+            return mListPos;
+        }
+
+        @Override
+        public void onEnterElement(XmlSchemaElement element, XmlSchemaTypeInfo typeInfo, boolean previouslyVisited) {
+            // TODO Auto-generated method stub
+            if (mListPos >= mExpectedElements.size()) {
+                throw new IllegalStateException("unexpected element");
+            }
+            String expected = mExpectedElements.get(mListPos++);
+            if (!element.getQName().toString().equals(expected)) {
+                throw new IllegalStateException("incorrect element");
+            }
+        }
+
+        @Override
+        public void onExitElement(XmlSchemaElement element, XmlSchemaTypeInfo typeInfo, boolean previouslyVisited) {
+            // TODO Auto-generated method stub
+
+        }
+
+        @Override
+        public void onVisitAttribute(XmlSchemaElement element, XmlSchemaAttrInfo attrInfo) {
+            // TODO Auto-generated method stub
+
+        }
+
+        @Override
+        public void onEndAttributes(XmlSchemaElement element, XmlSchemaTypeInfo typeInfo) {
+            // TODO Auto-generated method stub
+
+        }
+
+        @Override
+        public void onEnterSubstitutionGroup(XmlSchemaElement base) {
+            // TODO Auto-generated method stub
+
+        }
+
+        @Override
+        public void onExitSubstitutionGroup(XmlSchemaElement base) {
+            // TODO Auto-generated method stub
+
+        }
+
+        @Override
+        public void onEnterAllGroup(XmlSchemaAll all) {
+            // TODO Auto-generated method stub
+
+        }
+
+        @Override
+        public void onExitAllGroup(XmlSchemaAll all) {
+            // TODO Auto-generated method stub
+
+        }
+
+        @Override
+        public void onEnterChoiceGroup(XmlSchemaChoice choice) {
+            // TODO Auto-generated method stub
+
+        }
+
+        @Override
+        public void onExitChoiceGroup(XmlSchemaChoice choice) {
+            // TODO Auto-generated method stub
+
+        }
+
+        @Override
+        public void onEnterSequenceGroup(XmlSchemaSequence seq) {
+            // TODO Auto-generated method stub
+
+        }
+
+        @Override
+        public void onExitSequenceGroup(XmlSchemaSequence seq) {
+            // TODO Auto-generated method stub
+
+        }
+
+        @Override
+        public void onVisitAny(XmlSchemaAny any) {
+            // TODO Auto-generated method stub
+
+        }
+
+        @Override
+        public void onVisitAnyAttribute(XmlSchemaElement element, XmlSchemaAnyAttribute anyAttr) {
+            // TODO Auto-generated method stub
+
+        }
+
+    }
+
+    private static XmlSchemaElement getElementOf(XmlSchemaCollection collection, String name) {
+
+        XmlSchemaElement elem = null;
+        XmlSchema[] schemas = collection.getXmlSchemas();
+        for (XmlSchema schema : schemas) {
+            elem = schema.getElementByName(name);
+            if (elem != null) {
+                break;
+            }
+        }
+        return elem;
+    }
+}
+
diff --git a/xmlschema-walker/src/test/java/org/apache/ws/commons/schema/walker/TestSchemaWalker.java b/xmlschema-walker/src/test/java/org/apache/ws/commons/schema/walker/TestSchemaWalker.java
index 51ef535..c4ab3b4 100644
--- a/xmlschema-walker/src/test/java/org/apache/ws/commons/schema/walker/TestSchemaWalker.java
+++ b/xmlschema-walker/src/test/java/org/apache/ws/commons/schema/walker/TestSchemaWalker.java
@@ -498,12 +498,7 @@
         private HashMap<String, List<Attribute>> attributes;
     }
 
-    /**
-     * Test for src/main/resources/test_schema.xsd
-     */
-    @SuppressWarnings("unchecked")
-    @Test
-    public void test() throws Exception {
+    public void test(File aFile) throws Exception {
         // Build the expectations.
         ArrayList<Attribute> attrGroupAttrs = new ArrayList<Attribute>(43);
 
@@ -856,11 +851,10 @@
         XmlSchemaCollection collection = null;
         FileReader fileReader = null;
         try {
-            File file = UtilsForTests.buildFile("src", "test", "resources", "test_schema.xsd");
-            fileReader = new FileReader(file);
+            fileReader = new FileReader(aFile);
 
             collection = new XmlSchemaCollection();
-            collection.read(new StreamSource(fileReader, file.getAbsolutePath()));
+            collection.read(new StreamSource(fileReader, aFile.getAbsolutePath()));
 
         } finally {
             if (fileReader != null) {
@@ -883,6 +877,24 @@
         Assert.assertTrue(stack.isEmpty());
     }
 
+    /**
+     * test for test_schema.xsd
+     */
+    @Test
+    public void testSchemaWalker() throws Exception {
+        File file = UtilsForTests.buildFile("src", "test", "resources", "test_schema.xsd");
+        test(file);
+    }
+
+    /**
+     * test for test_multiple_files_per_namespace2.xsd, which is test_schema.xsd distributed between three files
+     */
+    @Test
+    public void testMultipleFilesPerNamespace2() throws Exception {
+        File file = UtilsForTests.buildFile("src", "test", "resources", "test_multiple_files_per_namespace2.xsd");
+        test(file);
+    }
+
     private static void checkFacets(String nextName, XmlSchemaTypeInfo typeInfo,
                                     Set<XmlSchemaRestriction> nextFacets) {
         if (typeInfo == null) {
diff --git a/xmlschema-walker/src/test/resources/test_mfpn2_included1.xsd b/xmlschema-walker/src/test/resources/test_mfpn2_included1.xsd
new file mode 100644
index 0000000..7ae2523
--- /dev/null
+++ b/xmlschema-walker/src/test/resources/test_mfpn2_included1.xsd
@@ -0,0 +1,104 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ 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. 
+ -->
+<!--
+ This file is included by test_multiple_files_per_namespace2.xsd
+ -->
+ <xsd:schema xmlns="http://www.w3.org/2001/XMLSchema" targetNamespace="http://avro.apache.org/AvroTest" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:avro="http://avro.apache.org/AvroTest">
+
+	<xsd:attributeGroup name="attrGroup" id="attrGroup">
+		<xsd:annotation>
+			<xsd:documentation>An attribute group with attributes of all simple types.</xsd:documentation>
+		</xsd:annotation>
+		<xsd:attribute name="anySimpleType"        type="xsd:anySimpleType"      use="optional" />
+		<xsd:attribute name="duration"             type="xsd:duration"           use="optional" />
+		<xsd:attribute name="dateTime"             type="xsd:dateTime"           use="optional" />
+		<xsd:attribute name="date"                 type="xsd:date"               use="optional" />
+		<xsd:attribute name="time"                 type="xsd:time"               use="optional" />
+		<xsd:attribute name="gYearMonth"           type="xsd:gYearMonth"         use="optional" />
+		<xsd:attribute name="gYear"                type="xsd:gYear"              use="optional" />
+		<xsd:attribute name="gMonthDay"            type="xsd:gMonthDay"          use="optional" />
+		<xsd:attribute name="gDay"                 type="xsd:gDay"               use="optional" />
+		<xsd:attribute name="gMonth"               type="xsd:gMonth"             use="optional" />
+		<xsd:attribute name="string"               type="xsd:string"             use="optional" />
+		<xsd:attribute name="boolean"              type="xsd:boolean"            use="optional" />
+		<xsd:attribute name="base64Binary"         type="xsd:base64Binary"       use="optional" />
+		<xsd:attribute name="hexBinary"            type="xsd:hexBinary"          use="optional" />
+		<xsd:attribute name="float"                type="xsd:float"              use="optional" />
+		<xsd:attribute name="decimal"              use="optional">
+			<xsd:simpleType>
+				<xsd:restriction base="xsd:decimal">
+					<xsd:fractionDigits value="0"></xsd:fractionDigits>
+				</xsd:restriction>
+			</xsd:simpleType>
+		</xsd:attribute>
+		<xsd:attribute name="double"               type="xsd:double"             use="optional" />
+		<xsd:attribute name="anyURI"               type="xsd:anyURI"             use="optional" />
+		<xsd:attribute name="qname"                type="xsd:QName"              use="optional" />
+		<xsd:attribute name="normalizedString"     type="xsd:normalizedString"   use="optional" />
+		<xsd:attribute name="token"                type="xsd:token"              use="optional" />
+		<xsd:attribute name="language"             type="xsd:language"           use="optional" />
+		<xsd:attribute name="name"                 type="xsd:Name"               use="optional" />
+		<xsd:attribute name="ncName"               type="xsd:NCName"             use="optional" />
+		<xsd:attribute name="nmtoken"              type="xsd:NMTOKEN"            use="optional" />
+		<xsd:attribute name="nmtokens"             type="xsd:NMTOKENS"           use="optional" />
+		<xsd:attribute name="id"                   type="xsd:ID"                 use="optional" />
+		<xsd:attribute name="idref"                type="xsd:IDREF"              use="optional" />
+		<xsd:attribute name="idrefs"               type="xsd:IDREFS"             use="optional" />
+		<xsd:attribute name="entity"               type="xsd:ENTITY"             use="optional" />
+		<xsd:attribute name="entities"             type="xsd:ENTITIES"           use="optional" />
+		<xsd:attribute name="integer"              type="xsd:integer"            use="optional" />
+		<xsd:attribute name="nonPositiveInteger"   type="xsd:nonPositiveInteger" use="optional" />
+		<xsd:attribute name="nonNegativeInteger"   type="xsd:nonNegativeInteger" use="optional" />
+		<xsd:attribute name="positiveInteger"      type="xsd:positiveInteger"    use="optional" />
+		<xsd:attribute name="negativeInteger"      type="xsd:negativeInteger"    use="optional" />
+		<xsd:attribute name="long"                 type="xsd:long"               use="optional" />
+		<xsd:attribute name="int"                  type="xsd:int"                use="optional" />
+		<xsd:attribute name="short"                type="xsd:short"              use="optional" />
+		<xsd:attribute name="byte"                 type="xsd:byte"               use="optional" />
+		<xsd:attribute name="unsignedLong"         type="xsd:unsignedLong"       use="optional" />
+		<xsd:attribute name="unsignedInt"          type="xsd:unsignedInt"        use="optional" />
+		<xsd:attribute name="unsignedShort"        type="xsd:unsignedShort"      use="optional" />
+		<xsd:attribute name="unsignedByte"         type="xsd:unsignedByte"       use="optional" />
+		<xsd:attribute name="unknown"              use="optional"/>
+	</xsd:attributeGroup>
+
+	<xsd:group name="groupOfAll">
+		<xsd:annotation>
+			<xsd:documentation>An All Group</xsd:documentation>
+		</xsd:annotation>
+		<xsd:all>
+			<xsd:element ref="avro:primitive"        />
+			<xsd:element ref="avro:nonNullPrimitive" />
+			<xsd:element ref="avro:record"           />
+			<xsd:element ref="avro:list"             />
+		</xsd:all>
+	</xsd:group>
+
+	<xsd:simpleType name="nonNullPrimitiveType">
+		<xsd:restriction base="avro:primitiveType">
+			<xsd:enumeration value="boolean" />
+			<xsd:enumeration value="int" />
+			<xsd:enumeration value="long" />
+			<xsd:enumeration value="float" />
+			<xsd:enumeration value="double" />
+			<xsd:enumeration value="decimal" />
+			<xsd:enumeration value="bytes" />
+			<xsd:enumeration value="string" />
+		</xsd:restriction>
+	</xsd:simpleType>
+</xsd:schema>
diff --git a/xmlschema-walker/src/test/resources/test_mfpn2_included2.xsd b/xmlschema-walker/src/test/resources/test_mfpn2_included2.xsd
new file mode 100644
index 0000000..5d726ac
--- /dev/null
+++ b/xmlschema-walker/src/test/resources/test_mfpn2_included2.xsd
@@ -0,0 +1,50 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ 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. 
+ -->
+ <!--
+ This file is included by test_multiple_files_per_namespace2.xsd
+ -->
+ <xsd:schema xmlns="http://www.w3.org/2001/XMLSchema" targetNamespace="http://avro.apache.org/AvroTest" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:avro="http://avro.apache.org/AvroTest">
+
+	<xsd:attribute name="size">
+		<xsd:simpleType>
+			<xsd:restriction base="xsd:nonNegativeInteger">
+				<xsd:maxExclusive value="100" />
+			</xsd:restriction>
+		</xsd:simpleType>
+	</xsd:attribute>
+
+	<xsd:group name="group">
+		<xsd:annotation>
+			<xsd:documentation>A group of nested sequences, choices, and elements.</xsd:documentation>
+		</xsd:annotation>
+		<xsd:sequence>
+			<xsd:choice minOccurs="0" maxOccurs="unbounded">
+				<xsd:element ref="avro:primitive"        />
+				<xsd:element ref="avro:nonNullPrimitive" />
+				<xsd:element ref="avro:record"           />
+				<xsd:element ref="avro:list"             />
+				<xsd:element ref="avro:tuple"            />
+			</xsd:choice>
+		</xsd:sequence>
+	</xsd:group>
+
+	<xsd:complexType name="recordType">
+		<xsd:group ref="avro:group" />
+	</xsd:complexType>
+
+</xsd:schema>
diff --git a/xmlschema-walker/src/test/resources/test_mfpn_included1.xsd b/xmlschema-walker/src/test/resources/test_mfpn_included1.xsd
new file mode 100644
index 0000000..cad2370
--- /dev/null
+++ b/xmlschema-walker/src/test/resources/test_mfpn_included1.xsd
@@ -0,0 +1,37 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ 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. 
+ -->
+ <!--
+ This file is included by test_multiple_files_per_namespace.xsd 
+  -->
+<xs:schema targetNamespace="http://avro.apache.org/AvroTest"
+	xmlns:xs="http://www.w3.org/2001/XMLSchema"
+	xmlns:avro="http://avro.apache.org/AvroTest"
+	xmlns:avro2="http://avro.apache.org/AvroTest2">
+
+	<xs:import namespace="http://avro.apache.org/AvroTest2" schemaLocation="test_mfpn_included2.xsd"/>
+	<xs:import namespace="" schemaLocation="test_mfpn_included3.xsd"/>
+
+	<xs:complexType name="Included">
+		<xs:sequence>
+			<xs:element name="includedElement" type="xs:string"/>
+			<xs:element name="differentNamespaceType" type="avro2:DifferentNS"/>
+			<xs:element name="noNamespaceType" type="NoNS"/>
+		</xs:sequence>
+	</xs:complexType>
+
+</xs:schema>
diff --git a/xmlschema-walker/src/test/resources/test_mfpn_included2.xsd b/xmlschema-walker/src/test/resources/test_mfpn_included2.xsd
new file mode 100644
index 0000000..11f26ff
--- /dev/null
+++ b/xmlschema-walker/src/test/resources/test_mfpn_included2.xsd
@@ -0,0 +1,31 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ 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. 
+ -->
+ <!--
+ This file is imported by test_mpfn_included1 which is in turn included by test_multiple_files_per_namespace.xsd 
+  -->
+<xs:schema targetNamespace="http://avro.apache.org/AvroTest2"
+	xmlns:xs="http://www.w3.org/2001/XMLSchema"
+	xmlns:avro2="http://avro.apache.org/AvroTest2">
+
+	<xs:complexType name="DifferentNS">
+		<xs:sequence>
+			<xs:element name="differentNamespaceElement" type="xs:string"/>
+		</xs:sequence>
+	</xs:complexType>
+
+</xs:schema>
diff --git a/xmlschema-walker/src/test/resources/test_mfpn_included3.xsd b/xmlschema-walker/src/test/resources/test_mfpn_included3.xsd
new file mode 100644
index 0000000..0a98076
--- /dev/null
+++ b/xmlschema-walker/src/test/resources/test_mfpn_included3.xsd
@@ -0,0 +1,29 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ 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. 
+ -->
+ <!--
+ This file is imported by test_mpfn_included1 which is in turn included by test_multiple_files_per_namespace.xsd 
+  -->
+<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">
+
+	<xs:complexType name="NoNS">
+		<xs:sequence>
+			<xs:element name="noNSElement" type="xs:string"/>
+		</xs:sequence>
+	</xs:complexType>
+
+</xs:schema>
diff --git a/xmlschema-walker/src/test/resources/test_multiple_files_per_namespace.xsd b/xmlschema-walker/src/test/resources/test_multiple_files_per_namespace.xsd
new file mode 100644
index 0000000..7ba23c9
--- /dev/null
+++ b/xmlschema-walker/src/test/resources/test_multiple_files_per_namespace.xsd
@@ -0,0 +1,38 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ 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. 
+ -->
+<xs:schema targetNamespace="http://avro.apache.org/AvroTest"
+	xmlns:xs="http://www.w3.org/2001/XMLSchema"
+	xmlns:avro="http://avro.apache.org/AvroTest">
+
+	<xs:include schemaLocation="test_mfpn_included1.xsd"/>
+
+	<xs:complexType name="BaseType">
+		<xs:sequence>
+			<xs:element name="baseElement" type="xs:string"/>
+			<xs:element name="includedType" type="avro:Included"/>
+		</xs:sequence>
+	</xs:complexType>
+
+	<xs:complexType name="Test">
+		<xs:complexContent>
+ 			<xs:extension base="avro:BaseType"/>
+		</xs:complexContent>
+	</xs:complexType>
+
+	<xs:element name="root" type="avro:Test"/>
+</xs:schema>
diff --git a/xmlschema-walker/src/test/resources/test_multiple_files_per_namespace2.xsd b/xmlschema-walker/src/test/resources/test_multiple_files_per_namespace2.xsd
new file mode 100644
index 0000000..5cc2bef
--- /dev/null
+++ b/xmlschema-walker/src/test/resources/test_multiple_files_per_namespace2.xsd
@@ -0,0 +1,94 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ 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. 
+ -->
+
+ <!--
+ This test distributes test_schema.xsd among three files, this one, test_mfpn2_included1.xsd
+ and test_mfpn2_included2.xsd 
+  -->
+<xsd:schema xmlns="http://www.w3.org/2001/XMLSchema" targetNamespace="http://avro.apache.org/AvroTest" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:avro="http://avro.apache.org/AvroTest">
+	<xsd:include schemaLocation="test_mfpn2_included1.xsd"/>
+	<xsd:include schemaLocation="test_mfpn2_included2.xsd"/>	
+
+	<xsd:attribute name="id">
+		<xsd:simpleType>
+			<xsd:restriction base="xsd:ID">
+				<xsd:minLength value="1" />
+			</xsd:restriction>
+		</xsd:simpleType>
+	</xsd:attribute>
+
+
+	<xsd:simpleType name="primitiveType">
+		<xsd:restriction base="xsd:NMTOKEN">
+			<xsd:enumeration value="null" />
+			<xsd:enumeration value="boolean" />
+			<xsd:enumeration value="int" />
+			<xsd:enumeration value="long" />
+			<xsd:enumeration value="float" />
+			<xsd:enumeration value="double" />
+			<xsd:enumeration value="decimal" />
+			<xsd:enumeration value="bytes" />
+			<xsd:enumeration value="string" />
+		</xsd:restriction>
+	</xsd:simpleType>
+
+	<xsd:element name="root">
+		<xsd:complexType>
+			<xsd:group ref="avro:group" />
+			<xsd:attributeGroup ref="avro:attrGroup" />
+		</xsd:complexType>
+	</xsd:element>
+	<xsd:element name="primitive" type="avro:primitiveType" />
+	<xsd:element name="nonNullPrimitive" type="avro:nonNullPrimitiveType" />
+
+	<xsd:element name="record" type="avro:recordType" />
+	<xsd:element name="map" substitutionGroup="avro:record">
+		<xsd:complexType>
+			<xsd:complexContent>
+				<xsd:extension base="avro:recordType">
+					<xsd:attribute ref="avro:id" use="required" />
+				</xsd:extension>
+			</xsd:complexContent>
+		</xsd:complexType>
+	</xsd:element>
+	<xsd:element name="list">
+		<xsd:complexType>
+			<xsd:choice>
+				<xsd:element ref="avro:primitive" minOccurs="1" maxOccurs="100" />
+				<xsd:element ref="avro:record"    minOccurs="1" maxOccurs="100" />
+			</xsd:choice>
+			<xsd:attribute ref="avro:size" />
+		</xsd:complexType>
+	</xsd:element>
+	<xsd:element name="tuple">
+		<xsd:complexType>
+			<xsd:group ref="avro:groupOfAll" />
+		</xsd:complexType>
+	</xsd:element>
+	<xsd:element name="nonNullRecord">
+		<xsd:complexType>
+			<xsd:complexContent>
+				<xsd:restriction base="avro:recordType">
+					<xsd:sequence>
+						<xsd:element ref="avro:nonNullPrimitive" />
+					</xsd:sequence>
+				</xsd:restriction>
+			</xsd:complexContent>
+		</xsd:complexType>
+	</xsd:element>
+</xsd:schema>