/* * geração das transitions baseado no protocolo da ação. */ public List <Transition> getTransitions(XmlNode node, MetaUnit unit, int initial, int final, int numStates, int numTransations) { List <Transition> transitions = new List <Transition> (); Queue <Transition> treat = new Queue <Transition> (); //Console.WriteLine("Initial {0} | Final {1} | numStates {2} | numTrans {3}", initial, final, numStates, numTransations); treat.Enqueue(new Transition(initial, final, node, numTransations++)); Transition t; XmlNode pivotNode, child, guardNode; XmlNodeList children; XmlAttribute attr; Condition condition; int initialState, finalState; bool repeat; initialState = finalState = 0; while (treat.Count > 0) { t = treat.Dequeue(); pivotNode = (XmlNode)t.Action; t.Action = null; transitions.Add(t); condition = null; attr = (XmlAttribute)pivotNode.Attributes.GetNamedItem("id"); if (attr != null) { t.AddId(attr.Value); } repeat = false; attr = (XmlAttribute)pivotNode.Attributes.GetNamedItem("repeat"); if (attr != null) { repeat = attr.Value.Equals("true"); } guardNode = pivotNode.SelectSingleNode("guard"); condition = null; //Console.WriteLine("[XmlLoaderUtil.getTransitions] Ação a avaliar... {0}", pivotNode.Name); if (pivotNode.Name.Equals("seq") || pivotNode.Name.Equals("par")) { if (guardNode != null) { condition = getCondition(guardNode); Transition tElse; initialState = numStates++; if (condition != null) //condition nao é else. { transitions.Add(new Transition(t.InitialState, initialState, new ExecutionAction(null, condition), Transition.INTERNAL_TRANSITION)); tElse = new Transition(t.InitialState, t.FinalState, Configuration.LAMBDA_TRANSITION, Transition.INTERNAL_TRANSITION); } else { tElse = new Transition(t.InitialState, initialState, Configuration.LAMBDA_TRANSITION, Transition.INTERNAL_TRANSITION); } tElse.IsElse = true; transitions.Add(tElse); } else { initialState = t.InitialState; } } switch (pivotNode.Name) { case "seq": children = pivotNode.ChildNodes; for (int r = 0; r < children.Count; r++) { child = children.Item(r); if (child.Name.Equals("guard")) { continue; } if (r == (children.Count - 1)) { if (repeat) { finalState = t.InitialState; } else { finalState = t.FinalState; } } else { finalState = numStates++; } treat.Enqueue(new Transition(initialState, finalState, child.FirstChild, numTransations++)); initialState = finalState; } break; case "par": children = pivotNode.ChildNodes; if (repeat) { finalState = numStates++; transitions.Add(new Transition(finalState, t.InitialState, Configuration.LAMBDA_TRANSITION, Transition.INTERNAL_TRANSITION)); } else { finalState = t.FinalState; } for (int r = 0; r < children.Count; r++) { child = children.Item(r); if (child.Name.Equals("guard")) { continue; } treat.Enqueue(new Transition(initialState, finalState, child.FirstChild, numTransations++)); } break; case "perform": bool isElse = false; initialState = t.InitialState; finalState = t.FinalState; child = pivotNode; if (guardNode != null) { condition = getCondition(guardNode); if (condition == null) { isElse = true; } } attr = (XmlAttribute)child.Attributes.GetNamedItem("slice_id"); //Console.WriteLine("[XmlLoaderUtil.getTransitions] Avaliando ação sobre a fatia {0}", attr.Value); string sliceName = ""; if (attr != null) { sliceName = attr.Value; } string methodName = child.Attributes.GetNamedItem("action_id").Value; //Console.WriteLine("[XmlLoaderUtil.getTransitions] Avaliando ação {0}", methodName); MetaAction selectedAction = null; if (sliceName.Equals("")) { //Console.WriteLine("[XmlLoaderUtil.getTransitions] unit {0} | action {1}", unit.Name, methodName); unit.Actions.TryGetValue(methodName, out selectedAction); //Console.WriteLine("[XmlLoaderUtil.getTransitions] Action {0} encontrada? {1}",methodName, selectedAction != null); if (selectedAction == null) { selectedAction = new MetaAction(); selectedAction.Id = generator.genId(); selectedAction.Name = methodName; selectedAction.Father = unit; unit.AddAction(methodName, selectedAction); } } else { MetaSlice slice = null; //Console.WriteLine("[XmlLoaderUtil.getTransitions] slice {0}", sliceName); unit.Slices.TryGetValue(sliceName, out slice); if (slice == null && candidateSlices != null) { candidateSlices.TryGetValue(sliceName, out slice); } if (slice != null) { //Console.WriteLine("[XmlLoaderUtil.getTransitions] slice {0} encontrada", sliceName); if (slice.Unit.Actions != null) { foreach (MetaAction mact in slice.Unit.Actions.Values) { if (mact.Name.Equals(methodName)) { selectedAction = mact; break; } } } if (selectedAction == null) { selectedAction = new MetaAction(); selectedAction.Id = generator.genId(); selectedAction.Name = methodName; selectedAction.Father = slice.Unit; slice.Unit.AddAction(methodName, selectedAction); } } } if (selectedAction != null) { Transition tst = new Transition(initialState, finalState, new ExecutionAction(selectedAction, condition), numTransations++); tst.IsElse = isElse; transitions.Add(tst); } else { throw new Exception("Fatia inexistente nesta unidade: " + sliceName); } break; default: throw new Exception("invalid action: " + pivotNode.Name); } } this.numStates = numStates; this.numTransations = numTransations; return(transitions); }
/* * Procura e retorna a fatia procurada. Ela corresponde a uma unidade de um innerComponent. * Caso não exista, a unidade será criada, atribuída ao innerComponent e ao final retornada. * * Caso innerComponent citado não exista, o retorno do método será nulo. */ public Dictionary <string, MetaSlice> getSlices(XmlNodeList sliceNodes) { Dictionary <string, MetaSlice> slices = new Dictionary <string, MetaSlice> (); List <MetaInnerComponent> innerList = new List <MetaInnerComponent>(); innerList.AddRange(innerComponents); if (candidateInnerComponents != null) { innerList.AddRange(candidateInnerComponents); } if (sliceNodes != null) { MetaUnit unit = null; MetaSlice slice = null; string innerName, unitName; int index; XmlAttribute attr; XmlNode sliceNode; IEnumerator senum = (IEnumerator)sliceNodes.GetEnumerator(); while (senum.MoveNext()) { sliceNode = (XmlNode)senum.Current; attr = (XmlAttribute)sliceNode.Attributes.GetNamedItem("inner"); innerName = attr.Value; attr = (XmlAttribute)sliceNode.Attributes.GetNamedItem("unit"); unitName = attr.Value; attr = (XmlAttribute)sliceNode.Attributes.GetNamedItem("index"); if (attr != null) { index = Convert.ToInt32(attr.Value); } else { index = 0; } foreach (MetaInnerComponent comp in innerList) { if (comp.Identifier.Equals(innerName)) { if (comp.Units != null) { //TODO deveria usar a indexacao do dictionary. O index pode trazer problemas. foreach (MetaUnit u in comp.Units.Values) { if (u.Name.Equals(unitName) /* && u.Index.Equals (index)*/) { unit = u; break; } } } if (unit == null) { unit = new MetaUnit(); unit.Id = generator.genId(); unit.Father = comp; unit.Name = unitName; unit.Index = index; comp.AddUnit(unit.Name, unit); } break; } } if (unit != null) { slice = new MetaSlice(unit); slice.Inner = innerName; unit = null; } if (slice != null) { slices.Add(innerName, slice); } else { throw new Exception("Erro ao carregar fatia: Inner component inexistente: " + innerName); } } } return(slices); }