public void Test_InsertStepAndTransition() { Model model = new Model("SFC Test 1"); ProcedureFunctionChart pfc = new ProcedureFunctionChart(model, "SFC 1", "", Guid.NewGuid()); IPfcStepNode t0 = pfc.CreateStep("START", "", Guid.Empty); IPfcStepNode t1 = pfc.CreateStep("FINISH", "", Guid.Empty); pfc.Bind(t0, t1); string structureString = PfcDiagnostics.GetStructure(pfc); Console.WriteLine("Structure is \r\n" + structureString); // Get reference to old successor IPfcNode pfcNode = pfc.Nodes["T_000"]; IPfcNode oldSuccessorNode = pfcNode.SuccessorNodes[0]; // Add the step IPfcStepNode newStep = pfc.CreateStep("STEP_1", "", Guid.Empty); IPfcTransitionNode newTrans = pfc.CreateTransition(); // We are adding a step following a transition - binding is from selectedTrans-newStep-newTrans-oldSuccessorStep pfc.Bind(pfcNode, newStep); pfc.Bind(newStep, newTrans); pfc.Bind(newTrans, oldSuccessorNode); // Disconnect old successor pfc.Unbind(pfcNode, oldSuccessorNode); structureString = PfcDiagnostics.GetStructure(pfc); Console.WriteLine("Structure is \r\n" + structureString); Assert.IsTrue(structureString.Equals("{START-->[L_000(SFC 1.Root)]-->T_000}\r\n{T_000-->[L_002(SFC 1.Root)]-->STEP_1}\r\n{STEP_1-->[L_003(SFC 1.Root)]-->T_001}\r\n{T_001-->[L_004(SFC 1.Root)]-->FINISH}\r\n")); }
private void _TestTransitionToTransitionBinding() { string testName = "Transition-to-Transition binding, maintaining SFC Compliance"; Model model = new Model("SFC Test 1"); ProcedureFunctionChart pfc = new ProcedureFunctionChart(model, "SFC 1", "", Guid.NewGuid()); IPfcTransitionNode s1 = pfc.CreateTransition("Alice", "", Guid.Empty); IPfcTransitionNode s2 = pfc.CreateTransition("Bob", "", Guid.Empty); //IPfcTransitionNode s3 = pfc.CreateTransition("Charlie", "", Guid.Empty); pfc.Bind(s1, s2); string structureString = PfcDiagnostics.GetStructure(pfc); Console.WriteLine("After a " + testName + ", structure is \r\n" + structureString); }
/// <summary> /// Evaluates the macro using the specified arguments. /// </summary> /// <param name="args">The arguments. This macro requires one argument, /// the transition that owns it, and it must be of type <see cref="T:IPfcTransitionNode"/></param> /// <returns> /// The evaluated representation of the macro. /// </returns> protected override string Evaluate(object[] args) { IPfcTransitionNode node = (IPfcTransitionNode)args[0]; if (node.PredecessorNodes.Count > 0) { StringBuilder sb = new StringBuilder(); sb.Append("( "); node.PredecessorNodes.ForEach(delegate(IPfcNode pred) { sb.Append("'" + pred.Name + "/BSTATUS' = '$recipe_state:Complete' AND "); }); string retval = sb.ToString(); retval = retval.Substring(0, retval.Length - " AND ".Length); retval += " )"; return(retval); } else { return("TRUE"); } }
private void UpdateClosureToken(IPfcTransitionNode closureTransition) { // Find the youngest common ancestor to all gazinta tokens. IPfcNode yca = DivergenceNodeFor(closureTransition); bool completeParallelConverge = AllParallelAndAtLeastOneOfEachSetOfSerialPathsContain(yca, closureTransition); ValidationToken replacementToken = completeParallelConverge ? // Are all of the root node's outbound // paths closed by the closure node? GetValidationData(yca).ValidationToken : // If so, its token is the closure token. GetValidationData(closureTransition.PredecessorNodes[0]).ValidationToken; // If not, pick one of the gazinta tokens. replacementToken.IncrementAlternatePathsOpen(); GetValidationData(closureTransition).ValidationToken = replacementToken; if (m_diagnostics) { Console.WriteLine("\t\tAssigning {0} ({1}) to {2} on its closure.", replacementToken.Name, replacementToken.AlternatePathsOpen, closureTransition.Name); } }
internal void ResolveUnknowns() { if (m_hasUnknowns) { List <ExpressionElement> temp = m_elements; m_elements = new List <ExpressionElement>(); foreach (ExpressionElement ee in temp) { if (ee is UnknownReferenceElement) { Guid guid = ee.Guid; if (m_participantDirectory.Contains(guid)) { m_elements.Add(m_participantDirectory[guid]); } else { IPfcTransitionNode trans = m_owner as IPfcTransitionNode; string msg; if (trans != null) { msg = string.Format("Failed to map Guid {0} into an object on behalf of {1} in Pfc {2}.", guid, trans.Name, trans.Parent.Name); } else { msg = string.Format("Failed to map Guid {0} into an object on behalf of {1}.", guid, m_owner); } throw new ApplicationException(msg); } } else { m_elements.Add(ee); } } m_hasUnknowns = false; } }
public void Test_SynchronizerConstruct_Transitions() { Model model = new Model("SFC Test 1"); ProcedureFunctionChart pfc = new ProcedureFunctionChart(model, "SFC 1", "", Guid.NewGuid()); IPfcTransitionNode t0 = pfc.CreateTransition("T_Alice", "", Guid.Empty); IPfcTransitionNode t1 = pfc.CreateTransition("T_Bob", "", Guid.Empty); IPfcTransitionNode t2 = pfc.CreateTransition("T_Charley", "", Guid.Empty); IPfcTransitionNode t3 = pfc.CreateTransition("T_David", "", Guid.Empty); IPfcTransitionNode t4 = pfc.CreateTransition("T_Edna", "", Guid.Empty); IPfcTransitionNode t5 = pfc.CreateTransition("T_Frank", "", Guid.Empty); IPfcTransitionNode t6 = pfc.CreateTransition("T_Gary", "", Guid.Empty); IPfcTransitionNode t7 = pfc.CreateTransition("T_Hailey", "", Guid.Empty); pfc.Synchronize(new IPfcTransitionNode[] { t0, t1, t2, t3 }, new IPfcTransitionNode[] { t4, t5, t6, t7 }); string structureString = PfcDiagnostics.GetStructure(pfc); string shouldBe = "{T_Alice-->[L_000(SFC 1.Root)]-->S_000}\r\n{S_000-->[L_001(SFC 1.Root)]-->T_000}\r\n{T_Bob-->[L_002(SFC 1.Root)]-->S_001}\r\n{S_001-->[L_003(SFC 1.Root)]-->T_000}\r\n{T_Charley-->[L_004(SFC 1.Root)]-->S_002}\r\n{S_002-->[L_005(SFC 1.Root)]-->T_000}\r\n{T_David-->[L_006(SFC 1.Root)]-->S_003}\r\n{S_003-->[L_007(SFC 1.Root)]-->T_000}\r\n{T_000-->[L_008(SFC 1.Root)]-->S_004}\r\n{S_004-->[L_009(SFC 1.Root)]-->T_Edna}\r\n{T_000-->[L_010(SFC 1.Root)]-->S_005}\r\n{S_005-->[L_011(SFC 1.Root)]-->T_Frank}\r\n{T_000-->[L_012(SFC 1.Root)]-->S_006}\r\n{S_006-->[L_013(SFC 1.Root)]-->T_Gary}\r\n{T_000-->[L_014(SFC 1.Root)]-->S_007}\r\n{S_007-->[L_015(SFC 1.Root)]-->T_Hailey}\r\n"; Console.WriteLine("After a synchronization of transitions, structure is \r\n" + structureString); Assert.AreEqual(structureString, shouldBe, "Structure should have been\r\n" + shouldBe + "\r\nbut it was\r\n" + structureString + "\r\ninstead."); if (m_runSFCs) { TestEvaluator testEvaluator = new TestEvaluator(new IPfcTransitionNode[] { t0, t1, t2, t3, t4, t5, t6, t7 }); testEvaluator.NextExpectedActivations = new IPfcTransitionNode[] { t0, t1, t2, t3, t4, t5, t6, t7 }; foreach (IPfcNode ilinkable in new IPfcTransitionNode[] { t0, t1, t2, t3 }) { Console.WriteLine("Incrementing " + ilinkable.Name + "."); //ilinkable.Increment(); throw new ApplicationException("PFCs are not currently executable."); } testEvaluator.NextExpectedActivations = new IPfcTransitionNode[] { }; // Ensure it's empty and all have fired. } }
public void Test_RemoveStep() { string testName = "PFC With Simultaneous Branch"; IModel model = new Model(testName); /* * START * + {T1} * STEP1 * + (T2) * STEP2 STEP3 * | + (T3) * | STEP4 * + (T4) * STEP5 * + (T5) * FINISH */ ProcedureFunctionChart pfc = new ProcedureFunctionChart(model, testName); IPfcNode startStep = pfc.CreateStep("START", string.Empty, Guid.NewGuid()); IPfcNode step1 = pfc.CreateStep("STEP1", string.Empty, Guid.NewGuid()); IPfcNode step2 = pfc.CreateStep("STEP2", string.Empty, Guid.NewGuid()); IPfcNode step3 = pfc.CreateStep("STEP3", string.Empty, Guid.NewGuid()); IPfcNode step4 = pfc.CreateStep("STEP4", string.Empty, Guid.NewGuid()); IPfcNode step5 = pfc.CreateStep("STEP5", string.Empty, Guid.NewGuid()); IPfcNode finishStep = pfc.CreateStep("FINISH", string.Empty, Guid.NewGuid()); IPfcNode t1 = pfc.CreateTransition("T1", string.Empty, Guid.NewGuid()); IPfcNode t2 = pfc.CreateTransition("T2", string.Empty, Guid.NewGuid()); IPfcNode t3 = pfc.CreateTransition("T3", string.Empty, Guid.NewGuid()); IPfcNode t4 = pfc.CreateTransition("T4", string.Empty, Guid.NewGuid()); IPfcNode t5 = pfc.CreateTransition("T4", string.Empty, Guid.NewGuid()); pfc.Bind(startStep, t1); pfc.Bind(t1, step1); pfc.Bind(step1, t2); pfc.Bind(t2, step2); pfc.Bind(t2, step3); pfc.Bind(step2, t4); pfc.Bind(step3, t3); pfc.Bind(t3, step4); pfc.Bind(step4, t4); pfc.Bind(t4, step5); pfc.Bind(step5, t5); pfc.Bind(t5, finishStep); /* Delete Step4 and T3*/ // Need to delete the predecessor transition IPfcTransitionNode predecessorTrans = (IPfcTransitionNode)step4.PredecessorNodes[0]; Assert.IsTrue(predecessorTrans.Name == t3.Name, "The predecessor trans should be T3"); IPfcStepNode predecessorStep = (IPfcStepNode)predecessorTrans.PredecessorNodes[0]; Assert.IsTrue(predecessorStep.Name == step3.Name, "The predecessor step should be STEP3"); IPfcTransitionNode successorTrans = (IPfcTransitionNode)step4.SuccessorNodes[0]; Assert.IsTrue(successorTrans.Name == t4.Name, "The successor trans should be T4"); // Connect the predecessor step to the successor transition pfc.Bind(predecessorStep, successorTrans); // Unbind the existing path from the predecessor step to the successor transition pfc.Unbind(predecessorStep, predecessorTrans); pfc.Unbind(predecessorTrans, step4); pfc.Unbind(step4, successorTrans); // Delete the predecessor transition pfc.Delete(predecessorTrans); // Delete step pfc.Delete(step4); Assert.IsTrue(pfc.Transitions[t3.Name] == null, "T3 Should be Deleted"); Assert.IsTrue(pfc.Steps[step4.Name] == null, "Step4 Should be Deleted"); }
public TransitionStateMachine StateMachineForTransition(IPfcTransitionNode trans) { return(m_transitionStateMachines[trans]); }
public void TestSequencers() { Model model = new Model("MyTestModel"); ProcedureFunctionChart pfc = new ProcedureFunctionChart(model, "RootPfc"); pfc.ExecutionEngineConfiguration = new ExecutionEngineConfiguration(); // Start // | // + T_Start // | // ===================================== // | | | | | // Step0 Step1 Step2 Step3 Step4 // | | | | | // ===================================== // | // + Finis // // (We want to run these in order "Step3", "Step1", "Step4", "Step2", "Step0") #region Create PFC IPfcStepNode start = pfc.CreateStep("Start", null, Guid.NewGuid()); IPfcTransitionNode startTrans = pfc.CreateTransition("T_Start", null, Guid.NewGuid()); pfc.Bind(start, startTrans); IPfcTransitionNode finis = pfc.CreateTransition("Finish", null, Guid.NewGuid()); for (int i = 0; i < 5; i++) { IPfcStepNode step = pfc.CreateStep("Step" + i, null, Guid.NewGuid()); pfc.Bind(startTrans, step); pfc.Bind(step, finis); } #endregion Create PFC Guid sequencerKey = Guid.NewGuid(); string[] stepSeq = new string[] { "Step4", "Step3", "Step2", "Step1", "Step0" }; for (int n = 0; n < 10; n++) { Console.WriteLine("\r\n\r\n========================================================\r\nStarting test iteration # " + n + ":\r\n"); stepSeq = Shuffle(stepSeq); Console.WriteLine("Expecting sequence " + StringOperations.ToCommasAndAndedList(new List <string>(stepSeq))); int j = 0; StringBuilder sb = new StringBuilder(); foreach (string stepNodeName in stepSeq) { IPfcStepNode step = pfc.Steps[stepNodeName]; step.Precondition = new Sequencer(sequencerKey, j++).Precondition; step.LeafLevelAction = new PfcAction(delegate(PfcExecutionContext pfcec, StepStateMachine ssm) { sb.Append("Running " + ssm.MyStep.Name + " "); }); } model.Executive.RequestEvent( new ExecEventReceiver(pfc.Run), DateTime.MinValue, 0.0, new PfcExecutionContext(pfc, "PFCEC", null, Guid.NewGuid(), null), ExecEventType.Detachable); pfc.Model.Start(); Console.Out.Flush(); string tgtString = string.Format(@"Running {0} Running {1} Running {2} Running {3} Running {4} ", stepSeq[0], stepSeq[1], stepSeq[2], stepSeq[3], stepSeq[4]); System.Diagnostics.Debug.Assert(sb.ToString().Equals(tgtString)); pfc.Model.Executive.Reset(); Console.WriteLine("========================================================"); } }
public static ProcedureFunctionChart CreateRandomPFC(int nSteps, int seed) { Guid mask = GuidOps.FromString(string.Format("{0}, {1}", nSteps, seed)); Guid seedGuid = GuidOps.FromString(string.Format("{0}, {1}", seed, nSteps)); int rotate = 3; GuidGenerator guidGen = new GuidGenerator(seedGuid, mask, rotate); PfcElementFactory pfcef = new PfcElementFactory(guidGen); ProcedureFunctionChart pfc = new ProcedureFunctionChart(new Highpoint.Sage.SimCore.Model("Test model", Guid.NewGuid()), "Name", "", guidGen.Next(), pfcef); IPfcStepNode start = pfc.CreateStep("Start", "", Guid.Empty); IPfcStepNode step1 = pfc.CreateStep("Step1", "", Guid.Empty); IPfcStepNode finish = pfc.CreateStep("Finish", "", Guid.Empty); pfc.Bind(start, step1); pfc.Bind(step1, finish); Console.WriteLine("Seed = {0}.", seed); Random r = new Random(seed); while (pfc.Steps.Count < nSteps) { double steeringValue = r.NextDouble(); if (steeringValue < .5) { // Insert a step in series. IPfcLinkElement link = pfc.Links[r.Next(0, pfc.Links.Count - 1)]; IPfcStepNode stepNode = pfc.CreateStep(); pfc.Bind(link.Predecessor, stepNode); pfc.Bind(stepNode, link.Successor); //Console.WriteLine("Inserted {0} between {1} and {2}.", stepNode.Name, link.Predecessor.Name, link.Successor.Name); link.Detach(); } else if (steeringValue < .666) { // Insert a step in parallel. for (int i = 0; i < 50; i++) // Try, but give up if don't find suitable step. { IPfcStepNode target = pfc.Steps[r.Next(0, pfc.Steps.Count - 1)]; if (target.PredecessorNodes.Count == 1 && target.SuccessorNodes.Count == 1) { IPfcStepNode stepNode = pfc.CreateStep(); pfc.Bind(target.PredecessorNodes[0], stepNode); pfc.Bind(stepNode, target.SuccessorNodes[0]); //Console.WriteLine("Inserted {0} parallel to {1}.", stepNode.Name, target.Name); break; } } } else if (steeringValue < .833) { // Insert a branch for (int i = 0; i < 50; i++) // Try, but give up if don't find suitable step. { IPfcStepNode step = pfc.Steps[r.Next(0, pfc.Steps.Count - 1)]; if (step.PredecessorNodes.Count == 1 && step.SuccessorNodes.Count == 1) { IPfcStepNode entryStep = pfc.CreateStep(step.Name + "_IN", null, Guid.Empty); IPfcStepNode exitStep = pfc.CreateStep(step.Name + "_OUT", null, Guid.Empty); IPfcStepNode leftStep = pfc.CreateStep(step.Name + "_LFT", null, Guid.Empty); IPfcStepNode rightStep = pfc.CreateStep(step.Name + "_RGT", null, Guid.Empty); pfc.Bind(step.PredecessorNodes[0], entryStep); pfc.Bind(entryStep, leftStep); pfc.Bind(entryStep, rightStep); pfc.Bind(leftStep, exitStep); pfc.Bind(rightStep, exitStep); pfc.Bind(exitStep, step.SuccessorNodes[0]); pfc.Unbind(step.PredecessorNodes[0], step); pfc.Unbind(step, step.SuccessorNodes[0]); //Console.WriteLine("Inserted a branch in place of {0}.", step.Name); break; } } } else { for (int i = 0; i < 50; i++) // Try, but give up if don't find suitable step. { IPfcTransitionNode trans = pfc.Transitions[r.Next(0, pfc.Transitions.Count - 1)]; if (trans.PredecessorNodes.Count == 1 && trans.SuccessorNodes.Count == 1) { IPfcStepNode successor = (IPfcStepNode)trans.SuccessorNodes[0]; IPfcStepNode subject = pfc.CreateStep(); pfc.Bind(trans, subject); pfc.Bind(subject, successor); pfc.Unbind(trans, successor); IPfcStepNode loopback = pfc.CreateStep(); pfc.Bind(subject, loopback); pfc.Bind(loopback, subject); //Console.WriteLine("Inserted {0} between {1} and {2}, and created a branchback around it using {3}.", // subject.Name, trans.PredecessorNodes[0].Name, successor.Name, loopback.Name); break; } } //// insert a loopback //IPfcStepNode step; //do { step = pfc.Steps[r.Next(0, pfc.Steps.Count - 1)]; } while (step == start || step == finish); //IPfcStepNode newNode = pfc.CreateStep(); //pfc.Bind(step, newNode); //pfc.Bind(newNode, step); //Console.WriteLine("Inserted a loopback around {0} using new step, {1}.", step.Name, newNode.Name); } //IPfcStepNode origin = pfc.Steps[r.Next(0, pfc.Steps.Count - 1)]; //if (origin.Equals(finish)) continue; //if (r.NextDouble() < .2) { // IPfcStepNode stepNode = pfc.CreateStep(); // IPfcNode target = origin.SuccessorNodes[r.Next(0, origin.SuccessorNodes.Count - 1)]; // // Insert a step in series. // pfc.Bind(origin, stepNode); // pfc.Bind(stepNode, target); // pfc.Unbind(origin, target); // Console.WriteLine("Inserting {0} between {1} and {2}.", // stepNode.Name, origin.Name, target.Name); //} else if (r.NextDouble() < .55) { // // Insert a step in parallel // if (origin.PredecessorNodes.Count == 1 && origin.SuccessorNodes.Count == 1) { // origin = origin.PredecessorNodes[0]; // target = origin.SuccessorNodes[0]; // pfc.Bind(origin, stepNode); // pfc.Bind(stepNode, target); // Console.WriteLine("Inserting {0} parallel to {1} - between {2} and {3}.", // stepNode.Name, parallelTo.Name, origin.Name, target.Name); // } //} else { // // Insert a loopback or branchforward. // IPfcNode target = null; // string parallelType = null; // if (!origin.PredecessorNodes.Contains(start) && r.NextDouble() < .5) { // target = origin; // parallelType = "loopback"; // } else if (origin.SuccessorNodes.Count==1 && origin.PredecessorNodes==1) { // target = origin.SuccessorNodes[r.Next(0, origin.SuccessorNodes.Count - 1)]; // parallelType = "branch forward"; // } // if (target != null) { // IPfcStepNode stepNode = pfc.CreateStep(); // pfc.Bind(origin, stepNode); // pfc.Bind(stepNode, target); // Console.WriteLine("Inserting {0} around {1} to {2}, with {3} on the new alternate path.", // parallelType, origin.Name, target.Name, stepNode.Name); // } //} } return(pfc); }
public TransitionStateMachine(IPfcTransitionNode myTransition) { m_myTransition = myTransition; m_predecessors = new List <StepStateMachine>(); m_successors = new List <StepStateMachine>(); }