/// <summary> /// This method checks whether the found counterexample is spurious or not. /// This checking only works for abstraction for parameterized systems. /// </summary> /// <returns></returns> protected virtual bool IsCounterExampleSpurious() { Stack <ConfigurationBase> working = new Stack <ConfigurationBase>(1024); List <ConfigurationBase> ConcreteCounterExampleTrace = new List <ConfigurationBase>(64); working.Push(InitialStep); Stack <int> depthStack = new Stack <int>(1024); depthStack.Push(0); List <int> depthList = new List <int>(1024); StringHashTable visited = new StringHashTable(1024); visited.Add("0-" + InitialStep.GetID()); do { ConfigurationBase current = working.Pop(); int depth = depthStack.Pop(); if (depth > 0) { while (depthList[depthList.Count - 1] >= depth) { int lastIndex = depthList.Count - 1; depthList.RemoveAt(lastIndex); ConcreteCounterExampleTrace.RemoveAt(lastIndex); } } ConcreteCounterExampleTrace.Add(current); depthList.Add(depth); if (ConcreteCounterExampleTrace.Count == VerificationOutput.CounterExampleTrace.Count) { VerificationOutput.CounterExampleTrace = ConcreteCounterExampleTrace; Ultility.Ultility.CutNumber = 2; return(false); } else { ConfigurationBase abstractStep = VerificationOutput.CounterExampleTrace[depth + 1]; IEnumerable <ConfigurationBase> steps = current.MakeOneMove(abstractStep.Event); //for (int j = 0; j < steps.Length; j++) foreach (ConfigurationBase step in steps) { if (abstractStep.EqualsV(step)) { string tmp = (depth + 1) + "-" + step.GetID(); if (!visited.ContainsKey(tmp)) { working.Push(step); depthStack.Push(depth + 1); visited.Add(tmp); } } } } } while (working.Count > 0); return(true); }
/// <summary> /// To get all states which can be reached by tau-transitions only; meanwhile, identify which of them are divergent states. /// </summary> /// <param name="States"></param> /// <returns></returns> private static bool IsDivergent(ConfigurationBase States) { Dictionary<string, int[]> DFSData = new Dictionary<string, int[]>(); Dictionary<string, List<string>> transitions = new Dictionary<string, List<string>>(); List<string> StronglyConnectedComponets = new List<string>(); Stack<ConfigurationBase> TaskStack = new Stack<ConfigurationBase>(); TaskStack.Push(States); DFSData.Add(States.GetID(), new int[] { VISITED_NOPREORDER, 0 }); transitions.Add(States.GetID(), new List<string>()); Stack<ConfigurationBase> stepStack = new Stack<ConfigurationBase>(); //# Preorder counter int ii = 0; //store the expended event step of a node to avoid multiple invocation of the make one move. Dictionary<string, List<ConfigurationBase>> ExpendedNode = new Dictionary<string, List<ConfigurationBase>>(); do { ConfigurationBase pair = TaskStack.Peek(); string v = pair.GetID(); List<string> outgoing = transitions[v]; int[] nodeData = DFSData[v]; if (nodeData[0] == VISITED_NOPREORDER) { nodeData[0] = ii; ii++; } bool done = true; if (ExpendedNode.ContainsKey(v)) { List<ConfigurationBase> list = ExpendedNode[v]; if (list.Count > 0) { //transverse all steps for (int k = list.Count - 1; k >= 0; k--) { ConfigurationBase step = list[k]; string tmp = step.GetID(); //if the step is a unvisited step //if (!preorder.ContainsKey(t)) if (DFSData[tmp][0] == VISITED_NOPREORDER) { //only add the first unvisited step //for the second or more unvisited steps, ignore at the monent if (done) { TaskStack.Push(step); //procPath.Add(step.GetID()); done = false; list.RemoveAt(k); } } else { list.RemoveAt(k); } } } } else { List<ConfigurationBase> product = new List<ConfigurationBase>(pair.MakeOneMove(Constants.TAU)); //.AmpleTau(procPath, false); for (int k = product.Count - 1; k >= 0; k--) { ConfigurationBase step = product[k]; string tmp = step.GetID(); //if (DFSData.ContainsKey(tmp)) int[] data; if (DFSData.TryGetValue(tmp, out data)) { //int t = visited[stateString]; outgoing.Add(tmp); //if this node is still not visited //if (!preorder.ContainsKey(tmp)) if (data[0] == VISITED_NOPREORDER) { //only put the first one to the work list stack. //if there are more than one node to be visited, //simply ignore them and keep its event step in the list. if (done) { TaskStack.Push(step); done = false; product.RemoveAt(k); } else { product[k] = step; } } //this node is truly visited. can be removed else { product.RemoveAt(k); } } else { DFSData.Add(tmp, new int[] { VISITED_NOPREORDER, 0 }); transitions.Add(tmp, new List<string>(8)); outgoing.Add(tmp); //only put the first one into the stack. if (done) { TaskStack.Push(step); done = false; product.RemoveAt(k); } else { product[k] = step; } } } //create the remaining steps as the expending list for v ExpendedNode.Add(v, product); } if (done) { int lowlinkV = nodeData[0]; int preorderV = lowlinkV; bool selfLoop = false; for (int j = 0; j < outgoing.Count; j++) { string w = outgoing[j]; if (w == v) { selfLoop = true; } int[] wdata = DFSData[w]; if (wdata[0] != SCC_FOUND) { if (wdata[0] > preorderV) { lowlinkV = Math.Min(lowlinkV, wdata[1]); } else { lowlinkV = Math.Min(lowlinkV, wdata[0]); } } } nodeData[1] = lowlinkV; TaskStack.Pop(); if (lowlinkV == preorderV) { StronglyConnectedComponets.Add(v); nodeData[0] = SCC_FOUND; while (stepStack.Count > 0 && DFSData[stepStack.Peek().GetID()][0] > preorderV) { ConfigurationBase s = stepStack.Pop(); string tmp = s.GetID(); //int k = visited[tmp]; StronglyConnectedComponets.Add(tmp); //scc_found.Add(tmp); } //outgoing.Count == 0 --> deadlock, we need to check //outgoing.Count == 0 //StronglyConnectedComponets.Count > 1 || selfLoop -> non-trivial case, we need to check if (StronglyConnectedComponets.Count > 1 || selfLoop) { return true; } foreach (string componet in StronglyConnectedComponets) { ExpendedNode.Remove(componet); } StronglyConnectedComponets.Clear(); } else { stepStack.Push(pair); } } } while (TaskStack.Count > 0); foreach (string key in DFSData.Keys) { VisitedNonDivStates.Add(key); } return false; }
private static Automata BuildAutomataWithRefusalsAndDiv(ConfigurationBase InitSpecStep) { Dictionary<string, FAState> visited = new Dictionary<string, FAState>(); Stack<ConfigurationBase> working = new Stack<ConfigurationBase>(1024); working.Push(InitSpecStep); Automata auto = new Automata(); FAState init = auto.AddState(); auto.SetInitialState(init); visited.Add(InitSpecStep.GetID(), init); do { ConfigurationBase current = working.Pop(); FAState currentState = visited[current.GetID()]; if (current.IsDivergent()) { currentState.IsDiv = true; } else { IEnumerable<ConfigurationBase> list = current.MakeOneMove(); List<string> negateRefusal = new List<string>(); bool hasTau = false; //for (int i = 0; i < list.Length; i++) foreach (ConfigurationBase step in list) { //ConfigurationBase step = list[i]; if (step.Event == Constants.TAU) { hasTau = true; } else { negateRefusal.Add(step.Event); } FAState target; string nextID = step.GetID(); if (visited.ContainsKey(nextID)) { target = visited[nextID]; } else { target = auto.AddState(); working.Push(step); visited.Add(nextID, target); } auto.AddTransition(currentState, step.Event, target); } if (hasTau) { currentState.NegatedRefusal = null; } else { currentState.NegatedRefusal = negateRefusal; } } } while (working.Count > 0); return auto; }
public bool IsDivergent() { Stack <ConfigurationBase> working = new Stack <ConfigurationBase>(); List <string> path = new List <string>(100); StringHashTable visited = new StringHashTable(100); //The following are for identifying the current path. Stack <int> depthStack = new Stack <int>(1024); depthStack.Push(0); List <int> depthList = new List <int>(1024); //The above are for identifying the current path. working.Push(this); visited.Add(GetID()); while (working.Count > 0) { ConfigurationBase current = working.Pop(); IEnumerable <ConfigurationBase> nextStates = current.MakeOneMove(Constants.TAU); //The following are for identifying the current path. int depth = depthStack.Pop(); if (depth > 0) { while (depthList[depthList.Count - 1] >= depth) { int lastIndex = depthList.Count - 1; depthList.RemoveAt(lastIndex); path.RemoveAt(lastIndex); } } path.Add(current.GetID()); depthList.Add(depth); if (nextStates != null) { //for (int i = 0; i < nextStates.Length; i++) foreach (ConfigurationBase next in nextStates) { //ConfigurationBase next = nextStates[i]; string ID = next.GetID(); if (path.Contains(ID)) { return(true); } else { if (!visited.ContainsKey(ID)) { visited.Add(ID); working.Push(next); depthStack.Push(depth + 1); } } } } } return(false); }