1 package edu.berkeley.fleet.api;
3 public abstract class Instruction {
5 public final Pump pump;
6 public Instruction(Pump pump) { this.pump = pump; }
7 public String toString() { return pump+": "; }
9 public boolean isLooping() { return false; }
10 public boolean isRepeating() { return false; }
11 public boolean isStanding() { return false; }
12 public boolean isSK() { return false; }
13 public boolean isDL() { return false; }
15 public static class Clog extends Instruction {
16 public Clog(Pump pump) { super(pump); }
17 public String toString() { return super.toString() + "clog;"; }
20 public static class UnClog extends Instruction {
21 public UnClog(Pump pump) { super(pump); }
22 public String toString() { return super.toString() + "unclog;"; }
25 public static class Massacre extends Instruction {
26 public Massacre(Pump pump) { super(pump); }
29 public static class Kill extends Instruction {
30 public final int count;
31 public Kill(Pump pump, int count) { super(pump); this.count = count; }
32 public String toString() { return super.toString() + "kill"+(count==1?"":(" "+count))+";"; }
35 public static class DecrLoop extends Instruction {
36 public DecrLoop(Pump pump) { super(pump); }
37 public boolean isDL() { return true; }
40 public static class Counter extends Instruction {
41 public static final int DATA_LATCH = -1;
42 public static final int REPEAT_COUNTER = -2;
43 public static final int LOOP_COUNTER = -3;
44 public final int source;
45 public final int dest;
46 public Counter(Pump pump, int source, int dest) {
51 public String toString() {
52 if (source==LOOP_COUNTER && dest==DATA_LATCH) return "take loop counter;";
53 StringBuffer ret = new StringBuffer();
56 case LOOP_COUNTER: ret.append("loop"); break;
57 case REPEAT_COUNTER: ret.append("repeat"); break;
58 default: throw new RuntimeException("invalid");
60 ret.append(" counter");
62 ret.append(" with " + source);
63 } else if (source!=DATA_LATCH) {
64 throw new RuntimeException("invalid");
67 return ret.toString();
69 public boolean isLooping() { return true; }
72 public static class Move extends Instruction {
73 public final Destination dest;
75 public final boolean tokenIn;
76 public final boolean dataIn;
77 public final boolean latch;
78 public final boolean dataOutDest;
79 public final boolean dataOut;
80 public final boolean tokenOut;
81 public final boolean requeue;
82 public final boolean ignoreUntilLast;
83 public final boolean standing;
85 /** count=0 denotes a standing move */
86 public Move(Pump pump,
96 boolean ignoreUntilLast) {
99 this.tokenIn = tokenIn;
100 this.dataIn = dataIn;
102 this.dataOutDest = dataOutDest;
103 this.dataOut = dataOut;
104 this.tokenOut = tokenOut;
105 this.requeue = requeue;
106 this.ignoreUntilLast = ignoreUntilLast;
107 this.standing = count==0;
108 if (pump.isInbox() && tokenIn && dataIn)
109 throw new RuntimeException("cannot have both \"wait\" and \"take\"/\"recieve\" on an inbox: " + this);
110 if (pump.isOutbox() && tokenOut && dataOut)
111 throw new RuntimeException("cannot have both \"sendto\" and \"notify\" on an outbox: " + this);
112 if (latch && !dataIn)
113 throw new RuntimeException("cannot have latch bit set without dataIn bit: " + this);
116 public String toString() {
118 String ret = super.toString();
119 boolean needcomma = false;
120 if (tokenIn) { ret += (needcomma ? ", " : "") + "wait"; needcomma = true; }
121 if (dataIn && latch) {
123 ret += (needcomma ? ", " : "") + "receive";
125 ret += (needcomma ? ", " : "") + "take";
128 if (dataIn && !latch) { ret += (needcomma ? ", " : "") + "dismiss"; needcomma = true; }
130 if (pump.isInbox() || dest==null)
131 ret += (needcomma ? ", " : "") + "deliver";
133 ret += (needcomma ? ", " : "") + "sendto "+dest;
136 if (tokenOut) { ret += (needcomma ? ", " : "") + "notify "+dest; needcomma = true; }
140 public boolean isLooping() { return true; }
141 public boolean isRepeating() { return true; }
142 public boolean isStanding() { return standing; }
146 public static class FullLiteral extends Executable {
147 public final long literal;
148 public boolean isRequeueing() { return true; }
149 public HalfLiteral(Pump pump, long literal) {
151 this.literal = literal;
153 public Instruction.Executable decrementCount() {
154 if (count==1) return null;
155 return new FullLiteral(pump, literal, count-1, high);
160 public static class HalfLiteral extends Instruction {
161 public final long literal;
162 public final boolean high;
163 public boolean isRequeueing() { return true; }
164 public HalfLiteral(Pump pump, long literal, int count, boolean high) {
166 this.literal = literal;
169 public boolean isLooping() { return true; }
172 public static class CodeBagDescriptor extends Instruction {
173 /** address of CBD, relative to address that this instruction was loaded from */
174 public final long offset;
175 public final long size;
176 public CodeBagDescriptor(Pump pump, long offset, long size) {
178 this.offset = offset;
181 public String toString() {
182 String off = ""+offset;
183 if (offset > 0) off = "+"+off;
184 return "(CBD @"+off+"+"+size+"): sendto " + pump;