private static bool ProcessOuterApplyOverProject(
            RuleProcessingContext context,
            System.Data.Entity.Core.Query.InternalTrees.Node applyNode,
            out System.Data.Entity.Core.Query.InternalTrees.Node newNode)
        {
            newNode = applyNode;
            System.Data.Entity.Core.Query.InternalTrees.Node child1_1 = applyNode.Child1;
            System.Data.Entity.Core.Query.InternalTrees.Node child1_2 = child1_1.Child1;
            TransformationRulesContext transformationRulesContext     = (TransformationRulesContext)context;
            Var computedVar = context.Command.GetExtendedNodeInfo(child1_1.Child0).NonNullableDefinitions.First;

            if (computedVar == null && child1_2.Children.Count == 1 && (child1_2.Child0.Child0.Op.OpType == OpType.InternalConstant || child1_2.Child0.Child0.Op.OpType == OpType.NullSentinel))
            {
                return(false);
            }
            Command command = context.Command;

            System.Data.Entity.Core.Query.InternalTrees.Node node1 = (System.Data.Entity.Core.Query.InternalTrees.Node)null;
            InternalConstantOp internalConstantOp = (InternalConstantOp)null;
            ExtendedNodeInfo   extendedNodeInfo1  = command.GetExtendedNodeInfo(child1_1.Child0);
            bool flag = false;

            foreach (System.Data.Entity.Core.Query.InternalTrees.Node child in child1_2.Children)
            {
                System.Data.Entity.Core.Query.PlanCompiler.PlanCompiler.Assert(child.Op.OpType == OpType.VarDef, "Expected VarDefOp. Found " + (object)child.Op.OpType + " instead");
                VarRefOp op = child.Child0.Op as VarRefOp;
                if (op == null || !extendedNodeInfo1.Definitions.IsSet(op.Var))
                {
                    if (computedVar == null)
                    {
                        internalConstantOp = command.CreateInternalConstantOp(command.IntegerType, (object)1);
                        System.Data.Entity.Core.Query.InternalTrees.Node node2          = command.CreateNode((Op)internalConstantOp);
                        System.Data.Entity.Core.Query.InternalTrees.Node varDefListNode = command.CreateVarDefListNode(node2, out computedVar);
                        ProjectOp projectOp = command.CreateProjectOp(computedVar);
                        projectOp.Outputs.Or(extendedNodeInfo1.Definitions);
                        node1 = command.CreateNode((Op)projectOp, child1_1.Child0, varDefListNode);
                    }
                    System.Data.Entity.Core.Query.InternalTrees.Node node3 = internalConstantOp == null || !internalConstantOp.IsEquivalent(child.Child0.Op) && child.Child0.Op.OpType != OpType.NullSentinel ? transformationRulesContext.BuildNullIfExpression(computedVar, child.Child0) : command.CreateNode((Op)command.CreateVarRefOp(computedVar));
                    child.Child0 = node3;
                    command.RecomputeNodeInfo(child);
                    flag = true;
                }
            }
            if (flag)
            {
                command.RecomputeNodeInfo(child1_2);
            }
            applyNode.Child1 = node1 ?? child1_1.Child0;
            command.RecomputeNodeInfo(applyNode);
            child1_1.Child0 = applyNode;
            ExtendedNodeInfo extendedNodeInfo2 = command.GetExtendedNodeInfo(applyNode.Child0);

            ((ProjectOp)child1_1.Op).Outputs.Or(extendedNodeInfo2.Definitions);
            newNode = child1_1;
            return(true);
        }
Example #2
0
 public override System.Data.Entity.Core.Query.InternalTrees.Node Visit(ProjectOp op, System.Data.Entity.Core.Query.InternalTrees.Node n)
 {
     this.PruneVarSet(op.Outputs);
     this.VisitChildrenReverse(n);
     if (!op.Outputs.IsEmpty)
     {
         return(n);
     }
     return(n.Child0);
 }
Example #3
0
        private static bool ProcessProjectWithSimpleVarRedefinitions(
            RuleProcessingContext context,
            System.Data.Entity.Core.Query.InternalTrees.Node n,
            out System.Data.Entity.Core.Query.InternalTrees.Node newNode)
        {
            newNode = n;
            ProjectOp op1 = (ProjectOp)n.Op;

            if (n.Child1.Children.Count == 0)
            {
                return(false);
            }
            TransformationRulesContext transformationRulesContext = (TransformationRulesContext)context;
            Command          command          = transformationRulesContext.Command;
            ExtendedNodeInfo extendedNodeInfo = command.GetExtendedNodeInfo(n);
            bool             flag             = false;

            foreach (System.Data.Entity.Core.Query.InternalTrees.Node child in n.Child1.Children)
            {
                System.Data.Entity.Core.Query.InternalTrees.Node child0 = child.Child0;
                if (child0.Op.OpType == OpType.VarRef)
                {
                    VarRefOp op2 = (VarRefOp)child0.Op;
                    if (!extendedNodeInfo.ExternalReferences.IsSet(op2.Var))
                    {
                        flag = true;
                        break;
                    }
                }
            }
            if (!flag)
            {
                return(false);
            }
            List <System.Data.Entity.Core.Query.InternalTrees.Node> args = new List <System.Data.Entity.Core.Query.InternalTrees.Node>();

            foreach (System.Data.Entity.Core.Query.InternalTrees.Node child in n.Child1.Children)
            {
                VarDefOp op2 = (VarDefOp)child.Op;
                VarRefOp op3 = child.Child0.Op as VarRefOp;
                if (op3 != null && !extendedNodeInfo.ExternalReferences.IsSet(op3.Var))
                {
                    op1.Outputs.Clear(op2.Var);
                    op1.Outputs.Set(op3.Var);
                    transformationRulesContext.AddVarMapping(op2.Var, op3.Var);
                }
                else
                {
                    args.Add(child);
                }
            }
            System.Data.Entity.Core.Query.InternalTrees.Node node = command.CreateNode((Op)command.CreateVarDefListOp(), args);
            n.Child1 = node;
            return(true);
        }
Example #4
0
        /// <summary>
        /// ExistsOp
        ///
        /// The child must be a ProjectOp - with exactly 1 var. Mark it as referenced
        /// </summary>
        /// <param name="op">the ExistsOp</param>
        /// <param name="n">the input node</param>
        /// <returns></returns>
        public override Node Visit(ExistsOp op, Node n)
        {
            // Ensure that the child is a projectOp, and has exactly one var. Mark
            // that var as referenced always
            ProjectOp projectOp = (ProjectOp)n.Child0.Op;

            //It is enougth to reference the first output, this usually is a simple constant
            AddReference(projectOp.Outputs.First);

            VisitChildren(n);
            return(n);
        }
        /// <summary>
        ///     ProjectOp
        ///     We visit the projections first (the VarDefListOp child), and then
        ///     the input (the RelOp child) - this reverse order is necessary, since
        ///     the projections need to be visited to determine if anything from
        ///     the input is really needed.
        ///     The VarDefListOp child will handle the removal of unnecessary VarDefOps.
        ///     On the way out, we then update our "Vars" property to reflect the Vars
        ///     that have been eliminated
        /// </summary>
        /// <param name="op"> the ProjectOp </param>
        /// <param name="n"> the current node </param>
        /// <returns> modified subtree </returns>
        public override Node Visit(ProjectOp op, Node n)
        {
            // Update my Vars - to remove "unreferenced" vars. Do this before visiting
            // the children - the outputs of the ProjectOp are only consumed by upstream
            // consumers, and if a Var has not yet been referenced, its not needed upstream
            PruneVarSet(op.Outputs);

            // first visit the computed expressions, then visit the input relop
            VisitChildrenReverse(n);

            // If there are no Vars left, then simply return my child - otherwise,
            // return the current node
            return(op.Outputs.IsEmpty ? n.Child0 : n);
        }
Example #6
0
        public override void Visit(ProjectOp op, System.Data.Entity.Core.Query.InternalTrees.Node n)
        {
            this.VisitChildren(n);
            ExtendedNodeInfo extendedNodeInfo = n.Child0.GetExtendedNodeInfo(this.m_command);

            if (!extendedNodeInfo.Keys.NoKeys)
            {
                VarVec varVec = this.m_command.CreateVarVec(op.Outputs);
                Dictionary <Var, Var> varRemappings = NodeInfoVisitor.ComputeVarRemappings(n.Child1);
                VarVec other = extendedNodeInfo.Keys.KeyVars.Remap(varRemappings);
                varVec.Or(other);
                op.Outputs.InitFrom(varVec);
            }
            this.m_command.RecomputeNodeInfo(n);
        }
Example #7
0
        private static bool ProcessProjectOverProject(
            RuleProcessingContext context,
            System.Data.Entity.Core.Query.InternalTrees.Node projectNode,
            out System.Data.Entity.Core.Query.InternalTrees.Node newNode)
        {
            newNode = projectNode;
            ProjectOp op1 = (ProjectOp)projectNode.Op;

            System.Data.Entity.Core.Query.InternalTrees.Node child1 = projectNode.Child1;
            System.Data.Entity.Core.Query.InternalTrees.Node child0 = projectNode.Child0;
            ProjectOp op2 = (ProjectOp)child0.Op;
            TransformationRulesContext transformationRulesContext = (TransformationRulesContext)context;
            Dictionary <Var, int>      varRefMap = new Dictionary <Var, int>();

            foreach (System.Data.Entity.Core.Query.InternalTrees.Node child in child1.Children)
            {
                if (!transformationRulesContext.IsScalarOpTree(child.Child0, varRefMap))
                {
                    return(false);
                }
            }
            Dictionary <Var, System.Data.Entity.Core.Query.InternalTrees.Node> varMap = transformationRulesContext.GetVarMap(child0.Child1, varRefMap);

            if (varMap == null)
            {
                return(false);
            }
            System.Data.Entity.Core.Query.InternalTrees.Node node = transformationRulesContext.Command.CreateNode((Op)transformationRulesContext.Command.CreateVarDefListOp());
            foreach (System.Data.Entity.Core.Query.InternalTrees.Node child in child1.Children)
            {
                child.Child0 = transformationRulesContext.ReMap(child.Child0, varMap);
                transformationRulesContext.Command.RecomputeNodeInfo(child);
                node.Children.Add(child);
            }
            ExtendedNodeInfo extendedNodeInfo = transformationRulesContext.Command.GetExtendedNodeInfo(projectNode);

            foreach (System.Data.Entity.Core.Query.InternalTrees.Node child in child0.Child1.Children)
            {
                VarDefOp op3 = (VarDefOp)child.Op;
                if (extendedNodeInfo.Definitions.IsSet(op3.Var))
                {
                    node.Children.Add(child);
                }
            }
            projectNode.Child0 = child0.Child0;
            projectNode.Child1 = node;
            return(true);
        }
Example #8
0
        /// <summary>
        /// Pulls up keys for a ProjectOp. First visits its children to pull
        /// up its keys; then identifies any keys from the input that it may have
        /// projected out - and adds them to the output list of vars
        /// </summary>
        /// <param name="op">Current ProjectOp</param>
        /// <param name="n">Current subtree</param>
        public override void Visit(ProjectOp op, Node n)
        {
            VisitChildren(n);

            ExtendedNodeInfo childNodeInfo = n.Child0.GetExtendedNodeInfo(m_command);

            if (!childNodeInfo.Keys.NoKeys)
            {
                VarVec outputVars = m_command.CreateVarVec(op.Outputs);
                // NOTE: This code appears in NodeInfoVisitor as well. Try to see if we
                //       can share this somehow.
                Dictionary <Var, Var> varRenameMap = NodeInfoVisitor.ComputeVarRemappings(n.Child1);
                VarVec mappedKeyVec = childNodeInfo.Keys.KeyVars.Remap(varRenameMap);
                outputVars.Or(mappedKeyVec);
                op.Outputs.InitFrom(outputVars);
            }
            m_command.RecomputeNodeInfo(n);
        }
Example #9
0
        private static bool ProcessGroupByOpWithNoAggregates(
            RuleProcessingContext context,
            System.Data.Entity.Core.Query.InternalTrees.Node n,
            out System.Data.Entity.Core.Query.InternalTrees.Node newNode)
        {
            Command          command          = context.Command;
            GroupByOp        op               = (GroupByOp)n.Op;
            ExtendedNodeInfo extendedNodeInfo = command.GetExtendedNodeInfo(n.Child0);
            ProjectOp        projectOp        = command.CreateProjectOp(op.Keys);
            VarDefListOp     varDefListOp     = command.CreateVarDefListOp();

            command.CreateNode((Op)varDefListOp);
            newNode = command.CreateNode((Op)projectOp, n.Child0, n.Child1);
            if (extendedNodeInfo.Keys.NoKeys || !op.Keys.Subsumes(extendedNodeInfo.Keys.KeyVars))
            {
                newNode = command.CreateNode((Op)command.CreateDistinctOp(command.CreateVarVec(op.Keys)), newNode);
            }
            return(true);
        }
Example #10
0
        private static bool ProcessDistinctOpOfKeys(
            RuleProcessingContext context,
            Node n,
            out Node newNode)
        {
            Command          command          = context.Command;
            ExtendedNodeInfo extendedNodeInfo = command.GetExtendedNodeInfo(n.Child0);
            DistinctOp       op = (DistinctOp)n.Op;

            if (!extendedNodeInfo.Keys.NoKeys && op.Keys.Subsumes(extendedNodeInfo.Keys.KeyVars))
            {
                ProjectOp    projectOp    = command.CreateProjectOp(op.Keys);
                VarDefListOp varDefListOp = command.CreateVarDefListOp();
                Node         node         = command.CreateNode((Op)varDefListOp);
                newNode = command.CreateNode((Op)projectOp, n.Child0, node);
                return(true);
            }
            newNode = n;
            return(false);
        }
        private static bool ProcessCrossApplyOverProject(
            RuleProcessingContext context,
            System.Data.Entity.Core.Query.InternalTrees.Node applyNode,
            out System.Data.Entity.Core.Query.InternalTrees.Node newNode)
        {
            newNode = applyNode;
            System.Data.Entity.Core.Query.InternalTrees.Node child1 = applyNode.Child1;
            ProjectOp        op               = (ProjectOp)child1.Op;
            Command          command          = context.Command;
            ExtendedNodeInfo extendedNodeInfo = command.GetExtendedNodeInfo(applyNode);
            VarVec           varVec           = command.CreateVarVec(op.Outputs);

            varVec.Or(extendedNodeInfo.Definitions);
            op.Outputs.InitFrom(varVec);
            applyNode.Child1 = child1.Child0;
            context.Command.RecomputeNodeInfo(applyNode);
            child1.Child0 = applyNode;
            newNode       = child1;
            return(true);
        }
Example #12
0
        internal System.Data.Entity.Core.Query.InternalTrees.Node GetInternalTree(
            Command targetIqtCommand,
            IList <System.Data.Entity.Core.Query.InternalTrees.Node> targetIqtArguments)
        {
            if (this.m_internalTreeNode == null)
            {
                DiscriminatorMap discriminatorMap;
                Command          command = ITreeGenerator.Generate(this.GenerateFunctionView(out discriminatorMap), discriminatorMap);
                System.Data.Entity.Core.Query.InternalTrees.Node root = command.Root;
                System.Data.Entity.Core.Query.PlanCompiler.PlanCompiler.Assert(root.Op.OpType == OpType.PhysicalProject, "Expected a physical projectOp at the root of the tree - found " + (object)root.Op.OpType);
                PhysicalProjectOp op = (PhysicalProjectOp)root.Op;
                System.Data.Entity.Core.Query.InternalTrees.Node child0 = root.Child0;
                command.DisableVarVecEnumCaching();
                System.Data.Entity.Core.Query.InternalTrees.Node relOpNode = child0;
                Var computedVar = op.Outputs[0];
                if (!Command.EqualTypes(op.ColumnMap.Type, this.FunctionImport.ReturnParameter.TypeUsage))
                {
                    TypeUsage typeUsage = ((CollectionType)this.FunctionImport.ReturnParameter.TypeUsage.EdmType).TypeUsage;
                    System.Data.Entity.Core.Query.InternalTrees.Node node1          = command.CreateNode((Op)command.CreateVarRefOp(computedVar));
                    System.Data.Entity.Core.Query.InternalTrees.Node node2          = command.CreateNode((Op)command.CreateSoftCastOp(typeUsage), node1);
                    System.Data.Entity.Core.Query.InternalTrees.Node varDefListNode = command.CreateVarDefListNode(node2, out computedVar);
                    ProjectOp projectOp = command.CreateProjectOp(computedVar);
                    relOpNode = command.CreateNode((Op)projectOp, relOpNode, varDefListNode);
                }
                this.m_internalTreeNode = command.BuildCollect(relOpNode, computedVar);
            }
            Dictionary <string, System.Data.Entity.Core.Query.InternalTrees.Node> viewArguments = new Dictionary <string, System.Data.Entity.Core.Query.InternalTrees.Node>(this.m_commandParameters.Length);

            for (int index = 0; index < this.m_commandParameters.Length; ++index)
            {
                DbParameterReferenceExpression commandParameter       = this.m_commandParameters[index];
                System.Data.Entity.Core.Query.InternalTrees.Node node = targetIqtArguments[index];
                if (TypeSemantics.IsEnumerationType(node.Op.Type))
                {
                    node = targetIqtCommand.CreateNode((Op)targetIqtCommand.CreateSoftCastOp(TypeHelpers.CreateEnumUnderlyingTypeUsage(node.Op.Type)), node);
                }
                viewArguments.Add(commandParameter.ParameterName, node);
            }
            return(FunctionImportMappingComposable.FunctionViewOpCopier.Copy(targetIqtCommand, this.m_internalTreeNode, viewArguments));
        }
 public override void Visit(ProjectOp op, Node n)
 {
     VisitRelOpDefault(op, n);
     AssertRelOpOrPhysicalOp(n.Child0.Op);
     AssertOpType(n.Child1.Op, OpType.VarDefList);
 }
Example #14
0
        private static bool ProcessProjectOpWithNullSentinel(
            RuleProcessingContext context,
            System.Data.Entity.Core.Query.InternalTrees.Node n,
            out System.Data.Entity.Core.Query.InternalTrees.Node newNode)
        {
            newNode = n;
            ProjectOp op = (ProjectOp)n.Op;

            if (n.Child1.Children.Where <System.Data.Entity.Core.Query.InternalTrees.Node>((Func <System.Data.Entity.Core.Query.InternalTrees.Node, bool>)(c => c.Child0.Op.OpType == OpType.NullSentinel)).Count <System.Data.Entity.Core.Query.InternalTrees.Node>() == 0)
            {
                return(false);
            }
            TransformationRulesContext transformationRulesContext = (TransformationRulesContext)context;
            Command          command           = transformationRulesContext.Command;
            ExtendedNodeInfo extendedNodeInfo  = command.GetExtendedNodeInfo(n.Child0);
            bool             flag1             = false;
            bool             nullSentinelValue = transformationRulesContext.CanChangeNullSentinelValue;
            Var int32Var;

            if (!nullSentinelValue || !TransformationRulesContext.TryGetInt32Var((IEnumerable <Var>)extendedNodeInfo.NonNullableDefinitions, out int32Var))
            {
                flag1 = true;
                if (!nullSentinelValue || !TransformationRulesContext.TryGetInt32Var(n.Child1.Children.Where <System.Data.Entity.Core.Query.InternalTrees.Node>((Func <System.Data.Entity.Core.Query.InternalTrees.Node, bool>)(child =>
                {
                    if (child.Child0.Op.OpType != OpType.Constant)
                    {
                        return(child.Child0.Op.OpType == OpType.InternalConstant);
                    }
                    return(true);
                })).Select <System.Data.Entity.Core.Query.InternalTrees.Node, Var>((Func <System.Data.Entity.Core.Query.InternalTrees.Node, Var>)(child => ((VarDefOp)child.Op).Var)), out int32Var))
                {
                    int32Var = n.Child1.Children.Where <System.Data.Entity.Core.Query.InternalTrees.Node>((Func <System.Data.Entity.Core.Query.InternalTrees.Node, bool>)(child => child.Child0.Op.OpType == OpType.NullSentinel)).Select <System.Data.Entity.Core.Query.InternalTrees.Node, Var>((Func <System.Data.Entity.Core.Query.InternalTrees.Node, Var>)(child => ((VarDefOp)child.Op).Var)).FirstOrDefault <Var>();
                    if (int32Var == null)
                    {
                        return(false);
                    }
                }
            }
            bool flag2 = false;

            for (int index = n.Child1.Children.Count - 1; index >= 0; --index)
            {
                System.Data.Entity.Core.Query.InternalTrees.Node child = n.Child1.Children[index];
                if (child.Child0.Op.OpType == OpType.NullSentinel)
                {
                    if (!flag1)
                    {
                        VarRefOp varRefOp = command.CreateVarRefOp(int32Var);
                        child.Child0 = command.CreateNode((Op)varRefOp);
                        command.RecomputeNodeInfo(child);
                        flag2 = true;
                    }
                    else if (!int32Var.Equals((object)((VarDefOp)child.Op).Var))
                    {
                        op.Outputs.Clear(((VarDefOp)child.Op).Var);
                        n.Child1.Children.RemoveAt(index);
                        transformationRulesContext.AddVarMapping(((VarDefOp)child.Op).Var, int32Var);
                        flag2 = true;
                    }
                }
            }
            if (flag2)
            {
                command.RecomputeNodeInfo(n.Child1);
            }
            return(flag2);
        }
Example #15
0
        private static bool ProcessJoinOverProject(
            RuleProcessingContext context,
            System.Data.Entity.Core.Query.InternalTrees.Node joinNode,
            out System.Data.Entity.Core.Query.InternalTrees.Node newNode)
        {
            newNode = joinNode;
            TransformationRulesContext transformationRulesContext = (TransformationRulesContext)context;
            Command command = transformationRulesContext.Command;

            System.Data.Entity.Core.Query.InternalTrees.Node node1 = joinNode.HasChild2 ? joinNode.Child2 : (System.Data.Entity.Core.Query.InternalTrees.Node)null;
            Dictionary <Var, int> varRefMap = new Dictionary <Var, int>();

            if (node1 != null && !transformationRulesContext.IsScalarOpTree(node1, varRefMap))
            {
                return(false);
            }
            VarVec varVec1 = command.CreateVarVec();
            List <System.Data.Entity.Core.Query.InternalTrees.Node> args = new List <System.Data.Entity.Core.Query.InternalTrees.Node>();

            if (joinNode.Op.OpType != OpType.LeftOuterJoin && joinNode.Child0.Op.OpType == OpType.Project && joinNode.Child1.Op.OpType == OpType.Project)
            {
                ProjectOp op1 = (ProjectOp)joinNode.Child0.Op;
                ProjectOp op2 = (ProjectOp)joinNode.Child1.Op;
                Dictionary <Var, System.Data.Entity.Core.Query.InternalTrees.Node> varMap1 = transformationRulesContext.GetVarMap(joinNode.Child0.Child1, varRefMap);
                Dictionary <Var, System.Data.Entity.Core.Query.InternalTrees.Node> varMap2 = transformationRulesContext.GetVarMap(joinNode.Child1.Child1, varRefMap);
                if (varMap1 == null || varMap2 == null)
                {
                    return(false);
                }
                System.Data.Entity.Core.Query.InternalTrees.Node node2;
                if (node1 != null)
                {
                    System.Data.Entity.Core.Query.InternalTrees.Node node3 = transformationRulesContext.ReMap(node1, varMap1);
                    System.Data.Entity.Core.Query.InternalTrees.Node node4 = transformationRulesContext.ReMap(node3, varMap2);
                    node2 = context.Command.CreateNode(joinNode.Op, joinNode.Child0.Child0, joinNode.Child1.Child0, node4);
                }
                else
                {
                    node2 = context.Command.CreateNode(joinNode.Op, joinNode.Child0.Child0, joinNode.Child1.Child0);
                }
                varVec1.InitFrom(op1.Outputs);
                foreach (Var output in op2.Outputs)
                {
                    varVec1.Set(output);
                }
                ProjectOp projectOp = command.CreateProjectOp(varVec1);
                args.AddRange((IEnumerable <System.Data.Entity.Core.Query.InternalTrees.Node>)joinNode.Child0.Child1.Children);
                args.AddRange((IEnumerable <System.Data.Entity.Core.Query.InternalTrees.Node>)joinNode.Child1.Child1.Children);
                System.Data.Entity.Core.Query.InternalTrees.Node node5 = command.CreateNode((Op)command.CreateVarDefListOp(), args);
                System.Data.Entity.Core.Query.InternalTrees.Node node6 = command.CreateNode((Op)projectOp, node2, node5);
                newNode = node6;
                return(true);
            }
            int index1;
            int index2;

            if (joinNode.Child0.Op.OpType == OpType.Project)
            {
                index1 = 0;
                index2 = 1;
            }
            else
            {
                System.Data.Entity.Core.Query.PlanCompiler.PlanCompiler.Assert(joinNode.Op.OpType != OpType.LeftOuterJoin, "unexpected non-LeftOuterJoin");
                index1 = 1;
                index2 = 0;
            }
            System.Data.Entity.Core.Query.InternalTrees.Node child = joinNode.Children[index1];
            ProjectOp op = child.Op as ProjectOp;
            Dictionary <Var, System.Data.Entity.Core.Query.InternalTrees.Node> varMap = transformationRulesContext.GetVarMap(child.Child1, varRefMap);

            if (varMap == null)
            {
                return(false);
            }
            ExtendedNodeInfo extendedNodeInfo = command.GetExtendedNodeInfo(joinNode.Children[index2]);
            VarVec           varVec2          = command.CreateVarVec(op.Outputs);

            varVec2.Or(extendedNodeInfo.Definitions);
            op.Outputs.InitFrom(varVec2);
            if (node1 != null)
            {
                System.Data.Entity.Core.Query.InternalTrees.Node node2 = transformationRulesContext.ReMap(node1, varMap);
                joinNode.Child2 = node2;
            }
            joinNode.Children[index1] = child.Child0;
            context.Command.RecomputeNodeInfo(joinNode);
            newNode = context.Command.CreateNode((Op)op, joinNode, child.Child1);
            return(true);
        }
Example #16
0
 public override void Visit(ProjectOp op, System.Data.Entity.Core.Query.InternalTrees.Node n)
 {
     this.VisitRelOpDefault((RelOp)op, n);
     this.Map(op.Outputs);
 }
Example #17
0
 public override void Visit(ProjectOp op, System.Data.Entity.Core.Query.InternalTrees.Node n)
 {
     this.VisitNode(n.Child1);
     this.VisitNode(n.Child0);
 }
        private static bool ProcessOuterApplyOverDummyProjectOverFilter(
            RuleProcessingContext context,
            System.Data.Entity.Core.Query.InternalTrees.Node applyNode,
            out System.Data.Entity.Core.Query.InternalTrees.Node newNode)
        {
            newNode = applyNode;
            System.Data.Entity.Core.Query.InternalTrees.Node child1 = applyNode.Child1;
            ProjectOp op = (ProjectOp)child1.Op;

            System.Data.Entity.Core.Query.InternalTrees.Node child0_1 = child1.Child0;
            System.Data.Entity.Core.Query.InternalTrees.Node child0_2 = child0_1.Child0;
            Command          command           = context.Command;
            ExtendedNodeInfo extendedNodeInfo1 = command.GetExtendedNodeInfo(child0_2);
            ExtendedNodeInfo extendedNodeInfo2 = command.GetExtendedNodeInfo(applyNode.Child0);

            if (op.Outputs.Overlaps(extendedNodeInfo2.Definitions) || extendedNodeInfo1.ExternalReferences.Overlaps(extendedNodeInfo2.Definitions))
            {
                return(false);
            }
            bool flag1 = false;
            TransformationRulesContext transformationRulesContext = (TransformationRulesContext)context;
            Var  int32Var;
            bool flag2;

            if (TransformationRulesContext.TryGetInt32Var((IEnumerable <Var>)extendedNodeInfo1.NonNullableDefinitions, out int32Var))
            {
                flag2 = true;
            }
            else
            {
                int32Var = extendedNodeInfo1.NonNullableDefinitions.First;
                flag2    = false;
            }
            System.Data.Entity.Core.Query.InternalTrees.Node node1;
            if (int32Var != null)
            {
                flag1 = true;
                System.Data.Entity.Core.Query.InternalTrees.Node child0_3 = child1.Child1.Child0;
                child0_3.Child0 = child0_3.Child0.Op.OpType != OpType.NullSentinel || !flag2 || !transformationRulesContext.CanChangeNullSentinelValue ? transformationRulesContext.BuildNullIfExpression(int32Var, child0_3.Child0) : context.Command.CreateNode((Op)context.Command.CreateVarRefOp(int32Var));
                command.RecomputeNodeInfo(child0_3);
                command.RecomputeNodeInfo(child1.Child1);
                node1 = child0_2;
            }
            else
            {
                node1 = child1;
                foreach (Var externalReference in command.GetNodeInfo(child0_1.Child1).ExternalReferences)
                {
                    if (extendedNodeInfo1.Definitions.IsSet(externalReference))
                    {
                        op.Outputs.Set(externalReference);
                    }
                }
                child1.Child0 = child0_2;
            }
            context.Command.RecomputeNodeInfo(child1);
            System.Data.Entity.Core.Query.InternalTrees.Node node2 = command.CreateNode((Op)command.CreateLeftOuterJoinOp(), applyNode.Child0, node1, child0_1.Child1);
            if (flag1)
            {
                ExtendedNodeInfo extendedNodeInfo3 = command.GetExtendedNodeInfo(node2);
                child1.Child0 = node2;
                op.Outputs.Or(extendedNodeInfo3.Definitions);
                newNode = child1;
            }
            else
            {
                newNode = node2;
            }
            return(true);
        }
Example #19
0
        internal Node GetInternalTree(Command targetIqtCommand, IList <Node> targetIqtArguments)
        {
            if (m_internalTreeNode == null)
            {
                var viewGenErrors = new List <EdmSchemaError>();
                DiscriminatorMap   discriminatorMap;
                DbQueryCommandTree tree = GenerateFunctionView(viewGenErrors, out discriminatorMap);
                if (viewGenErrors.Count > 0)
                {
                    throw new MappingException(Helper.CombineErrorMessage(viewGenErrors));
                }
                Debug.Assert(tree != null, "tree != null");

                // Convert this into an ITree first
                Command itree       = ITreeGenerator.Generate(tree, discriminatorMap);
                var     rootProject = itree.Root; // PhysicalProject(RelInput)
                PlanCompiler.Assert(rootProject.Op.OpType == OpType.PhysicalProject, "Expected a physical projectOp at the root of the tree - found " + rootProject.Op.OpType);
                var rootProjectOp = (PhysicalProjectOp)rootProject.Op;
                Debug.Assert(rootProjectOp.Outputs.Count == 1, "rootProjectOp.Outputs.Count == 1");
                var rootInput = rootProject.Child0; // the RelInput in PhysicalProject(RelInput)

                // #554756: VarVec enumerators are not cached on the shared Command instance.
                itree.DisableVarVecEnumCaching();

                // Function import returns a collection, so convert it to a scalar by wrapping into CollectOp.
                Node relNode = rootInput;
                Var  relVar  = rootProjectOp.Outputs[0];
                // ProjectOp does not implement Type property, so get the type from the column map.
                TypeUsage functionViewType = rootProjectOp.ColumnMap.Type;
                if (!Command.EqualTypes(functionViewType, this.FunctionImport.ReturnParameter.TypeUsage))
                {
                    Debug.Assert(TypeSemantics.IsPromotableTo(functionViewType, this.FunctionImport.ReturnParameter.TypeUsage), "Mapping expression result type must be promotable to the c-space function return type.");

                    // Build "relNode = Project(relNode, SoftCast(relVar))"
                    CollectionType expectedCollectionType = (CollectionType)this.FunctionImport.ReturnParameter.TypeUsage.EdmType;
                    var            expectedElementType    = expectedCollectionType.TypeUsage;

                    Node varRefNode     = itree.CreateNode(itree.CreateVarRefOp(relVar));
                    Node castNode       = itree.CreateNode(itree.CreateSoftCastOp(expectedElementType), varRefNode);
                    Node varDefListNode = itree.CreateVarDefListNode(castNode, out relVar);

                    ProjectOp projectOp = itree.CreateProjectOp(relVar);
                    relNode = itree.CreateNode(projectOp, relNode, varDefListNode);
                }

                // Build "Collect(PhysicalProject(relNode))
                m_internalTreeNode = itree.BuildCollect(relNode, relVar);
            }
            Debug.Assert(m_internalTreeNode != null, "m_internalTreeNode != null");

            // Prepare argument replacement dictionary
            Debug.Assert(m_commandParameters.Length == targetIqtArguments.Count, "m_commandParameters.Length == targetIqtArguments.Count");
            Dictionary <string, Node> viewArguments = new Dictionary <string, Node>(m_commandParameters.Length);

            for (int i = 0; i < m_commandParameters.Length; ++i)
            {
                var commandParam = (DbParameterReferenceExpression)m_commandParameters[i];
                var argumentNode = targetIqtArguments[i];

                // If function import parameter is of enum type, the argument value for it will be of enum type. We however have
                // converted enum types to underlying types for m_commandParameters. So we now need to softcast the argument
                // expression to the underlying type as well.
                if (TypeSemantics.IsEnumerationType(argumentNode.Op.Type))
                {
                    argumentNode = targetIqtCommand.CreateNode(
                        targetIqtCommand.CreateSoftCastOp(TypeHelpers.CreateEnumUnderlyingTypeUsage(argumentNode.Op.Type)),
                        argumentNode);
                }

                Debug.Assert(TypeSemantics.IsPromotableTo(argumentNode.Op.Type, commandParam.ResultType), "Argument type must be promotable to parameter type.");

                viewArguments.Add(commandParam.ParameterName, argumentNode);
            }

            return(FunctionViewOpCopier.Copy(targetIqtCommand, m_internalTreeNode, viewArguments));
        }
Example #20
0
 public override void Visit(ProjectOp op, Node n)
 {
     VisitRelOpDefault(op, n);
     Map(op.Outputs);
 }
 /// <summary>
 ///     Visitor pattern method for ProjectOp
 /// </summary>
 /// <param name="op"> The ProjectOp being visited </param>
 /// <param name="n"> The Node that references the Op </param>
 public virtual void Visit(ProjectOp op, Node n)
 {
     VisitRelOpDefault(op, n);
 }
Example #22
0
 // <summary>
 // ProjectOp
 // </summary>
 public override int Visit(ProjectOp op, Node n)
 {
     return(op.Outputs.Count);
 }
 /// <summary>
 ///     ProjectOp handling
 /// </summary>
 /// <param name="op"> </param>
 /// <param name="n"> </param>
 public override void Visit(ProjectOp op, Node n)
 {
     VisitNode(n.Child1); // visit projections first
     VisitNode(n.Child0); // then visit the relop input
 }
Example #24
0
        /// <summary>
        /// Try to push the given function aggregate candidate to the corresponding group into node.
        /// The candidate can be pushed if all ancestors of the group into node up to the least common
        /// ancestor between the group into node and the function aggregate have one of the following node op types:
        ///     Project
        ///     Filter
        ///     ConstraintSortOp
        /// </summary>
        /// <param name="command"></param>
        /// <param name="candidate"></param>
        /// <param name="groupAggregateVarInfo"></param>
        /// <param name="m_childToParent"></param>
        private void TryProcessCandidate(
            KeyValuePair <Node, Node> candidate,
            GroupAggregateVarInfo groupAggregateVarInfo)
        {
            IList <Node> functionAncestors;
            IList <Node> groupByAncestors;
            Node         definingGroupNode = groupAggregateVarInfo.DefiningGroupNode;

            FindPathsToLeastCommonAncestor(candidate.Key, definingGroupNode, out functionAncestors, out groupByAncestors);

            //Check whether all ancestors of the GroupByInto node are of type that we support propagating through
            if (!AreAllNodesSupportedForPropagation(groupByAncestors))
            {
                return;
            }

            //Add the function to the group by node
            GroupByIntoOp definingGroupOp = (GroupByIntoOp)definingGroupNode.Op;

            PlanCompiler.Assert(definingGroupOp.Inputs.Count == 1, "There should be one input var to GroupByInto at this stage");
            Var        inputVar   = definingGroupOp.Inputs.First;
            FunctionOp functionOp = (FunctionOp)candidate.Key.Op;

            //
            // Remap the template from referencing the groupAggregate var to reference the input to
            // the group by into
            //
            Node argumentNode = OpCopier.Copy(m_command, candidate.Value);
            Dictionary <Var, Var> dictionary = new Dictionary <Var, Var>(1);

            dictionary.Add(groupAggregateVarInfo.GroupAggregateVar, inputVar);
            VarRemapper remapper = new VarRemapper(m_command, dictionary);

            remapper.RemapSubtree(argumentNode);

            Node newFunctionDefiningNode = m_command.CreateNode(
                m_command.CreateAggregateOp(functionOp.Function, false),
                argumentNode);

            Var  newFunctionVar;
            Node varDefNode = m_command.CreateVarDefNode(newFunctionDefiningNode, out newFunctionVar);

            // Add the new aggregate to the list of aggregates
            definingGroupNode.Child2.Children.Add(varDefNode);
            GroupByIntoOp groupByOp = (GroupByIntoOp)definingGroupNode.Op;

            groupByOp.Outputs.Set(newFunctionVar);

            //Propagate the new var throught the ancestors of the GroupByInto
            for (int i = 0; i < groupByAncestors.Count; i++)
            {
                Node groupByAncestor = groupByAncestors[i];
                if (groupByAncestor.Op.OpType == OpType.Project)
                {
                    ProjectOp ancestorProjectOp = (ProjectOp)groupByAncestor.Op;
                    ancestorProjectOp.Outputs.Set(newFunctionVar);
                }
            }

            //Update the functionNode
            candidate.Key.Op = m_command.CreateVarRefOp(newFunctionVar);
            candidate.Key.Children.Clear();
        }
Example #25
0
        // <summary>
        // ProjectOp
        // </summary>
        // <remarks>
        // If after visiting the children, the ProjectOp's input is a SortOp, swap the ProjectOp and the SortOp,
        // to allow the SortOp to bubble up and be honored. This may only occur if the original input to the
        // ProjectOp was an UnnestOp.
        // There are three cases to handle in ProjectOp:
        // (1) The input is not a NestOp; but the ProjectOp locally defines some Vars
        // as collections:
        // ProjectOp(X,{a,CollectOp(PhysicalProjectOp(Y)),b,...}) ==> MsnOp(ProjectOp'(X,{a,b,...}),Y)
        // ProjectOp(X,{a,VarRef(ref-to-collect-var-Y),b,...})    ==> MsnOp(ProjectOp'(X,{a,b,...}),copy-of-Y)
        // Where:
        // ProjectOp' is ProjectOp less any vars that were collection vars, plus
        // any additional Vars needed by the collection.
        // (2) The input is a NestOp, but the ProjectOp does not local define some Vars
        // as collections:
        // ProjectOp(MsnOp(X,Y,...)) => MsnOp'(ProjectOp'(X),Y,...)
        // Where:
        // ProjectOp' is ProjectOp plus any additional Vars needed by NestOp
        // (see NestOp.Outputs – except the collection vars)
        // MsnOp'     should be MsnOp. Additionally, its Outputs should be enhanced
        // to include any Vars produced by the ProjectOp
        // (3) The combination of both (1) and (2) -- both the vars define a collection,
        // and the input is also a nestOp.  we handle this by first processing Case1,
        // then processing Case2.
        // </remarks>
        public override Node Visit(ProjectOp op, Node n)
        {
#if DEBUG
            var input = Dump.ToXml(n);
#endif
            //DEBUG

            // First, visit my children
            VisitChildren(n);
            m_varRemapper.RemapNode(n);

            Node newNode;

            // If the ProjectOp's input is a SortOp, swap the ProjectOp and the SortOp, 
            // to allow the SortOp to buble up and be honored. This may only occur if the original input to the  
            // ProjectOp was an UnnestOp (or a Project over a Unnest Op). 
            if (n.Child0.Op.OpType
                == OpType.Sort)
            {
                var sortNode = n.Child0;
                foreach (var key in ((SortOp)sortNode.Op).Keys)
                {
                    if (!Command.GetExtendedNodeInfo(sortNode).ExternalReferences.IsSet(key.Var))
                    {
                        op.Outputs.Set(key.Var);
                    }
                }
                n.Child0 = sortNode.Child0;
                Command.RecomputeNodeInfo(n);
                sortNode.Child0 = HandleProjectNode(n);
                Command.RecomputeNodeInfo(sortNode);

                newNode = sortNode;
            }
            else
            {
                newNode = HandleProjectNode(n);
            }

#if DEBUG
            var size = input.Length; // GC.KeepAlive makes FxCop Grumpy.
            var output = Dump.ToXml(newNode);
#endif
            //DEBUG
            return newNode;
        }
Example #26
0
        // <summary>
        // Copies a ProjectOp
        // </summary>
        // <param name="op"> The Op to Copy </param>
        // <param name="n"> The Node that references the Op </param>
        // <returns> A copy of the original Node that references a copy of the original Op </returns>
        public override Node Visit(ProjectOp op, Node n)
        {
            // Visit the Node's children and map their Vars
            var children = ProcessChildren(n);

            // Copy the ProjectOp's VarSet
            var newVarSet = Copy(op.Outputs);

            // Create a new ProjectOp based on the copied VarSet
            var newProject = m_destCmd.CreateProjectOp(newVarSet);

            // Return a new Node that references the copied ProjectOp and has the copied child Nodes as its children
            return m_destCmd.CreateNode(newProject, children);
        }
        public override Node Visit(ProjectOp op, Node n)
        {
            PlanCompiler.Assert(n.HasChild0, "projectOp without input?");

            if (OpType.Sort == n.Child0.Op.OpType
                || OpType.ConstrainedSort == n.Child0.Op.OpType)
            {
                var sort = (SortBaseOp)n.Child0.Op;

                // Don't pullup the sort if it doesn't have any keys.
                // An example of such sort is "ctx.Products.Take(1)".
                if (sort.Keys.Count > 0)
                {
                    IList<Node> sortChildren = new List<Node>();
                    sortChildren.Add(n);

                    //A ConstrainedSort has two other children besides the input and it needs to keep them.  
                    for (var i = 1; i < n.Child0.Children.Count; i++)
                    {
                        sortChildren.Add(n.Child0.Children[i]);
                    }

                    // Replace the ProjectOp input (currently the Sort node) with the input to the Sort.
                    n.Child0 = n.Child0.Child0;

                    // Vars produced by the Sort input and used as SortKeys should be considered outputs
                    // of the ProjectOp that now operates over what was the Sort input.
                    foreach (var key in sort.Keys)
                    {
                        op.Outputs.Set(key.Var);
                    }

                    // Finally, pull the Sort over the Project by creating a new Sort node with the original
                    // Sort as its Op and the Project node as its only child. This is sufficient because
                    // the ITreeGenerator ensures that the SortOp does not have any local VarDefs.
                    return VisitNode(m_command.CreateNode(sort, sortChildren));
                }
            }

            // perform default processing
            var newNode = VisitRelOpDefault(op, n);
            return newNode;
        }
Example #28
0
        /// <summary>
        ///     Pulls up keys for a ProjectOp. First visits its children to pull
        ///     up its keys; then identifies any keys from the input that it may have
        ///     projected out - and adds them to the output list of vars
        /// </summary>
        /// <param name="op"> Current ProjectOp </param>
        /// <param name="n"> Current subtree </param>
        public override void Visit(ProjectOp op, Node n)
        {
            VisitChildren(n);

            var childNodeInfo = n.Child0.GetExtendedNodeInfo(m_command);
            if (!childNodeInfo.Keys.NoKeys)
            {
                var outputVars = m_command.CreateVarVec(op.Outputs);
                // NOTE: This code appears in NodeInfoVisitor as well. Try to see if we
                //       can share this somehow.
                var varRenameMap = NodeInfoVisitor.ComputeVarRemappings(n.Child1);
                var mappedKeyVec = childNodeInfo.Keys.KeyVars.Remap(varRenameMap);
                outputVars.Or(mappedKeyVec);
                op.Outputs.InitFrom(outputVars);
            }
            m_command.RecomputeNodeInfo(n);
        }
        /// <summary>
        ///     ProjectOp
        ///     The computedVars (the VarDefList) are processed via the VisitChildren() call
        ///     We then try to update the "Vars" property to flatten out any structured
        ///     type Vars - if a new VarSet is produced, then the ProjectOp is cloned
        /// </summary>
        /// <param name="op"> </param>
        /// <param name="n"> </param>
        /// <returns> new subtree </returns>
        public override Node Visit(ProjectOp op, Node n)
        {
            VisitChildren(n);

            // update the output Vars with the right set of information 
            var newVars = FlattenVarSet(op.Outputs);

            if (op.Outputs != newVars)
            {
                // If the set of vars is empty, that means we didn;t need any of the Vars
                if (newVars.IsEmpty)
                {
                    return n.Child0;
                }
                n.Op = m_command.CreateProjectOp(newVars);
            }
            return n;
        }
Example #30
0
 public override void Visit(ProjectOp op, Node n)
 {
     VisitRelOpDefault(op, n);
     Map(op.Outputs);
 }
 /// <summary>
 /// ProjectOp handling
 /// </summary>
 /// <param name="op"></param>
 /// <param name="n"></param>
 public override void Visit(ProjectOp op, Node n)
 {
     VisitNode(n.Child1); // visit projections first
     VisitNode(n.Child0); // then visit the relop input
 }
 public override int Visit(ProjectOp op, System.Data.Entity.Core.Query.InternalTrees.Node n)
 {
     return(op.Outputs.Count);
 }