The Labs \ Source Viewer \ SSCLI \ System.Xml.Xsl.XsltOld \ ApplyTemplatesAction

  1. //------------------------------------------------------------------------------
  2. // <copyright file="ApplyTemplatesAction.cs" company="Microsoft">
  3. //
  4. // Copyright (c) 2006 Microsoft Corporation. All rights reserved.
  5. //
  6. // The use and distribution terms for this software are contained in the file
  7. // named license.txt, which can be found in the root of this distribution.
  8. // By using this software in any fashion, you are agreeing to be bound by the
  9. // terms of this license.
  10. //
  11. // You must not remove this notice, or any other, from this software.
  12. //
  13. // </copyright>
  14. //------------------------------------------------------------------------------
  15. namespace System.Xml.Xsl.XsltOld
  16. {
  17.     using Res = System.Xml.Utils.Res;
  18.     using System;
  19.     using System.Diagnostics;
  20.     using System.Collections;
  21.     using System.Xml;
  22.     using System.Xml.XPath;
  23.    
  24.     internal class ApplyTemplatesAction : ContainerAction
  25.     {
  26.         private const int ProcessedChildren = 2;
  27.         private const int ProcessNextNode = 3;
  28.         private const int PositionAdvanced = 4;
  29.         private const int TemplateProcessed = 5;
  30.        
  31.         private int selectKey = Compiler.InvalidQueryKey;
  32.         private XmlQualifiedName mode;
  33.        
  34.         //
  35.         // <xsl:template match="*|/" [mode="?"]>
  36.         // <xsl:apply-templates [mode="?"]/>
  37.         // </xsl:template>
  38.         //
  39.        
  40.         private static ApplyTemplatesAction s_BuiltInRule = new ApplyTemplatesAction();
  41.        
  42.         static internal ApplyTemplatesAction BuiltInRule()
  43.         {
  44.             Debug.Assert(s_BuiltInRule != null);
  45.             return s_BuiltInRule;
  46.         }
  47.        
  48.         static internal ApplyTemplatesAction BuiltInRule(XmlQualifiedName mode)
  49.         {
  50.             return (mode == null || mode.IsEmpty) ? BuiltInRule() : new ApplyTemplatesAction(mode);
  51.         }
  52.        
  53.         internal ApplyTemplatesAction()
  54.         {
  55.         }
  56.        
  57.         private ApplyTemplatesAction(XmlQualifiedName mode)
  58.         {
  59.             Debug.Assert(mode != null);
  60.             this.mode = mode;
  61.         }
  62.        
  63.         internal override void Compile(Compiler compiler)
  64.         {
  65.             CompileAttributes(compiler);
  66.             CompileContent(compiler);
  67.         }
  68.        
  69.         internal override bool CompileAttribute(Compiler compiler)
  70.         {
  71.             string name = compiler.Input.LocalName;
  72.             string value = compiler.Input.Value;
  73.             if (Keywords.Equals(name, compiler.Atoms.Select)) {
  74.                 this.selectKey = compiler.AddQuery(value);
  75.             }
  76.             else if (Keywords.Equals(name, compiler.Atoms.Mode)) {
  77.                 Debug.Assert(this.mode == null);
  78.                 if (compiler.AllowBuiltInMode && value == "*") {
  79.                     this.mode = Compiler.BuiltInMode;
  80.                 }
  81.                 else {
  82.                     this.mode = compiler.CreateXPathQName(value);
  83.                 }
  84.             }
  85.             else {
  86.                 return false;
  87.             }
  88.            
  89.             return true;
  90.         }
  91.        
  92.         private void CompileContent(Compiler compiler)
  93.         {
  94.             NavigatorInput input = compiler.Input;
  95.            
  96.             if (compiler.Recurse()) {
  97.                 do {
  98.                     switch (input.NodeType) {
  99.                         case XPathNodeType.Element:
  100.                             compiler.PushNamespaceScope();
  101.                             string nspace = input.NamespaceURI;
  102.                             string name = input.LocalName;
  103.                            
  104.                             if (Keywords.Equals(nspace, input.Atoms.XsltNamespace)) {
  105.                                 if (Keywords.Equals(name, input.Atoms.Sort)) {
  106.                                     AddAction(compiler.CreateSortAction());
  107.                                 }
  108.                                 else if (Keywords.Equals(name, input.Atoms.WithParam)) {
  109.                                     WithParamAction par = compiler.CreateWithParamAction();
  110.                                     CheckDuplicateParams(par.Name);
  111.                                     AddAction(par);
  112.                                 }
  113.                                 else {
  114.                                     throw compiler.UnexpectedKeyword();
  115.                                 }
  116.                             }
  117.                             else {
  118.                                 throw compiler.UnexpectedKeyword();
  119.                             }
  120.                             compiler.PopScope();
  121.                             break;
  122.                         case XPathNodeType.Comment:
  123.                         case XPathNodeType.ProcessingInstruction:
  124.                         case XPathNodeType.Whitespace:
  125.                         case XPathNodeType.SignificantWhitespace:
  126.                            
  127.                             break;
  128.                         default:
  129.                            
  130.                             throw XsltException.Create(Res.Xslt_InvalidContents, Keywords.s_ApplyTemplates);
  131.                             break;
  132.                     }
  133.                 }
  134.                 while (compiler.Advance());
  135.                
  136.                 compiler.ToParent();
  137.             }
  138.         }
  139.        
  140.         internal override void Execute(Processor processor, ActionFrame frame)
  141.         {
  142.             Debug.Assert(processor != null && frame != null);
  143.            
  144.             switch (frame.State) {
  145.                 case Initialized:
  146.                     processor.ResetParams();
  147.                     processor.InitSortArray();
  148.                     if (this.containedActions != null && this.containedActions.Count > 0) {
  149.                         processor.PushActionFrame(frame);
  150.                         frame.State = ProcessedChildren;
  151.                         break;
  152.                     }
  153.                     goto case ProcessedChildren;
  154.                     break;
  155.                 case ProcessedChildren:
  156.                     if (this.selectKey == Compiler.InvalidQueryKey) {
  157.                         if (!frame.Node.HasChildren) {
  158.                             frame.Finished();
  159.                             break;
  160.                         }
  161.                         frame.InitNewNodeSet(frame.Node.SelectChildren(XPathNodeType.All));
  162.                     }
  163.                     else {
  164.                         frame.InitNewNodeSet(processor.StartQuery(frame.NodeSet, this.selectKey));
  165.                     }
  166.                     if (processor.SortArray.Count != 0) {
  167.                         frame.SortNewNodeSet(processor, processor.SortArray);
  168.                     }
  169.                     frame.State = ProcessNextNode;
  170.                     goto case ProcessNextNode;
  171.                     break;
  172.                 case ProcessNextNode:
  173.                    
  174.                     Debug.Assert(frame.State == ProcessNextNode);
  175.                     Debug.Assert(frame.NewNodeSet != null);
  176.                    
  177.                     if (frame.NewNextNode(processor)) {
  178.                         frame.State = PositionAdvanced;
  179.                         goto case PositionAdvanced;
  180.                     }
  181.                     else {
  182.                         frame.Finished();
  183.                         break;
  184.                     }
  185.                     break;
  186.                 case PositionAdvanced:
  187.                    
  188.                     Debug.Assert(frame.State == PositionAdvanced);
  189.                    
  190.                         /*importsOf:*/                    processor.PushTemplateLookup(frame.NewNodeSet, this.mode, null);
  191.                    
  192.                     frame.State = TemplateProcessed;
  193.                     break;
  194.                 case TemplateProcessed:
  195.                    
  196.                     frame.State = ProcessNextNode;
  197.                     goto case ProcessNextNode;
  198.                     break;
  199.                 default:
  200.                    
  201.                     Debug.Fail("Invalid ApplyTemplatesAction execution state");
  202.                     break;
  203.             }
  204.         }
  205.     }
  206. }

Developer Fusion