public void parseTemporalOperator(Property property, out StateFormula state1, out StateFormula state2, ref bool is_ctl, out int temp) { Property property1, property2; if (property.GetType() == typeof(Next)) { property1 = ((Next)property).Operand; parseStateFormula(property1, out state1, ref is_ctl); state2 = new SError(); temp = 0; } else if (property.GetType() == typeof(Until)) { property1 = ((Until)property).LeftOperand; property2 = ((Until)property).RightOperand; parseStateFormula(property1, out state1, ref is_ctl); parseStateFormula(property2, out state2, ref is_ctl); temp = 1; } else if (property.GetType() == typeof(Eventually)) { property1 = ((Eventually)property).Operand; parseStateFormula(property1, out state1, ref is_ctl); state2 = new SError(); temp = 2; } else if (property.GetType() == typeof(Always)) { property1 = ((Always)property).Operand; parseStateFormula(property1, out state1, ref is_ctl); state2 = new SError(); temp = 3; } else if (property.GetType() == typeof(WeakUntil)) { property1 = ((WeakUntil)property).LeftOperand; property2 = ((WeakUntil)property).RightOperand; parseStateFormula(property1, out state1, ref is_ctl); parseStateFormula(property2, out state2, ref is_ctl); temp = 4; } else { state1 = new SError(); state2 = new SError(); temp = -1; is_ctl = false; } }
/* * Uses the factory which we created at the very beginning to * do the actual modelchecking * For each state formula it gets the satisfaction set * by using the state forumla class' method * Then it checks whether the initial state is in that set or not */ public void ModelChecker <T>(TransitionSystem <T> transition_system, LinkedList <T> states, StateFormula state_formula, out bool isSatiesfied, ref Pre_Compute_Factory <T> factory) where T : struct, Modest.Exploration.IState <T> { HashSet <T> sat; state_formula.isSatiesfied <T>(transition_system, states, out sat, ref factory); T initialState; transition_system.GetInitialState(out initialState); if (sat.Contains(initialState)) { isSatiesfied = true; } else { isSatiesfied = false; } }
public void AnalyzeTransitionSystem <T>(TransitionSystem <T> transitionSystem, ModelProperty[] properties) // called from Program.cs where T : struct, Modest.Exploration.IState <T> { /* * // Implement your transition system analysis procedures here * // For illustration, let's count the immediate successors of the initial state: * var successors = new HashSet<T>(); // the state types implement proper .GetHashCode and .Equals methods based on structural equality * T initialState, successorState; * transitionSystem.GetInitialState(out initialState); * foreach(var transition in transitionSystem.GetTransitions(ref initialState)) * { * transitionSystem.GetTargetState(ref initialState, transition, out successorState); * successors.Add(successorState); * // We could evaluate properties using transitionSystem.HasAtomicProposition(ref successorState, ...) here; * // also see the class diagram for properties (file Properties-Classes.png). * } * Console.WriteLine("The initial state has " + successors.Count.ToString(CI.InvariantCulture) + " distinct immediate successor state" + (successors.Count == 1 ? string.Empty : "s") + "."); */ // Write Tests into Files //var testAnalyzer = new TestAnalyzer(); //testAnalyzer.writeTestFiles<T>(transitionSystem, properties); T initialState; transitionSystem.GetInitialState(out initialState); var newStates = new Queue <T>(); newStates.Enqueue(initialState); /* * Use this factory to pre_compute everything * See class implementation for more information */ Pre_Compute_Factory <T> factory = new Pre_Compute_Factory <T>(transitionSystem); HashSet <T> states = factory.getStates(); Console.WriteLine("States: " + factory.number_states + "\n"); if (factory.terminal_encountered) { Console.WriteLine("Error: deadlocks detected\n"); return; } // Transform properties in State_Formulas; var state_formulas = new Dictionary <String, StateFormula>(); foreach (var model_property in properties) { Property property = model_property.Property; String name = model_property.Name; StateFormula complete_formula = new SError(); bool is_ctl = true; parseStateFormula(property, out complete_formula, ref is_ctl); if (!is_ctl) { Console.WriteLine(name + ": not supported \n"); } else { state_formulas.Add(name, complete_formula); } } //Transform into ENF var state_ENF = new Dictionary <String, StateFormula>(); foreach (var key_formula in state_formulas) { String name = key_formula.Key; StateFormula enf_formula = key_formula.Value.existentialNormalForm(); state_ENF.Add(key_formula.Key, enf_formula); } // Now do the model checking foreach (var entry in state_ENF) { String name = entry.Key; StateFormula state_formula = entry.Value; bool isSatisfied; LinkedList <T> linked_states = new LinkedList <T>(); foreach (var entry_state in states) { linked_states.AddLast(entry_state); } ModelChecker <T>(transitionSystem, linked_states, state_formula, out isSatisfied, ref factory); if (isSatisfied) { Console.WriteLine(name + ": true \n"); } else { Console.WriteLine(name + ": false \n"); } } Environment.Exit(0); }
// This function does not get called anymore // But im still leaving it here in case it is needed later /* * public void traverseTree<T>(TransitionSystem<T> transitionSystem, ref HashSet<T> already_expanded, ref Queue<T> newStates, ref T state_a, ref bool terminalStatesEncountered) * where T : struct, Modest.Exploration.IState<T> * { * * * int newSize = newStates.Count; * * * * while (newSize > 0) * { * //Console.WriteLine(newSize); * //Console.WriteLine(newSize); * int count = 0; * var state = newStates.Dequeue(); * * //if (!(oldStates.Contains(state))) * //already_expanded.Add(state); * T successor; * * foreach (var transition in transitionSystem.GetTransitions(ref state)) * { * transitionSystem.GetTargetState(ref state, transition, out successor); * * if (already_expanded.Add(successor)) * { * newStates.Enqueue(successor); * //newestStates.Add(successor); * } * * count++; * } * * newSize = newStates.Count; * * // If no transition has been encountered for this state it was terminal * if (count == 0) * terminalStatesEncountered = true; * } * * * } */ /* * Parses the property into our own tree structure */ public void parseStateFormula(Property property, out StateFormula result, ref bool is_ctl) { StateFormula state1, state2; Property property1, property2; int temp; if (property.GetType() == typeof(True)) { result = new SBoolean(true); } else if (property.GetType() == typeof(False)) { result = new SBoolean(false); } else if (property.GetType() == typeof(AtomicProposition)) { result = new SAtomic((AtomicProposition)property); } else if (property.GetType() == typeof(And)) { property1 = ((And)property).LeftOperand; property2 = ((And)property).RightOperand; parseStateFormula(property1, out state1, ref is_ctl); parseStateFormula(property2, out state2, ref is_ctl); result = new SAnd(state1, state2); } else if (property.GetType() == typeof(Or)) { property1 = ((Or)property).LeftOperand; property2 = ((Or)property).RightOperand; parseStateFormula(property1, out state1, ref is_ctl); parseStateFormula(property2, out state2, ref is_ctl); result = new SOr(state1, state2); } else if (property.GetType() == typeof(Not)) { property1 = ((Not)property).Operand; parseStateFormula(property1, out state1, ref is_ctl); result = new SNot(state1); } else if (property.GetType() == typeof(Exists)) { property1 = ((Exists)property).Operand; parseTemporalOperator(property1, out state1, out state2, ref is_ctl, out temp); switch (temp) { case 0: result = new SENext(state1); break; case 1: result = new SEUntil(state1, state2); break; case 2: result = new SEFinally(state1); break; case 3: result = new SEAlways(state1); break; case 4: result = new SEWeakUntil(state1, state2); break; default: result = new SError(); is_ctl = false; break; } } else if (property.GetType() == typeof(ForAll)) { property1 = ((ForAll)property).Operand; parseTemporalOperator(property1, out state1, out state2, ref is_ctl, out temp); switch (temp) { case 0: result = new SANext(state1); break; case 1: result = new SAUntil(state1, state2); break; case 2: result = new SAFinally(state1); break; case 3: result = new SAAlways(state1); break; case 4: result = new SAWeakUntil(state1, state2); break; default: result = new SError(); is_ctl = false; break; } } else { is_ctl = false; result = new SError(); } }