(DISTFILES): Comment out a few missing files.
[mono-project.git] / mcs / class / System.XML / System.Xml.Query / XQueryASTCompiler.cs
blob90651de30a2c1c879a75df0271888a7581d6d052
1 //
2 // XQueryASTCompiler.cs - XQuery static context compiler
3 //
4 // Author:
5 // Atsushi Enomoto <atsushi@ximian.com>
6 //
7 // Copyright (C) 2004 Novell, Inc (http://www.novell.com)
8 //
9 // Permission is hereby granted, free of charge, to any person obtaining
10 // a copy of this software and associated documentation files (the
11 // "Software"), to deal in the Software without restriction, including
12 // without limitation the rights to use, copy, modify, merge, publish,
13 // distribute, sublicense, and/or sell copies of the Software, and to
14 // permit persons to whom the Software is furnished to do so, subject to
15 // the following conditions:
16 //
17 // The above copyright notice and this permission notice shall be
18 // included in all copies or substantial portions of the Software.
19 //
20 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
21 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
22 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
23 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
24 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
25 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
26 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
29 #if NET_2_0
31 using System;
32 using System.Collections;
33 using System.Collections.Specialized;
34 using System.IO;
35 using System.Security.Policy;
36 using System.Xml;
37 using System.Xml.Query;
38 using System.Xml.Schema;
39 using Mono.Xml.XQuery;
40 using Mono.Xml.XQuery.Parser;
42 namespace Mono.Xml.XPath2
44 internal class XQueryASTCompiler
46 // Static method
48 public static XQueryStaticContext Compile (XQueryModule module, XQueryCompileOptions options, Evidence evidence, XQueryCommandImpl commandImpl)
50 if (options == null)
51 options = new XQueryCompileOptions ();
52 return new XQueryASTCompiler (module, options, new XQueryCompileContext (), evidence, commandImpl).Compile ();
55 // Constructor
57 private XQueryASTCompiler (XQueryModule module, XQueryCompileOptions options, XQueryCompileContext compileContext, Evidence evidence, XQueryCommandImpl commandImpl)
59 this.module = module;
60 this.options = options;
61 this.compileContext = compileContext;
62 this.evidence = evidence;
63 this.commandImpl = commandImpl;
65 inScopeSchemas = new XmlSchemaSet ();
66 localVariables = new Hashtable ();
67 localFunctions = new XQueryFunctionTable ();
70 XQueryModule module;
71 XQueryCompileOptions options;
72 XQueryCompileContext compileContext;
74 IXmlNamespaceResolver nsResolver;
75 string defaultFunctionNamespace;
77 // FIXME: Is it OK for an XmlSchema to be in two or more set?
78 XmlSchemaSet inScopeSchemas;
79 ArrayList libModuleContexts = new ArrayList ();
81 Hashtable localVariables;
82 XQueryFunctionTable localFunctions;
84 bool preserveWhitespace; // Xml space policy
85 bool constructionSpace; // construction mode
86 bool defaultOrdered; // Ordering mode
87 string baseUri;
88 Evidence evidence;
89 XQueryCommandImpl commandImpl;
91 // methods.
93 private XQueryStaticContext Compile ()
95 CompileProlog ();
97 XQueryMainModule main = module as XQueryMainModule;
98 ExprSequence expr = (main != null) ?
99 CompileExprSequence (main.QueryBody) : null;
101 return new XQueryStaticContext (
102 options,
103 compileContext,
104 expr,
105 inScopeSchemas,
106 localVariables,
107 localFunctions,
108 module.NSResolver,
109 module.Prolog.DefaultFunctionNamespace,
110 preserveWhitespace,
111 constructionSpace,
112 defaultOrdered,
113 baseUri,
114 evidence,
115 commandImpl);
118 private void CompileProlog ()
120 Prolog p = module.Prolog;
122 // resolve external modules
123 // FIXME: check if external queries are allowed by default.
124 // FIXME: check recursion
125 XmlUrlResolver res = new XmlUrlResolver ();
126 foreach (ModuleImport modimp in p.ModuleImports) {
127 foreach (string uri in modimp.Locations) {
128 Stream s = res.GetEntity (res.ResolveUri (null, uri), null, typeof (Stream)) as Stream;
129 XQueryLibraryModule ext = XQueryParser.Parse (new StreamReader (s)) as XQueryLibraryModule;
130 if (ext == null)
131 throw new XmlQueryCompileException (String.Format ("External module {0} is resolved as a main module, while it should be a library module."));
132 XQueryStaticContext sctx = new XQueryASTCompiler (ext, options, compileContext, evidence, commandImpl).Compile ();
133 libModuleContexts.Add (sctx);
137 // resolve and compile in-scope schemas
138 foreach (SchemaImport xsimp in p.SchemaImports) {
139 foreach (string uri in xsimp.Locations) {
140 XmlSchema schema = inScopeSchemas.Add (xsimp.Namespace, uri);
141 compileContext.InEffectSchemas.Add (schema);
144 inScopeSchemas.Compile ();
146 CheckReferences ();
148 ResolveVariableReferences ();
150 // compile FunctionDeclaration into XQueryFunction
151 foreach (FunctionDeclaration func in p.Functions.Values) {
152 XQueryFunction cfunc = CompileFunction (func);
153 localFunctions.Add (cfunc);
157 private void CheckReferences ()
159 XQueryMainModule main = module as XQueryMainModule;
160 if (main != null)
161 main.QueryBody.CheckReference (this);
162 foreach (FunctionDeclaration func in module.Prolog.Functions.Values) {
163 if (!func.External)
164 func.FunctionBody.CheckReference (this);
165 CheckSchemaType (func.ReturnType);
166 foreach (XQueryFunctionArgument param in func.Parameters)
167 CheckSchemaType (param.Type);
171 internal void CheckSchemaType (SequenceType type)
173 if (type == null)
174 return;
175 type.ItemType.CheckReference (this);
178 internal void CheckSchemaTypeName (XmlQualifiedName name)
180 XmlSchemaType type = XmlSchemaType.GetBuiltInType (name);
181 if (type != null)
182 return;
183 throw new XmlQueryCompileException (String.Format ("Unresolved schema type name: {0}", name));
186 internal void CheckVariableName (XmlQualifiedName name)
188 // This should not be done, since unresolved QName
189 // may be still valid in context of XmlArgumentList
190 // which is supplied at dynamic evaluation phase.
192 if (module.Prolog.Variables [name] != null)
193 return;
194 if (localVariables [name] != null)
195 return;
196 foreach (XQueryStaticContext ctx in libModuleContexts)
197 if (ctx.InScopeVariables [name] != null)
198 return;
199 throw new XmlQueryCompileException (String.Format ("Unresolved variable name: {0}", name));
203 internal void CheckFunctionName (XmlQualifiedName name)
205 if (XQueryFunction.FindKnownFunction (name) != null)
206 return;
207 if (module.Prolog.Functions [name] != null)
208 return;
209 foreach (XQueryStaticContext ctx in libModuleContexts)
210 if (ctx.InScopeFunctions [name] != null)
211 return;
212 throw new XmlQueryCompileException (String.Format ("Unresolved function name: {0}", name));
215 private void ResolveVariableReferences ()
217 // TODO
220 internal XmlSchemaType ResolveSchemaType (XmlQualifiedName name)
222 XmlSchemaType type = XmlSchemaType.GetBuiltInType (name);
223 if (type != null)
224 return type;
225 type = inScopeSchemas.GlobalTypes [name] as XmlSchemaType;
226 if (type != null)
227 return type;
228 return null;
231 private XQueryFunction CompileFunction (FunctionDeclaration func)
233 if (func.External)
234 return XQueryFunction.FromQName (func.Name);
235 return new XQueryUserFunction (func.Name, func.Parameters.ToArray (), func.FunctionBody.Expr, func.ReturnType);
238 private ExprSequence CompileExprSequence (ExprSequence expr)
240 for (int i = 0; i < expr.Count; i++)
241 expr [i] = expr [i].Compile (this);
242 return expr;
245 internal void CheckType (ExprSingle expr, SequenceType type)
247 if (!expr.StaticType.CanConvertTo (type))
248 throw new XmlQueryCompileException (String.Format ("Cannot convert type from {0} to {1}", expr.StaticType, type));
251 internal XQueryFunction ResolveFunction (XmlQualifiedName name)
253 XQueryFunction func = XQueryFunction.FindKnownFunction (name);
254 if (func == null)
255 func = localFunctions [name];
257 if (func != null)
258 return func;
259 else
260 throw new XmlQueryCompileException ("Could not find specified function.");
264 #endif