New test.
[mono.git] / mcs / class / System.Web / System.Web.UI / TemplateParser.cs
old mode 100755 (executable)
new mode 100644 (file)
index ae3df72..c99f839
@@ -6,8 +6,7 @@
 //     Gonzalo Paniagua Javier (gonzalo@ximian.com)
 //
 // (C) 2002,2003 Ximian, Inc. (http://www.ximian.com)
-//
-
+// Copyright (C) 2005 Novell, Inc (http://www.novell.com)
 //
 // Permission is hereby granted, free of charge, to any person obtaining
 // a copy of this software and associated documentation files (the
 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 //
-using System;
+
 using System.CodeDom.Compiler;
 using System.Collections;
 using System.IO;
 using System.Reflection;
-using System.Web;
+using System.Security.Permissions;
 using System.Web.Compilation;
 using System.Web.Configuration;
 using System.Web.Util;
 
-namespace System.Web.UI
-{
+namespace System.Web.UI {
+
+       // CAS
+       [AspNetHostingPermission (SecurityAction.LinkDemand, Level = AspNetHostingPermissionLevel.Minimal)]
+       [AspNetHostingPermission (SecurityAction.InheritanceDemand, Level = AspNetHostingPermissionLevel.Minimal)]
        public abstract class TemplateParser : BaseParser
        {
                string inputFile;
@@ -65,9 +67,13 @@ namespace System.Web.UI
                string oc_header, oc_custom, oc_param, oc_controls;
                bool oc_shared;
                OutputCacheLocation oc_location;
+#if NET_2_0
+               string src;
+               string partialClassName;
+#endif
                Assembly srcAssembly;
                int appAssemblyIndex = -1;
-                
+
                internal TemplateParser ()
                {
                        imports = new ArrayList ();
@@ -86,10 +92,26 @@ namespace System.Web.UI
                        imports.Add ("System.Web.UI.HtmlControls");
 
                        assemblies = new ArrayList ();
+#if NET_2_0
+                       bool addAssembliesInBin = false;
+                       foreach (AssemblyInfo info in CompilationConfig.Assemblies) {
+                               if (info.Assembly == "*")
+                                       addAssembliesInBin = true;
+                               else
+                                       AddAssemblyByName (info.Assembly);
+                       }
+                       if (addAssembliesInBin)
+                               AddAssembliesInBin ();
+
+                       foreach (NamespaceInfo info in PagesConfig.Namespaces) {
+                               imports.Add (info.Namespace);
+                       }
+#else
                        foreach (string a in CompilationConfig.Assemblies)
                                AddAssemblyByName (a);
                        if (CompilationConfig.AssembliesInBin)
                                AddAssembliesInBin ();
+#endif
 
                        language = CompilationConfig.DefaultLanguage;
                }
@@ -324,7 +346,16 @@ namespace System.Web.UI
                        if (!imports.Contains (namesp))
                                imports.Add (namesp);
                }
-               
+
+               internal virtual void AddSourceDependency (string filename)
+               {
+                       if (dependencies != null && dependencies.Contains (filename)) {
+                               ThrowParseException ("Circular file references are not allowed. File: " + filename);
+                       }
+
+                       AddDependency (filename);
+               }
+
                internal virtual void AddDependency (string filename)
                {
                        if (filename == "")
@@ -363,6 +394,22 @@ namespace System.Web.UI
                        }
                }
 
+               internal virtual Assembly AddAssemblyByFileName (string filename)
+               {
+                       Assembly assembly = null;
+                       Exception error = null;
+
+                       try {
+                               assembly = Assembly.LoadFrom (filename);
+                       } catch (Exception e) { error = e; }
+
+                       if (assembly == null)
+                               ThrowParseException ("Assembly " + filename + " not found", error);
+
+                       AddAssembly (assembly, true);
+                       return assembly;
+               }
+
                internal virtual Assembly AddAssemblyByName (string name)
                {
                        if (anames == null)
@@ -377,18 +424,21 @@ namespace System.Web.UI
                        }
 
                        Assembly assembly = null;
-                       try {
-                               assembly = Assembly.Load (name);
-                       } catch (Exception) {
+                       Exception error = null;
+                       if (name.IndexOf (',') != -1) {
                                try {
-                                       assembly = Assembly.LoadWithPartialName (name);
-                               } catch (Exception e) {
-                                       ThrowParseException ("Assembly " + name + " not found", e);
-                               }
+                                       assembly = Assembly.Load (name);
+                               } catch (Exception e) { error = e; }
+                       }
 
-                               if (assembly == null)
-                                       ThrowParseException ("Assembly " + name + " not found", null);
+                       if (assembly == null) {
+                               try {
+                                       assembly = Assembly.LoadWithPartialName (name);
+                               } catch (Exception e) { error = e; }
                        }
+                       
+                       if (assembly == null)
+                               ThrowParseException ("Assembly " + name + " not found", error);
 
                        AddAssembly (assembly, true);
                        return assembly;
@@ -397,29 +447,65 @@ namespace System.Web.UI
                internal virtual void ProcessMainAttributes (Hashtable atts)
                {
                        atts.Remove ("Description"); // ignored
+#if NET_1_1
                        atts.Remove ("CodeBehind");  // ignored
-                       atts.Remove ("AspCompat"); // ignored
-
-#if NET_2_0
-                       atts.Remove ("CodeFile"); // ignored
 #endif
+                       atts.Remove ("AspCompat"); // ignored
 
                        debug = GetBool (atts, "Debug", true);
                        compilerOptions = GetString (atts, "CompilerOptions", "");
                        language = GetString (atts, "Language", CompilationConfig.DefaultLanguage);
                        strictOn = GetBool (atts, "Strict", CompilationConfig.Strict);
                        explicitOn = GetBool (atts, "Explicit", CompilationConfig.Explicit);
+
+                       string inherits = GetString (atts, "Inherits", null);
+#if NET_2_0
+                       // In ASP 2, the source file is actually integrated with
+                       // the generated file via the use of partial classes. This
+                       // means that the code file has to be confirmed, but not
+                       // used at this point.
+                       src = GetString (atts, "CodeFile", null);
+
+                       if (src != null && inherits != null) {
+                               // Make sure the source exists
+                               src = UrlUtils.Combine (BaseVirtualDir, src);
+                               string realPath = MapPath (src, false);
+                               if (!File.Exists (realPath))
+                                       ThrowParseException ("File " + src + " not found");
+
+                               // Verify that the inherits is a valid identify not a
+                               // fully-qualified name.
+                               if (!CodeGenerator.IsValidLanguageIndependentIdentifier (inherits))
+                                       ThrowParseException (String.Format ("'{0}' is not valid for 'inherits'", inherits));
+
+                               // We are going to create a partial class that shares
+                               // the same name as the inherits tag, so reset the
+                               // name. The base type is changed because it is the
+                               // code file's responsibilty to extend the classes
+                               // needed.
+                               partialClassName = inherits;
+
+                               // Add the code file as an option to the
+                               // compiler. This lets both files be compiled at once.
+                               compilerOptions += " \"" + realPath + "\"";
+                       } else if (inherits != null) {
+                               // We just set the inherits directly because this is a
+                               // Single-Page model.
+                               SetBaseType (inherits);
+                       }
+#else
                        string src = GetString (atts, "Src", null);
+
                        if (src != null)
                                srcAssembly = GetAssemblyFromSource (src);
 
-                       string inherits = GetString (atts, "Inherits", null);
                        if (inherits != null)
                                SetBaseType (inherits);
 
                        className = GetString (atts, "ClassName", null);
                        if (className != null && !CodeGenerator.IsValidLanguageIndependentIdentifier (className))
                                ThrowParseException (String.Format ("'{0}' is not valid for 'className'", className));
+#endif
 
                        if (atts.Count > 0)
                                ThrowParseException ("Unknown attribute: " + GetOneKey (atts));
@@ -453,7 +539,7 @@ namespace System.Web.UI
                        if (!File.Exists (realPath))
                                ThrowParseException ("File " + vpath + " not found");
 
-                       AddDependency (realPath);
+                       AddSourceDependency (realPath);
 
                        CompilerResults result = CachingCompiler.Compile (language, realPath, realPath, assemblies);
                        if (result.NativeCompilerReturnValue != 0) {
@@ -475,6 +561,18 @@ namespace System.Web.UI
                        set { inputFile = value; }
                }
 
+#if NET_2_0
+               internal bool IsPartial
+               {
+                       get { return src != null; }
+               }
+
+               internal string PartialClassName
+               {
+                       get { return partialClassName; }
+               }
+#endif
+
                internal string Text
                {
                        get { return text; }
@@ -557,6 +655,7 @@ namespace System.Web.UI
 
                internal ArrayList Dependencies {
                        get { return dependencies; }
+                       set { dependencies = value; }
                }
 
                internal string CompilerOptions {
@@ -611,9 +710,17 @@ namespace System.Web.UI
                        get { return oc_param; }
                }
 
+#if NET_2_0
+               internal PagesSection PagesConfig {
+                       get {
+                               return WebConfigurationManager.GetSection ("system.web/pages") as PagesSection;
+                       }
+               }
+#else
                internal PagesConfiguration PagesConfig {
                        get { return PagesConfiguration.GetInstance (Context); }
                }
+#endif
        }
 }