예제 #1
0
 public void PatchUsersOfCopiedElements(
     Dictionary<PatternNode, PatternNode> nodeToCopy,
     Dictionary<PatternEdge, PatternEdge> edgeToCopy,
     Dictionary<PatternVariable, PatternVariable> variableToCopy)
 {
     if(GraphElement != null)
     {
         if(GraphElement is PatternNode)
         {
             if(nodeToCopy.ContainsKey((PatternNode)GraphElement))
                 GraphElement = nodeToCopy[(PatternNode)GraphElement];
         }
         else
         {
             if(edgeToCopy.ContainsKey((PatternEdge)GraphElement))
                 GraphElement = edgeToCopy[(PatternEdge)GraphElement];
         }
     }
     if(Variable != null)
     {
         if(variableToCopy.ContainsKey(Variable))
             Variable = variableToCopy[Variable];
     }
     if(Attribute != null)
     {
         if(Attribute.Owner is PatternNode)
         {
             if(nodeToCopy.ContainsKey((PatternNode)Attribute.Owner))
                 Attribute.Owner = nodeToCopy[(PatternNode)Attribute.Owner];
         }
         else
         {
             if(edgeToCopy.ContainsKey((PatternEdge)Attribute.Owner))
                 Attribute.Owner = edgeToCopy[(PatternEdge)Attribute.Owner];
         }
     }
 }
예제 #2
0
 public StorageAccessIndex(PatternVariable variable)
 {
     Variable = variable;
 }
예제 #3
0
 // Instantiates a new StorageAccessIndex object as a copy from an original storage access index, used for inlining.
 public StorageAccessIndex(StorageAccessIndex original)
 {
     GraphElement = original.GraphElement;
     Variable = original.Variable;
     GlobalVariable = original.GlobalVariable;
     Attribute = original.Attribute;
 }
예제 #4
0
 /// <summary>
 /// Instantiates a new PatternVariable object as a copy from an original variable, used for inlining.
 /// </summary>
 /// <param name="original">The original pattern variable to be copy constructed.</param>
 /// <param name="inlinedSubpatternEmbedding">The embedding which just gets inlined.</param>
 /// <param name="newHost">The pattern graph the new pattern element will be contained in.</param>
 /// <param name="nameSuffix">The suffix to be added to the name of the pattern variable (to avoid name collisions).</param>
 public PatternVariable(PatternVariable original, PatternGraphEmbedding inlinedSubpatternEmbedding, PatternGraph newHost, String nameSuffix)
 {
     type = original.type;
     name = original.name + nameSuffix;
     unprefixedName = original.unprefixedName + nameSuffix;
     pointOfDefinition = newHost;
     defToBeYieldedTo = original.defToBeYieldedTo;
     initialization = original.initialization;
     annotations = original.annotations;
     ParameterIndex = original.ParameterIndex;
     originalVariable = original;
     originalSubpatternEmbedding = inlinedSubpatternEmbedding;
 }
예제 #5
0
 // Instantiates a new StorageAccess object as a copy from an original storage access, used for inlining.
 public StorageAccess(StorageAccess original)
 {
     Variable = original.Variable;
     GlobalVariable = original.GlobalVariable;
     Attribute = original.Attribute;
 }
예제 #6
0
        /// <summary>
        /// Parallelize the scheduled search plan to the branching factor,
        /// splitting it at the first loop into a header part and a body part
        /// </summary>
        public void ParallelizeHeadBody(LGSPRulePattern rulePattern)
        {
            Debug.Assert(rulePattern.patternGraph.schedulesIncludingNegativesAndIndependents.Length == 1);
            ScheduledSearchPlan ssp = rulePattern.patternGraph.schedulesIncludingNegativesAndIndependents[0];
            
            int indexToSplitAt = 0;
            for(int i = 0; i < ssp.Operations.Length; ++i)
            {
                SearchOperation so = ssp.Operations[i];
                if(so.Type == SearchOperationType.Lookup || so.Type == SearchOperationType.Incident
                    || so.Type == SearchOperationType.Incoming || so.Type == SearchOperationType.Outgoing
                    || so.Type == SearchOperationType.PickFromStorage || so.Type == SearchOperationType.PickFromStorageDependent
                    || so.Type == SearchOperationType.PickFromIndex || so.Type == SearchOperationType.PickFromIndexDependent)
                {
                    indexToSplitAt = i;
                    break;
                }
            }

            rulePattern.patternGraph.parallelizedSchedule = new ScheduledSearchPlan[2];
            List<SearchOperation> headOperations = new List<SearchOperation>();
            List<SearchOperation> bodyOperations = new List<SearchOperation>();
            for(int i = 0; i < rulePattern.Inputs.Length; ++i)
            {
                if(rulePattern.Inputs[i] is VarType) // those don't appear in the schedule, they are only extracted into the search program
                {
                    VarType varType = (VarType)rulePattern.Inputs[i];
                    String varName = rulePattern.InputNames[i];
                    PatternVariable dummy = new PatternVariable(varType, varName, varName, i, false, null);
                    headOperations.Add(new SearchOperation(SearchOperationType.WriteParallelPresetVar,
                        dummy, null, 0));
                    bodyOperations.Add(new SearchOperation(SearchOperationType.ParallelPresetVar,
                        dummy, null, 0));
                }
            }
            for(int i = 0; i < ssp.Operations.Length; ++i)
            {
                SearchOperation so = ssp.Operations[i];
                if(i < indexToSplitAt)
                {
                    SearchOperation clone = (SearchOperation)so.Clone();
                    clone.Isomorphy.Parallel = true;
                    clone.Isomorphy.LockForAllThreads = true;
                    headOperations.Add(clone);
                    switch(so.Type)
                    {
                            // the target binding looping operations can't appear in the header, so we don't treat them here
                            // the non-target binding operations are completely handled by just adding them, happended already above
                            // the target binding non-looping operations are handled below,
                            // by parallel preset writing in the header and reading in the body
                            // with exception of def, its declaration and initializion is just re-executed in the body
                            // some presets can't appear in an action header, they are thus not taken care of
                        case SearchOperationType.ActionPreset:
                        case SearchOperationType.MapWithStorage:
                        case SearchOperationType.MapWithStorageDependent:
                        case SearchOperationType.Cast:
                        case SearchOperationType.Assign:
                        case SearchOperationType.Identity:
                        case SearchOperationType.ImplicitSource:
                        case SearchOperationType.ImplicitTarget:
                        case SearchOperationType.Implicit:
                            headOperations.Add(new SearchOperation(SearchOperationType.WriteParallelPreset,
                                (SearchPlanNode)so.Element, so.SourceSPNode, 0));
                            bodyOperations.Add(new SearchOperation(SearchOperationType.ParallelPreset, 
                                (SearchPlanNode)so.Element, so.SourceSPNode, 0));
                            break;
                        case SearchOperationType.AssignVar:
                            headOperations.Add(new SearchOperation(SearchOperationType.WriteParallelPresetVar,
                                (PatternVariable)so.Element, so.SourceSPNode, 0));
                            bodyOperations.Add(new SearchOperation(SearchOperationType.ParallelPresetVar,
                                (PatternVariable)so.Element, so.SourceSPNode, 0));
                            break;
                        case SearchOperationType.DefToBeYieldedTo:
                            bodyOperations.Add((SearchOperation)so.Clone());
                            break;
                    }                    
                }
                else if(i == indexToSplitAt)
                {
                    SearchOperation cloneHead = (SearchOperation)so.Clone();
                    headOperations.Add(cloneHead);
                    SearchOperation cloneBody = (SearchOperation)so.Clone();
                    cloneBody.Isomorphy.Parallel = true;
                    bodyOperations.Add(cloneBody);
                    switch(so.Type)
                    {
                        case SearchOperationType.Lookup:
                            cloneHead.Type = SearchOperationType.SetupParallelLookup;
                            cloneBody.Type = SearchOperationType.ParallelLookup;
                            break;
                        case SearchOperationType.Incident:
                            cloneHead.Type = SearchOperationType.SetupParallelIncident;
                            cloneBody.Type = SearchOperationType.ParallelIncident;
                            break;
                        case SearchOperationType.Incoming:
                            cloneHead.Type = SearchOperationType.SetupParallelIncoming;
                            cloneBody.Type = SearchOperationType.ParallelIncoming;
                            break;
                        case SearchOperationType.Outgoing:
                            cloneHead.Type = SearchOperationType.SetupParallelOutgoing;
                            cloneBody.Type = SearchOperationType.ParallelOutgoing;
                            break;
                        case SearchOperationType.PickFromStorage:
                            cloneHead.Type = SearchOperationType.SetupParallelPickFromStorage;
                            cloneBody.Type = SearchOperationType.ParallelPickFromStorage;
                            break;
                        case SearchOperationType.PickFromStorageDependent:
                            cloneHead.Type = SearchOperationType.SetupParallelPickFromStorageDependent;
                            cloneBody.Type = SearchOperationType.ParallelPickFromStorageDependent;
                            break;
                        case SearchOperationType.PickFromIndex:
                            cloneHead.Type = SearchOperationType.SetupParallelPickFromIndex;
                            cloneBody.Type = SearchOperationType.ParallelPickFromIndex;
                            break;
                        case SearchOperationType.PickFromIndexDependent:
                            cloneHead.Type = SearchOperationType.SetupParallelPickFromIndexDependent;
                            cloneBody.Type = SearchOperationType.ParallelPickFromIndexDependent;
                            break;
                    }
                }
                else
                {
                    SearchOperation clone = (SearchOperation)so.Clone();
                    clone.Isomorphy.Parallel = true;
                    bodyOperations.Add(clone);
                    if(clone.Element is PatternCondition)
                        SetNeedForParallelizedVersion((clone.Element as PatternCondition).ConditionExpression);
                }
            }
            ScheduledSearchPlan headSsp = new ScheduledSearchPlan(
                rulePattern.patternGraph, headOperations.ToArray(), headOperations.Count > 0 ? headOperations[0].CostToEnd : 0);
            rulePattern.patternGraph.parallelizedSchedule[0] = headSsp;
            ScheduledSearchPlan bodySsp = new ScheduledSearchPlan(
                rulePattern.patternGraph, bodyOperations.ToArray(), bodyOperations.Count > 0 ? bodyOperations[0].CostToEnd : 0);
            rulePattern.patternGraph.parallelizedSchedule[1] = bodySsp;
            ParallelizeNegativeIndependent(bodySsp);
            ParallelizeAlternativeIterated(rulePattern.patternGraph);
            ParallelizeYielding(rulePattern.patternGraph);
        }
예제 #7
0
        /// <summary>
        /// Inserts inlined variable assignments into the schedule given by the operations list at their earliest possible position
        /// </summary>
        public void InsertInlinedVariableAssignmentsIntoSchedule(PatternGraph patternGraph, List<SearchOperation> operations)
        {
            // compute the number of inlined parameter variables
            int numInlinedParameterVariables = 0;
            foreach(PatternVariable var in patternGraph.variablesPlusInlined)
            {
                if(var.AssignmentSource != null && patternGraph.WasInlinedHere(var.originalSubpatternEmbedding))
                    ++numInlinedParameterVariables;
            }

            if(numInlinedParameterVariables == 0)
                return;

            // get the inlined parameter variables and the elements needed in order to compute their defining expression
            Dictionary<String, bool>[] neededElements = new Dictionary<String, bool>[numInlinedParameterVariables];
            PatternVariable[] inlinedParameterVariables = new PatternVariable[numInlinedParameterVariables];
            int curInlParamVar = 0;
            foreach(PatternVariable var in patternGraph.variablesPlusInlined)
            {
                if(var.AssignmentSource == null)
                    continue;
                if(!patternGraph.WasInlinedHere(var.originalSubpatternEmbedding))
                    continue;

                neededElements[curInlParamVar] = new Dictionary<string, bool>();
                foreach(String neededNode in var.AssignmentDependencies.neededNodes)
                    neededElements[curInlParamVar][neededNode] = true;
                foreach(String neededEdge in var.AssignmentDependencies.neededEdges)
                    neededElements[curInlParamVar][neededEdge] = true;
                inlinedParameterVariables[curInlParamVar] = var;
                
                ++curInlParamVar;
            }

            // iterate over all inlined parameter variables
            for(int i = 0; i < inlinedParameterVariables.Length; ++i)
            {
                int j;
                float costToEnd = 0;

                // find leftmost place in scheduled search plan for current assignment
                // by search from end of schedule forward until the first element the expression assigned is dependent on is found
                for(j = operations.Count - 1; j >= 0; --j)
                {
                    SearchOperation op = operations[j];
                    if(op.Type == SearchOperationType.Condition
                        || op.Type == SearchOperationType.Assign
                        || op.Type == SearchOperationType.AssignVar
                        || op.Type == SearchOperationType.NegativePattern
                        || op.Type == SearchOperationType.IndependentPattern
                        || op.Type == SearchOperationType.DefToBeYieldedTo)
                    {
                        continue;
                    }

                    if(neededElements[i].ContainsKey(((SearchPlanNode)op.Element).PatternElement.Name))
                    {
                        costToEnd = op.CostToEnd;
                        break;
                    }
                }

                SearchOperation so = new SearchOperation(SearchOperationType.AssignVar,
                    inlinedParameterVariables[i], null, costToEnd);
                so.Expression = inlinedParameterVariables[i].AssignmentSource;
                operations.Insert(j + 1, so);
            }
        }
예제 #8
0
        /// <summary>
        /// Search program operations implementing the
        /// ParallelPresetVar search plan operation
        /// are created and inserted into search program
        /// </summary>
        private SearchProgramOperation buildParallelPresetVar(
            SearchProgramOperation insertionPoint,
            int currentOperationIndex,
            PatternVariable target)
        {
            // get candidate from parallelization preset
            GetCandidateByDrawing fromInputs =
                new GetCandidateByDrawing(
                    GetCandidateByDrawingType.FromParallelizationTaskVar,
                    target.Name,
                    TypesHelper.TypeName(target.Type));
            insertionPoint = insertionPoint.Append(fromInputs);

            //---------------------------------------------------------------------------
            // build next operation
            insertionPoint = BuildScheduledSearchPlanOperationIntoSearchProgram(
                currentOperationIndex + 1,
                insertionPoint);
            //---------------------------------------------------------------------------

            return insertionPoint;
        }
예제 #9
0
        /// <summary>
        /// Search program operations implementing the
        /// WriteParallelPresetVar search plan operation
        /// are created and inserted into search program
        /// </summary>
        private SearchProgramOperation buildWriteParallelPresetVar(
            SearchProgramOperation insertionPoint,
            int currentOperationIndex,
            PatternVariable target)
        {
            // write parallel preset var
            WriteParallelPresetVar writePresetVar =
                new WriteParallelPresetVar(
                    target.Name,
                    TypesHelper.TypeName(target.Type));
            insertionPoint = insertionPoint.Append(writePresetVar);

            //---------------------------------------------------------------------------
            // build next operation
            insertionPoint = BuildScheduledSearchPlanOperationIntoSearchProgram(
                currentOperationIndex + 1,
                insertionPoint);
            //---------------------------------------------------------------------------

            return insertionPoint;
        }
예제 #10
0
        /// <summary>
        /// Search program operations implementing the
        /// AssignVar search plan operation
        /// are created and inserted into search program
        /// </summary>
        private SearchProgramOperation buildAssignVar(
            SearchProgramOperation insertionPoint,
            int currentOperationIndex,
            PatternVariable variable,
            Expression expression)
        {
            // generate c#-code-string out of condition expression ast
            SourceBuilder assignmentExpression = new SourceBuilder();
            expression.Emit(assignmentExpression);

            // get candidate from other element (the cast is simply the following type check)
            AssignVariableFromExpression assignVar =
                new AssignVariableFromExpression(
                    variable.Name,
                    TypesHelper.TypeName(variable.type),
                    assignmentExpression.ToString());
            insertionPoint = insertionPoint.Append(assignVar);

            //---------------------------------------------------------------------------
            // build next operation
            insertionPoint = BuildScheduledSearchPlanOperationIntoSearchProgram(
                currentOperationIndex + 1,
                insertionPoint);
            //---------------------------------------------------------------------------

            return insertionPoint;
        }