// <summary>
        // The real driver.
        // </summary>
        // <param name="providerCommands"> list of provider commands </param>
        // <param name="resultColumnMap"> column map for the result </param>
        // <param name="entitySets"> the entity sets exposed in this query </param>
        private void Compile(
            out List <ProviderCommandInfo> providerCommands, out ColumnMap resultColumnMap, out int columnCount,
            out Set <md.EntitySet> entitySets)
        {
            Initialize(); // initialize the ITree

            var beforePreProcessor      = String.Empty;
            var beforeAggregatePushdown = String.Empty;
            var beforeNormalization     = String.Empty;
            var beforeNTE = String.Empty;
            var beforeProjectionPruning1   = String.Empty;
            var beforeNestPullup           = String.Empty;
            var beforeProjectionPruning2   = String.Empty;
            var beforeTransformationRules1 = String.Empty;
            var beforeProjectionPruning3   = String.Empty;
            var beforeTransformationRules2 = String.Empty;
            var beforeJoinElimination1     = String.Empty;
            var beforeTransformationRules3 = String.Empty;
            var beforeJoinElimination2     = String.Empty;
            var beforeTransformationRules4 = String.Empty;
            var beforeNullSemantics        = String.Empty;
            var beforeTransformationRules5 = String.Empty;
            var beforeCodeGen = String.Empty;

            //
            // We always need the pre-processor and the codegen phases.
            // It is generally a good thing to run through the transformation rules, and
            // the projection pruning phases.
            // The "optional" phases are AggregatePushdown, Normalization, NTE, NestPullup and JoinElimination
            //
            m_neededPhases = (1 << (int)PlanCompilerPhase.PreProcessor) |
                             // (1 << (int)PlanCompilerPhase.AggregatePushdown) |
                             // (1 << (int)PlanCompilerPhase.Normalization) |
                             // (1 << (int)PlanCompilerPhase.NTE) |
                             (1 << (int)PlanCompilerPhase.ProjectionPruning) |
                             // (1 << (int)PlanCompilerPhase.NestPullup) |
                             (1 << (int)PlanCompilerPhase.Transformations) |
                             // (1 << (int)PlanCompilerPhase.JoinElimination) |
                             // (1 << (int)PlanCompilerPhase.NullSemantics) |
                             (1 << (int)PlanCompilerPhase.CodeGen);

            // Perform any necessary preprocessing
            StructuredTypeInfo typeInfo;
            Dictionary <md.EdmFunction, md.EdmProperty[]> tvfResultKeys;

            beforePreProcessor = SwitchToPhase(PlanCompilerPhase.PreProcessor);
            PreProcessor.Process(this, out typeInfo, out tvfResultKeys);
            entitySets = typeInfo.GetEntitySets();

            if (IsPhaseNeeded(PlanCompilerPhase.AggregatePushdown))
            {
                beforeAggregatePushdown = SwitchToPhase(PlanCompilerPhase.AggregatePushdown);
                AggregatePushdown.Process(this);
            }

            if (IsPhaseNeeded(PlanCompilerPhase.Normalization))
            {
                beforeNormalization = SwitchToPhase(PlanCompilerPhase.Normalization);
                Normalizer.Process(this);
            }

            // Eliminate "structured" types.
            if (IsPhaseNeeded(PlanCompilerPhase.NTE))
            {
                beforeNTE = SwitchToPhase(PlanCompilerPhase.NTE);
                NominalTypeEliminator.Process(this, typeInfo, tvfResultKeys);
            }

            // Projection pruning - eliminate unreferenced expressions
            if (IsPhaseNeeded(PlanCompilerPhase.ProjectionPruning))
            {
                beforeProjectionPruning1 = SwitchToPhase(PlanCompilerPhase.ProjectionPruning);
                ProjectionPruner.Process(this);
            }

            // Nest Pull-up on the ITree
            if (IsPhaseNeeded(PlanCompilerPhase.NestPullup))
            {
                beforeNestPullup = SwitchToPhase(PlanCompilerPhase.NestPullup);

                NestPullup.Process(this);

                //If we do Nest Pull-up, we should again do projection pruning
                beforeProjectionPruning2 = SwitchToPhase(PlanCompilerPhase.ProjectionPruning);
                ProjectionPruner.Process(this);
            }

            // Run transformations on the tree
            if (IsPhaseNeeded(PlanCompilerPhase.Transformations))
            {
                var projectionPrunningNeeded = ApplyTransformations(ref beforeTransformationRules1, TransformationRulesGroup.All);

                if (projectionPrunningNeeded)
                {
                    beforeProjectionPruning3 = SwitchToPhase(PlanCompilerPhase.ProjectionPruning);
                    ProjectionPruner.Process(this);
                    ApplyTransformations(ref beforeTransformationRules2, TransformationRulesGroup.Project);
                }
            }

            // Join elimination
            if (IsPhaseNeeded(PlanCompilerPhase.JoinElimination))
            {
                beforeJoinElimination1 = SwitchToPhase(PlanCompilerPhase.JoinElimination);
                var modified = JoinElimination.Process(this);
                if (modified)
                {
                    ApplyTransformations(ref beforeTransformationRules3, TransformationRulesGroup.PostJoinElimination);
                    beforeJoinElimination2 = SwitchToPhase(PlanCompilerPhase.JoinElimination);
                    modified = JoinElimination.Process(this);
                    if (modified)
                    {
                        ApplyTransformations(ref beforeTransformationRules4, TransformationRulesGroup.PostJoinElimination);
                    }
                }
            }

            if (IsPhaseNeeded(PlanCompilerPhase.NullSemantics) &&
                !m_ctree.UseDatabaseNullSemantics)
            {
                beforeNullSemantics = SwitchToPhase(PlanCompilerPhase.NullSemantics);

                if (NullSemantics.Process(Command))
                {
                    ApplyTransformations(ref beforeTransformationRules5, TransformationRulesGroup.NullSemantics);
                }
            }

            // Code generation
            beforeCodeGen = SwitchToPhase(PlanCompilerPhase.CodeGen);
            CodeGen.Process(this, out providerCommands, out resultColumnMap, out columnCount);

#if DEBUG
            // GC.KeepAlive makes FxCop Grumpy.
            var size = beforePreProcessor.Length;
            size = beforeAggregatePushdown.Length;
            size = beforeNormalization.Length;
            size = beforeNTE.Length;
            size = beforeProjectionPruning1.Length;
            size = beforeNestPullup.Length;
            size = beforeProjectionPruning2.Length;
            size = beforeTransformationRules1.Length;
            size = beforeProjectionPruning3.Length;
            size = beforeTransformationRules2.Length;
            size = beforeJoinElimination1.Length;
            size = beforeTransformationRules3.Length;
            size = beforeJoinElimination2.Length;
            size = beforeTransformationRules4.Length;
            size = beforeNullSemantics.Length;
            size = beforeTransformationRules5.Length;
            size = beforeCodeGen.Length;
#endif
        }
Ejemplo n.º 2
0
        private void Compile(
            out List <ProviderCommandInfo> providerCommands,
            out ColumnMap resultColumnMap,
            out int columnCount,
            out Set <EntitySet> entitySets)
        {
            this.Initialize();
            string empty1  = string.Empty;
            string empty2  = string.Empty;
            string empty3  = string.Empty;
            string empty4  = string.Empty;
            string empty5  = string.Empty;
            string empty6  = string.Empty;
            string empty7  = string.Empty;
            string empty8  = string.Empty;
            string empty9  = string.Empty;
            string empty10 = string.Empty;
            string empty11 = string.Empty;
            string empty12 = string.Empty;
            string empty13 = string.Empty;
            string empty14 = string.Empty;
            string empty15 = string.Empty;

            this.m_neededPhases = 593;
            this.SwitchToPhase(PlanCompilerPhase.PreProcessor);
            StructuredTypeInfo typeInfo;
            Dictionary <EdmFunction, EdmProperty[]> tvfResultKeys;

            PreProcessor.Process(this, out typeInfo, out tvfResultKeys);
            entitySets = typeInfo.GetEntitySets();
            if (this.IsPhaseNeeded(PlanCompilerPhase.AggregatePushdown))
            {
                this.SwitchToPhase(PlanCompilerPhase.AggregatePushdown);
                AggregatePushdown.Process(this);
            }
            if (this.IsPhaseNeeded(PlanCompilerPhase.Normalization))
            {
                this.SwitchToPhase(PlanCompilerPhase.Normalization);
                Normalizer.Process(this);
            }
            if (this.IsPhaseNeeded(PlanCompilerPhase.NTE))
            {
                this.SwitchToPhase(PlanCompilerPhase.NTE);
                NominalTypeEliminator.Process(this, typeInfo, tvfResultKeys);
            }
            if (this.IsPhaseNeeded(PlanCompilerPhase.ProjectionPruning))
            {
                this.SwitchToPhase(PlanCompilerPhase.ProjectionPruning);
                ProjectionPruner.Process(this);
            }
            if (this.IsPhaseNeeded(PlanCompilerPhase.NestPullup))
            {
                this.SwitchToPhase(PlanCompilerPhase.NestPullup);
                NestPullup.Process(this);
                this.SwitchToPhase(PlanCompilerPhase.ProjectionPruning);
                ProjectionPruner.Process(this);
            }
            if (this.IsPhaseNeeded(PlanCompilerPhase.Transformations) && this.ApplyTransformations(ref empty8, TransformationRulesGroup.All))
            {
                this.SwitchToPhase(PlanCompilerPhase.ProjectionPruning);
                ProjectionPruner.Process(this);
                this.ApplyTransformations(ref empty10, TransformationRulesGroup.Project);
            }
            if (this.IsPhaseNeeded(PlanCompilerPhase.NullSemantics))
            {
                this.SwitchToPhase(PlanCompilerPhase.NullSemantics);
                if (!this.m_ctree.UseDatabaseNullSemantics && NullSemantics.Process(this.Command))
                {
                    this.ApplyTransformations(ref empty12, TransformationRulesGroup.NullSemantics);
                }
            }
            if (this.IsPhaseNeeded(PlanCompilerPhase.JoinElimination))
            {
                for (int index = 0; index < 10; ++index)
                {
                    this.SwitchToPhase(PlanCompilerPhase.JoinElimination);
                    if (JoinElimination.Process(this) || this.TransformationsDeferred)
                    {
                        this.TransformationsDeferred = false;
                        this.ApplyTransformations(ref empty14, TransformationRulesGroup.PostJoinElimination);
                    }
                    else
                    {
                        break;
                    }
                }
            }
            this.SwitchToPhase(PlanCompilerPhase.CodeGen);
            CodeGen.Process(this, out providerCommands, out resultColumnMap, out columnCount);
        }