summaryrefslogtreecommitdiff
path: root/sources/core
diff options
context:
space:
mode:
authorPaul Buetow <paul@buetow.org>2008-05-15 23:08:33 +0000
committerPaul Buetow <paul@buetow.org>2008-05-15 23:08:33 +0000
commitd4c1ddcc90c1e2e8660598fc36b3772d2bff6816 (patch)
tree28a0afc255e42f92adbca0d102e785301bc43a58 /sources/core
parent61599471a5978c1521b9c89c044ac2ce9a88c398 (diff)
1 Moved the stuff to trunk!
Diffstat (limited to 'sources/core')
-rw-r--r--sources/core/VSLamport.java19
-rw-r--r--sources/core/VSMessage.java56
-rw-r--r--sources/core/VSProcess.java442
-rw-r--r--sources/core/VSTask.java167
-rw-r--r--sources/core/VSTaskManager.java291
5 files changed, 975 insertions, 0 deletions
diff --git a/sources/core/VSLamport.java b/sources/core/VSLamport.java
new file mode 100644
index 0000000..157aaae
--- /dev/null
+++ b/sources/core/VSLamport.java
@@ -0,0 +1,19 @@
+package core;
+
+public class VSLamport {
+ private long time;
+ private long lamportTime;
+
+ public VSLamport(long time, long lamportTime) {
+ this.time = time;
+ this.lamportTime = lamportTime;
+ }
+
+ public long getTime() {
+ return time;
+ }
+
+ public long getLamportTime() {
+ return lamportTime;
+ }
+}
diff --git a/sources/core/VSMessage.java b/sources/core/VSMessage.java
new file mode 100644
index 0000000..b3c1d31
--- /dev/null
+++ b/sources/core/VSMessage.java
@@ -0,0 +1,56 @@
+package core;
+
+import prefs.VSPrefs;
+import protocols.*;
+import events.VSEvent;
+
+public class VSMessage extends VSPrefs implements VSEvent {
+ private String protocolClassname;
+ private VSProcess sendingProcess;
+ private long messageID;
+ private static long messageCounter;
+ private long lamportTime;
+
+ public VSMessage(String protocolClassname) {
+ this.protocolClassname = protocolClassname;
+ this.messageID = ++messageCounter;
+ }
+
+ public String getProtocolName() {
+ return RegisteredProtocols.getProtocolName(getProtocolClassname());
+ }
+
+ public String getProtocolClassname() {
+ return protocolClassname;
+ }
+
+ public long getMessageID() {
+ return messageID;
+ }
+
+ public void setSendingProcess(VSProcess sendingProcess) {
+ this.sendingProcess = sendingProcess;
+ lamportTime = sendingProcess.getLamportTime();
+ }
+
+ public VSProcess getSendingProcess() {
+ return sendingProcess;
+ }
+
+ public long getLamportTime() {
+ return lamportTime;
+ }
+
+ public String toString() {
+ return "ID: " + messageID;
+ }
+
+ public String toStringFull() {
+ return toString() + "; " + super.toString();
+ }
+
+ public boolean equals(VSMessage message) {
+ return messageID == message.getMessageID();
+ }
+}
+
diff --git a/sources/core/VSProcess.java b/sources/core/VSProcess.java
new file mode 100644
index 0000000..bb65959
--- /dev/null
+++ b/sources/core/VSProcess.java
@@ -0,0 +1,442 @@
+package core;
+
+import java.awt.*;
+import java.util.*;
+
+import prefs.*;
+import protocols.*;
+import simulator.*;
+import utils.*;
+import events.*;
+
+public final class VSProcess extends VSPrefs {
+ private VSTask randomCrashTask;
+ private Color currentColor;
+ private Color tmpColor;
+ private Color crashedColor;;
+ private VSLogging logging;
+ private VSPrefs prefs;
+ private VSRandom random;
+ private VSSimulationPanel simulationPanel;
+ private boolean hasStarted;
+ private boolean isHighlighted;
+ private boolean isPaused;
+ private boolean timeModified;
+ private double clockOffset;
+ private float clockVariance;
+ private int num;
+ private int processID;
+ private long globalTime;
+ private long localTime;
+ private static int processCounter;
+ private boolean isCrashed;
+ private long lamportTime;
+ private ArrayList<VSLamport> lamportTimestamps;
+ private ArrayList<Integer> vectorTimestamps;
+
+ /* This array contains all Integer prefs of the process which should show
+ * up in the prefs menu! All keys which dont start with "sim." only show
+ * up in the extended prefs menu!
+ */
+ private static final String DEFAULT_INTEGER_VALUE_KEYS[] = {
+ "sim.process.prob.crash",
+ "sim.message.prob.outage",
+ };
+
+ /* This array contains all Long prefs of the process which should show
+ * up in the prefs menu! All keys which dont start with "sim." only show
+ * up in the extended prefs menu!
+ */
+ private static final String DEFAULT_LONG_VALUE_KEYS[] = {
+ "sim.message.sendingtime.min",
+ "sim.message.sendingtime.max",
+ };
+
+ /* This array contains all Float prefs of the process which should show
+ * up in the prefs menu! All keys which dont start with "sim." only show
+ * up in the extended prefs menu!
+ */
+ private static final String DEFAULT_FLOAT_VALUE_KEYS[] = {
+ "sim.process.clock.variance",
+ };
+
+ /* This array contains all Color prefs of the process which should show
+ * up in the prefs menu! All keys which dont start with "sim." only show
+ * up in the extended prefs menu!
+ */
+ private static final String DEFAULT_COLOR_VALUE_KEYS[] = {
+ "process.default",
+ "process.running",
+ "process.stopped",
+ "process.highlight",
+ "process.crashed",
+ };
+
+ /* This array contains all String prefs of the process which should show
+ * up in the prefs menu! All keys which dont start with "sim." only show
+ * up in the extended prefs menu!
+ */
+ private static final String DEFAULT_STRING_VALUE_KEYS[] = {
+ };
+
+ public VSProcess(VSPrefs prefs, VSSimulationPanel simulationPanel, VSLogging logging, int num) {
+ this.prefs = prefs;
+ this.simulationPanel = simulationPanel;
+ this.logging = logging;
+ this.num = num;
+ this.random = new VSRandom(processID+processCounter);
+ this.lamportTimestamps = new ArrayList<VSLamport>();
+ this.vectorTimestamps = new ArrayList<Integer>();
+ setLamportTime(0);
+
+ setObject("protocols", new ArrayList<VSProtocol>());
+
+ isPaused = true;
+ processID = ++processCounter;
+
+ /* Create the super.VSPrefs with it's default prefs */
+ fillWithDefaults();
+
+ /* Make local copys in order to have more performance */
+ clockVariance = getFloat("sim.process.clock.variance");
+ currentColor = getColor("process.default");
+
+ /* Make additional process settings editable through GUI */
+ initInteger("sim.process.id", processID,
+ prefs.getString("lang.process.id"), 1, processID + 10);
+ setLongIfUnset("sim.process.localtime", localTime, prefs.getString("lang.process.time.local"));
+
+ crashedColor = getColor("process.crashed");
+ createRandomCrashTask();
+ }
+
+ /**
+ * Called from the VSProcessEditor, after finishing editing!
+ */
+ public synchronized void updateFromVSPrefs() {
+ setClockVariance(getFloat("sim.process.clock.variance"));
+ setProcessID(getInteger("sim.process.id"));
+ setLocalTime(getLong("sim.process.localtime"));
+ crashedColor = getColor("process.crashed");
+ simulationPanel.repaint();
+ createRandomCrashTask();
+ }
+
+ /**
+ * Called from the VSProcessEditor, before starting editing!
+ */
+ public synchronized void updatePrefs() {
+ setFloat("sim.process.clock.variance", getClockVariance());
+ setInteger("sim.process.id", getProcessID());
+ setLong("sim.process.localtime", getTime());
+ }
+
+ public synchronized void syncTime(final long globalTime) {
+ final long currentGlobalTimestep = globalTime - this.globalTime;
+ this.globalTime = globalTime;
+
+ if (!isCrashed) {
+ localTime += currentGlobalTimestep;
+ clockOffset += currentGlobalTimestep * (double) clockVariance;
+ }
+
+ while (clockOffset >= 1) {
+ clockOffset -= 1;
+ ++localTime;
+ }
+
+ while (clockOffset <= -1) {
+ clockOffset += 1;
+ --localTime;
+ }
+
+ if (localTime < 0)
+ localTime = 0;
+ }
+
+ private void setCurrentColor(Color newColor) {
+ if (isHighlighted)
+ tmpColor = newColor;
+ else
+ currentColor = newColor;
+ }
+
+ public synchronized void highlightOn() {
+ tmpColor = currentColor;
+ currentColor = getColor("process.highlight");
+ isHighlighted = true;
+ }
+
+ public synchronized void highlightOff() {
+ currentColor = tmpColor;
+ isHighlighted = false;
+ }
+
+ public synchronized void reset() {
+ isPaused = true;
+ isCrashed = false;
+ localTime = 0;
+ globalTime = 0;
+ clockOffset = 0;
+ lamportTime = 0;
+ lamportTimestamps.clear();
+ vectorTimestamps.clear();
+
+ if (objectExists("protocols.registered")) {
+ Object protocolsObj = getObject("protocols.registered");
+ if (protocolsObj instanceof Vector) {
+ Vector<VSProtocol> protocols = (Vector<VSProtocol>) protocolsObj;
+ for (VSProtocol protocol : protocols)
+ protocol.reset();
+ }
+ }
+
+ setCurrentColor(getColor("process.default"));
+ createRandomCrashTask();
+ }
+
+ private void createRandomCrashTask() {
+ if (!isCrashed) {
+ VSTaskManager taskManager = simulationPanel.getTaskManager();
+ long crashTime = getARandomCrashTime();
+
+ if (randomCrashTask != null)
+ taskManager.removeTask(randomCrashTask);
+
+ if (crashTime >= 0 && crashTime >= getGlobalTime()) {
+ randomCrashTask = new VSTask(crashTime, this, new ProcessCrashEvent());
+ taskManager.addTask(randomCrashTask);
+ //System.out.println("DEBUG " + processID + " crashes at " + crashTime);
+
+ } else {
+ randomCrashTask = null;
+ }
+ }
+ }
+
+ public synchronized void addClockOffset(long add) {
+ this.clockOffset += add;
+ }
+
+ public synchronized void play() {
+ isPaused = false;
+ setCurrentColor(getColor("process.running"));
+ }
+
+ public synchronized void pause() {
+ isPaused = true;
+ setCurrentColor(getColor("process.stopped"));
+ }
+
+ public synchronized void finish() {
+ isPaused = true;
+ setCurrentColor(getColor("process.default"));
+ }
+
+ public synchronized int getProcessID() {
+ return processID;
+ }
+
+ public synchronized void setProcessID(int processID) {
+ this.processID = processID;
+ }
+
+ public synchronized Color getColor() {
+ return currentColor;
+ }
+
+ public synchronized void setLocalTime(final long localTime) {
+ if (localTime >= 0)
+ this.localTime = localTime;
+ else
+ this.localTime = 0;
+ }
+
+ public synchronized long getTime() {
+ return localTime;
+ }
+
+ public synchronized void setTime(final long time) {
+ if (time >= 0)
+ this.localTime = time;
+ else
+ this.localTime = 0;
+
+ this.timeModified = true;
+ }
+
+ public synchronized boolean isCrashed() {
+ return isCrashed;
+ }
+
+ public synchronized void isCrashed(boolean isCrashed) {
+ this.isCrashed = isCrashed;
+ }
+
+ public synchronized Color getCrashedColor() {
+ return crashedColor;
+ }
+
+ public int getNum() {
+ return num;
+ }
+
+ public synchronized boolean timeModified() {
+ return timeModified;
+ }
+
+ public synchronized void timeModified(boolean timeModified) {
+ this.timeModified = timeModified;
+ }
+
+ public synchronized long getGlobalTime() {
+ return globalTime;
+ }
+
+ public synchronized void setGlobalTime(final long globalTime) {
+ this.globalTime = globalTime >= 0 ? globalTime : 0;
+ }
+
+ public synchronized float getClockVariance() {
+ return clockVariance;
+ }
+
+ public synchronized void setClockVariance(float clockVariance) {
+ /* If negative, only allow < 1 prefs */
+ if (clockVariance < 0) {
+ int part = (int) -clockVariance;
+ if (part > 0) {
+ this.clockVariance = 0;
+ return;
+ }
+ }
+
+ this.clockVariance = clockVariance;
+ }
+
+ public synchronized long getDurationTime() {
+ final long maxDurationTime = getLong("sim.message.sendingtime.max");
+ final long minDurationTime = getLong("sim.message.sendingtime.min");
+
+ if (maxDurationTime <= minDurationTime)
+ return minDurationTime;
+
+ final int diff = (int) (maxDurationTime - minDurationTime);
+
+ /* Integer overflow */
+ if (diff <= 0)
+ return minDurationTime;
+
+ return minDurationTime + random.nextInt(diff+1);
+ }
+
+ public synchronized long getARandomMessageOutageTime(final long durationTime) {
+ /* Check if the message will have an outage or not */
+ if (random.nextInt(100) <= getInteger("sim.message.prob.outage")) {
+ /* Calculate the random outage time! */
+ final long outageTime = globalTime + random.nextLong(durationTime+1) % simulationPanel.getUntilTime();
+ return outageTime;
+ }
+
+ /* No outage */
+ return -1;
+ }
+
+ private long getARandomCrashTime() {
+ /* Check if the process will crash or not */
+ if (random.nextInt(100) <= getInteger("sim.process.prob.crash")) {
+ /* Calculate the random crash time! */
+ final long crashTime = random.nextLong(simulationPanel.getUntilTime()+1) % simulationPanel.getUntilTime();
+ return crashTime;
+ }
+
+ /* No crash */
+ return -1;
+ }
+
+ public synchronized VSTask getCrashTask() {
+ return randomCrashTask;
+ }
+
+ public synchronized boolean isPaused() {
+ return isPaused;
+ }
+
+ public synchronized long getLamportTime() {
+ return lamportTime;
+ }
+
+ public synchronized void setLamportTime(long lamportTime) {
+ this.lamportTime = lamportTime;
+ lamportTimestamps.add(new VSLamport(globalTime, lamportTime));
+ }
+
+ public synchronized VSLamport[] getLamportArray() {
+ final int size = lamportTimestamps.size();
+ final VSLamport[] arr = new VSLamport[size];
+
+ for (int i = 0; i < size; ++i)
+ arr[i] = lamportTimestamps.get(i);
+
+ return arr;
+ }
+
+ public synchronized int[] getVectorTime() {
+ final int size = vectorTimestamps.size();
+ final int[] arr = new int[size];
+
+ for (int i = 0; i < size; ++i)
+ arr[i] = vectorTimestamps.get(i);
+
+ return arr;
+ }
+
+
+ public void sendMessage(VSMessage message) {
+ logg(prefs.getString("lang.message.sent") + "; "
+ + prefs.getString("lang.protocol") + ": " + message.getProtocolName() + "; "
+ + prefs.getString("lang.message") + " " + message.toStringFull());
+ simulationPanel.sendMessage(message);
+ }
+
+ public void logg(String message) {
+ logging.logg(toString() + "; " + message, globalTime);
+ }
+
+ public void fillWithDefaults() {
+ prefs.copyIntegers(this, DEFAULT_INTEGER_VALUE_KEYS);
+ prefs.copyLongs(this, DEFAULT_LONG_VALUE_KEYS);
+ prefs.copyFloats(this, DEFAULT_FLOAT_VALUE_KEYS);
+ prefs.copyColors(this, DEFAULT_COLOR_VALUE_KEYS);
+ prefs.copyStrings(this, DEFAULT_STRING_VALUE_KEYS);
+ }
+
+ public String toString() {
+ return
+ prefs.getString("lang.process.id") + ": "
+ + getProcessID() + "; "
+ + prefs.getString("lang.process.time.local") + ": "
+ + VSTools.getTimeString(getTime())
+ + "; Lamport: " + lamportTime;
+ }
+
+ public String toStringFull() {
+ return toString() + "; paused: " + isPaused + "; crashed: " + isCrashed + "; crashTask: " + randomCrashTask;
+ }
+
+ public boolean equals(VSProcess process) {
+ return process.getNum() == getNum();
+ }
+
+ public VSSimulationPanel getSimulationPanel() {
+ return simulationPanel;
+ }
+
+ public VSPrefs getPrefs() {
+ return prefs;
+ }
+
+ public static void resetProcessCounter() {
+ processCounter = 0;
+ }
+}
diff --git a/sources/core/VSTask.java b/sources/core/VSTask.java
new file mode 100644
index 0000000..43b0265
--- /dev/null
+++ b/sources/core/VSTask.java
@@ -0,0 +1,167 @@
+package core;
+
+import prefs.VSPrefs;
+import events.*;
+import protocols.VSProtocol;
+import simulator.*;
+
+public class VSTask implements Comparable {
+ //public final static int RUN_ON_CLIENT_START = 1;
+ private long taskTime;
+ private VSEvent event;
+ private VSProcess process;
+ private VSPrefs prefs;
+ private boolean isProgrammed;
+
+ public VSTask(long taskTime, VSProcess process, VSEvent event) {
+ this.process = process;
+ this.taskTime = taskTime > 0 ? taskTime : 0;
+ this.event = event;
+ this.prefs = process.getPrefs();
+ }
+
+ public void isProgrammed(boolean isProgrammed) {
+ this.isProgrammed = isProgrammed;
+ }
+
+ public boolean isProgrammed() {
+ return isProgrammed;
+ }
+
+ public boolean isMessage() {
+ return event instanceof VSMessage;
+ }
+
+ public boolean isProtocol(VSProtocol protocol) {
+ if (event instanceof VSProtocol)
+ return ((VSProtocol) event).equals(protocol);
+
+ return false;
+ }
+
+ public boolean isGlobalTimed() {
+ if (event instanceof VSProtocol)
+ return false;
+
+ return true;
+ }
+
+ public VSProcess getProcess() {
+ return process;
+ }
+
+ public void run() {
+ if (process.isCrashed())
+ return;
+
+ if (event instanceof VSMessage) {
+ onMessageRecv();
+
+ } else if (event instanceof VSProtocol) {
+ /* Lamport time will get incremented by the VSProtocol class */
+ onProtocolStart();
+
+ } else if (event instanceof VSProcessEvent) {
+ onProcessEventStart();
+
+ } else {
+ onDummy();
+ }
+ }
+
+ private void onDummy() {
+ logg(prefs.getString("lang.process.task"));
+ }
+
+ /**
+ * If the process recv a message, check if the message's protocol is activated
+ * by the process. If yes, run the protocol on the message! If not, just logg
+ * that the process does not support this protocol! The process will ignore the
+ * message!
+ */
+ private void onMessageRecv() {
+ final VSMessage message = (VSMessage) event;
+ final String protocolName = message.getProtocolName();
+ final String protocolClassname = message.getProtocolClassname();
+
+ final long recvLamportTime = message.getLamportTime() + 1;
+ final long lamportTime = process.getLamportTime() + 1;
+
+ if (recvLamportTime > lamportTime)
+ process.setLamportTime(recvLamportTime);
+ else
+ process.setLamportTime(lamportTime);
+
+ Object protocolObj;
+
+ if (process.objectExists(protocolClassname))
+ protocolObj = process.getObject(protocolClassname);
+ else
+ protocolObj = null;
+
+ String loggVSMessage = prefs.getString("lang.message.recv")
+ + "; " + prefs.getString("lang.protocol") + ": " + protocolName
+ + "; " + prefs.getString("lang.message") + " " + message;
+
+ if (protocolObj == null) {
+ logg(loggVSMessage);
+
+ } else {
+ final VSProtocol protocol = (VSProtocol) protocolObj;
+ logg(loggVSMessage);
+ protocol.onMessageRecv(message);
+ }
+ }
+
+ private void onProtocolStart() {
+ ((VSProtocol) event).onStart();
+ }
+
+ private void onProcessEventStart() {
+ final VSProcessEvent processEvent = (VSProcessEvent) event;
+ processEvent.onStart(process);
+ /*
+ if (process.isCrashed())
+ process.setLamportTime(process.getLamportTime()-1);
+ */
+ }
+
+ public long getTaskTime() {
+ return taskTime;
+ }
+
+ public VSEvent getEvent() {
+ return event;
+ }
+
+ private void logg(String message) {
+ process.logg(message);
+ }
+
+ public int compareTo(Object object) {
+ if (object instanceof VSTask) {
+ final VSTask task = (VSTask) object;
+
+ if (taskTime < task.getTaskTime())
+ return -1;
+
+ else if (taskTime > task.getTaskTime())
+ return 1;
+ }
+
+ return 0;
+ }
+
+ public String toString() {
+ String descr = "VSTask: " + getTaskTime();
+
+ if (event instanceof VSMessage)
+ descr += (VSMessage) event;
+
+ else if (event instanceof VSProtocol)
+ descr += (VSProtocol) event;
+
+ return descr;
+ }
+}
+
diff --git a/sources/core/VSTaskManager.java b/sources/core/VSTaskManager.java
new file mode 100644
index 0000000..28f5a36
--- /dev/null
+++ b/sources/core/VSTaskManager.java
@@ -0,0 +1,291 @@
+package core;
+
+import java.util.*;
+
+import protocols.*;
+import prefs.*;
+
+public class VSTaskManager {
+ private PriorityQueue<VSTask> tasks;
+ private PriorityQueue<VSTask> globalTasks;
+ private LinkedList<VSTask> fullfilledProgrammedTasks;
+ public final static boolean PROGRAMMED_TASK = true;
+ public final static boolean NOT_PROGRAMMED_TASK = false;
+ private VSPrefs prefs;
+
+ public VSTaskManager(VSPrefs prefs) {
+ this.prefs = prefs;
+ Comparator<VSTask> comparator = createComparator();
+ this.tasks = new PriorityQueue<VSTask>(100, comparator);
+ this.globalTasks = new PriorityQueue<VSTask>(100, comparator);
+ this.fullfilledProgrammedTasks = new LinkedList<VSTask>();
+ }
+
+ private Comparator<VSTask> createComparator() {
+ return new Comparator<VSTask>() {
+ public int compare(VSTask a, VSTask b) {
+ if (a.getTaskTime() > b.getTaskTime())
+ return 1;
+
+ if (a.getTaskTime() < b.getTaskTime())
+ return -1;
+
+ return 0;
+ }
+ };
+ }
+
+ public synchronized void runVSTasks(final long step, final long offset, final long lastGlobalTime) {
+ VSTask task = null;
+ VSProcess process = null;
+ long localTime;
+ long offsetTime;
+ long taskTime;
+ long globalTime;
+ final long globalOffsetTime = lastGlobalTime + step;
+ boolean redo;
+
+ do {
+ redo = false;
+
+ /* Run tasks which have for its schedule the global time */
+ while (globalTasks.size() != 0) {
+ task = globalTasks.peek();
+ process = task.getProcess();
+ localTime = process.getTime();
+ offsetTime = localTime + step;
+ taskTime = task.getTaskTime();
+ globalTime = process.getGlobalTime();
+
+ if (globalOffsetTime < taskTime)
+ break;
+
+ globalTasks.poll();
+ redo = true;
+
+ if (process.isCrashed()) {
+ if (task.isProgrammed())
+ fullfilledProgrammedTasks.add(task);
+ continue;
+ }
+
+ if (globalOffsetTime == taskTime) {
+ process.setGlobalTime(globalOffsetTime);
+ process.setLocalTime(offsetTime);
+ process.timeModified(false);
+ task.run();
+ process.setGlobalTime(globalTime);
+ if (process.isCrashed())
+ process.addClockOffset(step);
+ if (process.timeModified())
+ process.addClockOffset(process.getTime()-offsetTime);
+ process.setLocalTime(localTime);
+
+ } else /* if (globalOffsetTime > taskTime) */ {
+ final long diff = globalOffsetTime - taskTime;
+ if (globalOffsetTime - diff < lastGlobalTime)
+ process.setGlobalTime(lastGlobalTime);
+ else
+ process.setGlobalTime(globalOffsetTime - diff);
+ process.setLocalTime(offsetTime - diff);
+ process.timeModified(false);
+ task.run();
+ process.setGlobalTime(globalTime);
+ if (process.isCrashed())
+ process.addClockOffset(step);
+ if (process.timeModified())
+ process.addClockOffset(process.getTime()-(offsetTime-diff));
+ process.setLocalTime(localTime);
+ }
+
+ if (task.isProgrammed())
+ fullfilledProgrammedTasks.add(task);
+ }
+
+ /* Run tasks which have for its schedule the local process times */
+ while (tasks.size() != 0) {
+ task = tasks.peek();
+ process = task.getProcess();
+ localTime = process.getTime();
+ offsetTime = localTime + step;
+ taskTime = task.getTaskTime();
+ globalTime = process.getGlobalTime();
+
+ if (offsetTime < taskTime)
+ break;
+
+ tasks.poll();
+ redo = true;
+
+ if (process.isCrashed()) {
+ if (task.isProgrammed())
+ fullfilledProgrammedTasks.add(task);
+ continue;
+ }
+
+ if (offsetTime == taskTime) {
+ process.setGlobalTime(globalOffsetTime);
+ process.setLocalTime(offsetTime);
+ process.timeModified(false);
+ task.run();
+ process.setGlobalTime(globalTime);
+ if (process.timeModified())
+ process.addClockOffset(process.getTime()-offsetTime);
+ process.setLocalTime(localTime);
+
+ } else /* if (offsetTime > taskTime) */ {
+ final long diff = offsetTime - taskTime;
+ if (globalOffsetTime - diff < lastGlobalTime)
+ process.setGlobalTime(lastGlobalTime);
+ else
+ process.setGlobalTime(globalOffsetTime - diff);
+ process.setLocalTime(offsetTime - diff);
+ process.timeModified(false);
+ task.run();
+ process.setGlobalTime(globalTime);
+ if (process.timeModified())
+ process.addClockOffset(process.getTime()-(offsetTime-diff));
+ process.setLocalTime(localTime);
+ }
+
+ if (task.isProgrammed())
+ fullfilledProgrammedTasks.add(task);
+ }
+
+ } while (redo);
+ }
+
+ public synchronized void reset() {
+ PriorityQueue<VSTask> tmp = tasks;
+ PriorityQueue<VSTask> tmp2 = globalTasks;
+ tasks = new PriorityQueue<VSTask>();
+ globalTasks = new PriorityQueue<VSTask>();
+
+ while (fullfilledProgrammedTasks.size() != 0) {
+ VSTask task = fullfilledProgrammedTasks.removeFirst();
+ if (task.isProgrammed())
+ insert(task);
+ }
+
+ while (tmp.size() != 0) {
+ VSTask task = tmp.poll();
+ if (task.isProgrammed())
+ insert(task);
+ }
+
+ while (tmp2.size() != 0) {
+ VSTask task = tmp2.poll();
+ if (task.isProgrammed())
+ insert(task);
+ }
+ }
+
+ private void insert(VSTask task) {
+ if (task.isGlobalTimed())
+ globalTasks.add(task);
+ else
+ tasks.add(task);
+ }
+
+ public void addTask(VSTask task) {
+ addTask(task, VSTaskManager.NOT_PROGRAMMED_TASK);
+ }
+
+ public synchronized void addTask(VSTask task, boolean isProgrammed) {
+ task.isProgrammed(isProgrammed);
+ insert(task);
+ }
+
+ public synchronized void removeTask(VSTask task) {
+ if (task.isGlobalTimed())
+ globalTasks.remove(task);
+ else
+ tasks.remove(task);
+ }
+
+ public synchronized LinkedList<VSTask> getProtocolTasks(VSProtocol protocol) {
+ LinkedList<VSTask> protocolVSTasks = new LinkedList<VSTask>();
+
+ for (VSTask task : fullfilledProgrammedTasks)
+ if (task.isProtocol(protocol))
+ protocolVSTasks.addLast(task);
+
+ for (VSTask task : globalTasks)
+ if (task.isProtocol(protocol))
+ protocolVSTasks.addLast(task);
+
+ for (VSTask task : tasks)
+ if (task.isProtocol(protocol))
+ protocolVSTasks.addLast(task);
+
+ return protocolVSTasks;
+ }
+
+ public synchronized LinkedList<VSTask> getNonProtocolTasks(VSProtocol protocol) {
+ LinkedList<VSTask> nonProtocolTasks = new LinkedList<VSTask>();
+
+ for (VSTask task : fullfilledProgrammedTasks)
+ if (!task.isProtocol(protocol))
+ nonProtocolTasks.addLast(task);
+
+ for (VSTask task : globalTasks)
+ if (!task.isProtocol(protocol))
+ nonProtocolTasks.addLast(task);
+
+ for (VSTask task : tasks)
+ if (!task.isProtocol(protocol))
+ nonProtocolTasks.addLast(task);
+
+ return nonProtocolTasks;
+ }
+
+ public synchronized void modifyProtocolTasks(VSProtocol protocol, LinkedList<VSTask> protocolVSTasks) {
+ VSProcess process = protocol.getProcess();
+ LinkedList<VSTask> nonProtocolTasks = getNonProtocolTasks(protocol);
+ //System.out.println("NON PROTO: " + nonProtocolTasks);
+ ListIterator<VSTask> iter1 = protocolVSTasks.listIterator(0);
+ ListIterator<VSTask> iter2 = nonProtocolTasks.listIterator(0);
+ long localTime = process.getTime();
+
+ fullfilledProgrammedTasks.clear();
+ globalTasks.clear();
+ tasks.clear();
+
+ for (VSTask task : nonProtocolTasks) {
+ if (task.getTaskTime() < localTime)
+ fullfilledProgrammedTasks.addLast(task);
+ else
+ insert(task);
+ }
+
+ for (VSTask task : protocolVSTasks) {
+ if (task.getTaskTime() < localTime)
+ fullfilledProgrammedTasks.addLast(task);
+ else
+ insert(task);
+ }
+ }
+
+ public String toString() {
+ final String taskManager = prefs.getString("lang.taskmanager");
+ String descr = "fullfilled: ";
+
+ for (VSTask task : fullfilledProgrammedTasks)
+ descr += task + "; ";
+
+ descr += "global: ";
+
+ for (VSTask task : globalTasks)
+ descr += task + "; ";
+
+ descr += "local: ";
+
+ for (VSTask task : tasks)
+ descr += task + "; ";
+
+ if (descr.endsWith("; "))
+ return taskManager + " (" + descr.substring(0, descr.length()-2) + ")";
+
+ return taskManager + " (" + descr + ")";
+ }
+}