fix how the fleeterpreter deals with kill*
authoradam <adam@megacz.com>
Fri, 16 Feb 2007 17:28:54 +0000 (18:28 +0100)
committeradam <adam@megacz.com>
Fri, 16 Feb 2007 17:28:54 +0000 (18:28 +0100)
src/edu/berkeley/fleet/interpreter/InstructionPort.java

index 893e881..284e9fe 100644 (file)
@@ -20,31 +20,20 @@ public abstract class InstructionPort extends InterpreterBenkoBox {
         super(ship, name);
     }
 
+    int killCount = 0;
+    boolean killOnlyStandingInstructions = false;
+
     public void kill(int count, boolean killOnlyStandingInstructions) {
-        if (currentlyExecuting != null) {
-            currentlyExecuting = null;
-            if (killOnlyStandingInstructions && currentlyExecuting.count != 0)
-                return;
-            count--;
-        }
-        for(; count > 0; count--) {
-            if (instructions.size() == 0) {
-                if (currentlyExecuting == null) {
-                    Log.error("You have deadlocked ship " + this +
-                              " by sending a kill to an empty ififo.  I feel sorry for you.");
-                    return;
-                }
-            } else {
-                Instruction.Executable inst = instructions.peek();
-                if (killOnlyStandingInstructions && inst.count != 0)
-                    return;
-                instructions.remove();
-            }
-        }
+        if (killCount > 0 && killOnlyStandingInstructions != this.killOnlyStandingInstructions)
+            throw new RuntimeException("you mixed kill and kill*");
+        killCount += count;
+        this.killOnlyStandingInstructions = killOnlyStandingInstructions;
     }
 
     /** an instruction arrives from the instruction horn */
     void addInstruction(Instruction.Executable instr) {
+        if (killCount > 0)
+            throw new RuntimeException("you tried to add an instruction to a BenkoBox that hadn't finished a kill yet");
         instructions.add(instr);
     }
 
@@ -73,6 +62,13 @@ public abstract class InstructionPort extends InterpreterBenkoBox {
             if (currentlyExecutingCount == 0) currentlyExecutingCount = Integer.MAX_VALUE;
         }
 
+        if (currentlyExecuting != null &&
+            (killCount > 0 && (!killOnlyStandingInstructions || currentlyExecutingCount == Integer.MAX_VALUE))) {
+            killCount--;
+            currentlyExecuting = null;
+            return;
+        }
+
         boolean ret = service(currentlyExecuting);
         if (!ret) return;
         if (currentlyExecuting.recycle) {