1 package Analysis.Scheduling;
5 import Analysis.TaskStateAnalysis.FEdge;
6 import Analysis.TaskStateAnalysis.FlagState;
9 /** This class holds flag transition diagram(s) can be put on one core.
11 public class ScheduleNode extends GraphNode implements Cloneable{
16 private static int nodeID=0;
17 public static int colorID = 0;
19 private Vector<ClassNode> classNodes;
20 Vector<ScheduleEdge> scheduleEdges;
22 private int executionTime;
25 * @param cd ClassDescriptor
28 public ScheduleNode(int gid) {
29 this.uid = ScheduleNode.nodeID++;
32 this.executionTime = -1;
33 this.classNodes = null;
34 this.scheduleEdges = null;
37 public ScheduleNode(ClassNode cn, int gid) {
38 this.uid = ScheduleNode.nodeID++;
41 this.classNodes = new Vector<ClassNode>();
42 this.scheduleEdges = new Vector<ScheduleEdge>();
43 this.classNodes.add(cn);
44 this.addEdge(cn.getEdgeVector());
45 this.executionTime = -1;
56 public void setCid(int cid) {
60 public String toString() {
61 String temp = new String("");
62 for(int i = 0; i < classNodes.size(); i++) {
63 temp += classNodes.elementAt(i).getClassDescriptor().toString() + ", ";
65 temp += getTextLabel();
69 public Vector getClassNodes() {
73 public Iterator getClassNodesIterator() {
74 if(classNodes == null) {
77 return classNodes.iterator();
80 public void resetClassNodes() {
84 public Vector getScheduleEdges() {
88 public Iterator getScheduleEdgesIterator() {
89 if(scheduleEdges == null) {
92 return scheduleEdges.iterator();
95 public void resetScheduleEdges() {
99 public int getExeTime() {
100 if(this.executionTime == -1) {
103 } catch (Exception e) {
107 return this.executionTime;
110 public void calExeTime() throws Exception {
111 if(this.classNodes.size() != 1) {
112 throw new Exception("Error: there are multiple ClassNodes inside the ScheduleNode when calculating executionTime");
114 ClassNode cn = this.classNodes.elementAt(0);
116 throw new Error("Error: Non-sorted ClassNode!");
118 this.executionTime = cn.getFlagStates().elementAt(0).getExeTime();
121 /** Tests for equality of two flagstate objects.
124 public boolean equals(Object o) {
125 if (o instanceof ScheduleNode) {
126 ScheduleNode fs=(ScheduleNode)o;
127 if(fs.gid == this.gid) {
128 if(fs.uid != this.uid) {
131 if(fs.cid != this.cid) {
135 if ((fs.executionTime != this.executionTime)){
138 if(fs.classNodes != null) {
139 if(!fs.classNodes.equals(classNodes)) {
142 } else if(classNodes != null) {
150 public int hashCode() {
151 int hashcode = gid^uid^cid^executionTime;
152 if(this.classNodes != null) {
153 hashcode ^= classNodes.hashCode();
158 public String getLabel() {
159 return "cluster" + uid;
162 public String getTextLabel() {
170 public Object clone(Hashtable<ClassNode, ClassNode> cn2cn, int gid) {
171 ScheduleNode o = null;
173 o = (ScheduleNode)super.clone();
174 } catch(CloneNotSupportedException e){
177 o.uid = ScheduleNode.nodeID++;
180 // Clone all the internal ClassNodes and ScheduleEdges
181 Vector<ClassNode> tcns = new Vector<ClassNode>();
182 Vector<ScheduleEdge> tses = new Vector<ScheduleEdge>();
184 for(i = 0; i < this.classNodes.size(); i++) {
185 ClassNode tcn = this.classNodes.elementAt(i);
186 ClassNode cn = (ClassNode)tcn.clone();
187 cn.setScheduleNode(o);
191 for(i = 0; i < this.scheduleEdges.size(); i++) {
192 ScheduleEdge temp = this.scheduleEdges.elementAt(i);
193 ScheduleEdge se = null;
194 switch(temp.getType()) {
195 case ScheduleEdge.NEWEDGE: {
196 se = new ScheduleEdge(o, "new", temp.getFstate(), ScheduleEdge.NEWEDGE, gid);
197 se.setProbability(temp.getProbability());
198 se.setNewRate(temp.getNewRate());
201 case ScheduleEdge.TRANSEDGE: {
202 se = new ScheduleEdge(o, "transmit", temp.getFstate(), ScheduleEdge.TRANSEDGE, gid);
203 se.setProbability(temp.getProbability());
204 se.setNewRate(temp.getNewRate());
208 se.setSourceCNode(cn2cn.get(temp.getSourceCNode()));
209 se.setTargetCNode(cn2cn.get(temp.getTargetCNode()));
210 se.setTransTime(temp.getTransTime());
211 se.setFEdge(temp.getFEdge());
212 se.setTargetFState(temp.getTargetFState());
217 o.scheduleEdges = tses;
221 o.inedges = new Vector();
222 o.edges = new Vector();
226 public void mergeSEdge(ScheduleEdge se) throws Exception {
227 ScheduleNode sn = (ScheduleNode)se.getTarget();
228 Vector<ClassNode> targetCNodes = (Vector<ClassNode>)sn.getClassNodes();
229 Vector<ScheduleEdge> targetSEdges = (Vector<ScheduleEdge>)sn.getScheduleEdges();
231 for(int i = 0; i < targetCNodes.size(); i++) {
232 targetCNodes.elementAt(i).setScheduleNode(this);
235 if(classNodes == null) {
236 classNodes = targetCNodes;
237 scheduleEdges = targetSEdges;
239 if(targetCNodes.size() != 0) {
240 classNodes.addAll(targetCNodes);
242 if(targetSEdges.size() != 0) {
243 scheduleEdges.addAll(targetSEdges);
248 if(ScheduleEdge.TRANSEDGE == se.getType()) {
252 // merge the split ClassNode of same class
253 FlagState sfs = se.getFstate();
254 FlagState tfs = se.getTargetFState();
255 ClassNode scn = se.getSourceCNode();
256 ClassNode tcn = se.getTargetCNode();
257 sfs.getEdgeVector().addAll(tfs.getEdgeVector());
258 // merge the subtree whose root is nfs from the whole flag transition tree
259 Vector<FlagState> sfss = scn.getFlagStates();
260 sfss.addAll(tcn.getFlagStates());
261 sfss.removeElement(tfs);
262 classNodes.removeElement(tcn);
264 // flush the exeTime of fs and its ancestors
266 Queue<FlagState> toiterate = new LinkedList<FlagState>();
268 while(!toiterate.isEmpty()) {
269 FlagState tmpfs = toiterate.poll();
270 int ttime = tmpfs.getExeTime();
271 Iterator it_inedges = tmpfs.inedges();
272 while(it_inedges.hasNext()) {
273 FEdge fEdge = (FEdge)it_inedges.next();
274 FlagState temp = (FlagState)fEdge.getSource();
275 int time = fEdge.getExeTime() + ttime;
276 if(temp.getExeTime() > time) {
277 temp.setExeTime(time);
284 // redirct internal ScheduleEdge from tcn to scn
285 for(int i = 0; i < targetSEdges.size(); ++i) {
286 ScheduleEdge tmpse = targetSEdges.elementAt(i);
287 if(tmpse.getSourceCNode().equals(tcn)) {
288 tmpse.setSourceCNode(scn);
292 // redirect external ScheduleEdges to this ScheduleNode
293 // and scn if it is originally from tcn
294 Iterator it_edges = sn.edges();
295 while(it_edges.hasNext()) {
296 ScheduleEdge tse = (ScheduleEdge)it_edges.next();
298 if(tse.getSourceCNode().equals(tcn)) {
299 tse.setSourceCNode(scn);
301 this.edges.addElement(tse);
306 // As all tasks inside one ScheduleNode are executed sequentially,
307 // simply add the execution time of all the ClassNodes inside one ScheduleNode.
308 if(this.executionTime == -1) {
309 throw new Exception("Error: ScheduleNode without initiate execution time when analysising.");
311 if(this.executionTime < sn.getExeTime()) {
312 this.executionTime = sn.getExeTime();
314 } else if(ScheduleEdge.NEWEDGE == se.getType()) {
317 scheduleEdges.add(se);
318 se.resetListExeTime();
321 Iterator it_edges = sn.edges();
322 while(it_edges.hasNext()) {
323 ScheduleEdge tse = (ScheduleEdge)it_edges.next();
325 this.edges.addElement(tse);
328 // As all tasks inside one ScheduleNode are executed sequentially,
329 // simply add the execution time of all the ClassNodes inside one ScheduleNode.
330 if(this.executionTime == -1) {
331 this.executionTime = 0;
333 this.executionTime += ((ScheduleNode)se.getTarget()).getExeTime();
337 public void mergeSNode(ScheduleNode sn) throws Exception {
338 Vector<ClassNode> targetCNodes = (Vector<ClassNode>)sn.getClassNodes();
339 Vector<ScheduleEdge> targetSEdges = (Vector<ScheduleEdge>)sn.getScheduleEdges();
341 for(int i = 0; i < targetCNodes.size(); i++) {
342 targetCNodes.elementAt(i).setScheduleNode(this);
345 if(classNodes == null) {
346 classNodes = targetCNodes;
347 scheduleEdges = targetSEdges;
349 if(targetCNodes.size() != 0) {
350 classNodes.addAll(targetCNodes);
352 if(targetSEdges.size() != 0) {
353 scheduleEdges.addAll(targetSEdges);
359 // redirect external ScheduleEdges to this ScheduleNode
360 Iterator it_edges = sn.edges();
361 while(it_edges.hasNext()) {
362 ScheduleEdge tse = (ScheduleEdge)it_edges.next();
364 this.edges.addElement(tse);
367 it_edges = sn.inedges();
368 while(it_edges.hasNext()) {
369 ScheduleEdge tse = (ScheduleEdge)it_edges.next();
371 this.inedges.addElement(tse);
374 // As all tasks inside one ScheduleNode are executed sequentially,
375 // simply add the execution time of all the ClassNodes inside one ScheduleNode.
376 if(this.executionTime == -1) {
377 this.executionTime = 0;
379 this.executionTime += sn.getExeTime();