Author: mhabersack
Date: 2008-02-05 17:59:46 -0500 (Tue, 05 Feb 2008)
New Revision: 94968

Modified:
   trunk/mcs/class/System.Web/System.Web.Compilation/BuildManager.cs
   trunk/mcs/class/System.Web/System.Web.Compilation/ChangeLog
Log:
2008-02-06  Marek Habersack  <[EMAIL PROTECTED]>

        * BuildManager.cs: protect non-page builds from endless recursion
        if a non-page file recursively references/includes another file
        from the same batch. If such case is detected, the recursively
        referenced file is compiled into a separate assembly and removed
        from the previous compilation batch. Fixes bug #358742.


Modified: trunk/mcs/class/System.Web/System.Web.Compilation/BuildManager.cs
===================================================================
--- trunk/mcs/class/System.Web/System.Web.Compilation/BuildManager.cs   
2008-02-05 22:48:07 UTC (rev 94967)
+++ trunk/mcs/class/System.Web/System.Web.Compilation/BuildManager.cs   
2008-02-05 22:59:46 UTC (rev 94968)
@@ -209,6 +209,8 @@
                
                static object buildCacheLock = new object ();
 
+               static Stack <BuildKind> recursiveBuilds = new Stack 
<BuildKind> ();
+               
                //
                // Disabled - see comment at the end of BuildAssembly below
                //
@@ -474,8 +476,16 @@
 
                        if (kind == BuildKind.Theme || kind == 
BuildKind.Application)
                                return ret;
+                       
+                       bool doBatch = BatchMode;
 
-                       if (BatchMode) {
+                       lock (buildCacheLock) {
+                               if (recursiveBuilds.Count > 0 && 
recursiveBuilds.Peek () == kind)
+                                       doBatch = false;
+                               recursiveBuilds.Push (kind);
+                       }
+                       
+                       if (doBatch) {
                                string[] files = Directory.GetFiles 
(physicalDir, "*.*");
                                BuildKind fileKind;
                        
@@ -770,6 +780,8 @@
                        object ticket;
                        bool acquired;
                        string virtualDir = GetVirtualPathDirectory 
(virtualPath);
+                       BuildKind buildKind = BuildKind.Unknown;
+                       bool kindPushed = false;
                        
                        acquired = AcquireCompilationTicket (virtualDir, out 
ticket);
                        try {
@@ -781,17 +793,29 @@
                                
                                string assemblyBaseName;
                                Dictionary <string, bool> vpCache = new 
Dictionary <string, bool> ();
-                               BuildKind buildKind;
                                List <BuildItem> buildItems = 
LoadBuildProviders (virtualPath, virtualDir, vpCache, out buildKind, out 
assemblyBaseName);
+                               kindPushed = true;
                                
                                if (buildItems.Count == 0)
                                        return;
                                
                                Dictionary <Type, List <AssemblyBuilder>> 
assemblyBuilders = new Dictionary <Type, List <AssemblyBuilder>> ();
-                               foreach (BuildItem buildItem in buildItems)
+                               bool checkForRecursion = buildKind == 
BuildKind.NonPages;
+                               
+                               foreach (BuildItem buildItem in buildItems) {
+                                       if (checkForRecursion) {
+                                               // Expensive but, alas, 
necessary - the builder in
+                                               // our list might've been put 
into a different
+                                               // assembly in a recursive call.
+                                               lock (buildCacheLock) {
+                                                       if 
(buildCache.ContainsKey (buildItem.VirtualPath))
+                                                               continue;
+                                               }
+                                       }
+                                       
                                        if (buildItem.assemblyBuilder == null)
                                                AssignToAssemblyBuilder 
(assemblyBaseName, virtualPath, buildItem, assemblyBuilders);
-
+                               }
                                CompilerResults results;
                                Assembly compiledAssembly;
                                string vp;
@@ -844,6 +868,12 @@
 //                                             HttpRuntime.UnloadAppDomain ();
 //                             }
                        } finally {
+                               if (kindPushed && buildKind == BuildKind.Pages 
|| buildKind == BuildKind.NonPages) {
+                                       lock (buildCacheLock) {
+                                               recursiveBuilds.Pop ();
+                                       }
+                               }
+                               
                                Monitor.Exit (ticket);
                                if (acquired)
                                        ReleaseCompilationTicket (virtualDir);

Modified: trunk/mcs/class/System.Web/System.Web.Compilation/ChangeLog
===================================================================
--- trunk/mcs/class/System.Web/System.Web.Compilation/ChangeLog 2008-02-05 
22:48:07 UTC (rev 94967)
+++ trunk/mcs/class/System.Web/System.Web.Compilation/ChangeLog 2008-02-05 
22:59:46 UTC (rev 94968)
@@ -1,3 +1,11 @@
+2008-02-06  Marek Habersack  <[EMAIL PROTECTED]>
+
+       * BuildManager.cs: protect non-page builds from endless recursion
+       if a non-page file recursively references/includes another file
+       from the same batch. If such case is detected, the recursively
+       referenced file is compiled into a separate assembly and removed
+       from the previous compilation batch. Fixes bug #358742.
+
 2008-02-05  Marek Habersack  <[EMAIL PROTECTED]>
 
        * BuildManager.cs: GetAbsoluteVirtualPath correctly converts

_______________________________________________
Mono-patches maillist  -  [email protected]
http://lists.ximian.com/mailman/listinfo/mono-patches

Reply via email to