-package era.mi.logic;
-
-import era.mi.logic.timeline.Timeline;
-
-public class Simulation
-{
- public final static Timeline TIMELINE = new Timeline(11);
-
- public static void main(String[] args)
- {
- }
+package era.mi.logic;\r
+\r
+import era.mi.logic.timeline.Timeline;\r
+\r
+public class Simulation {\r
+ public final static Timeline TIMELINE = new Timeline(11);\r
+\r
+ public static void main(String[] args) {\r
+ }\r
}
\ No newline at end of file
-package era.mi.logic;
-
-import java.util.Arrays;
-
-public final class Util
-{
-
- @SuppressWarnings("unchecked")
- public static <T> T[] concat(T[]... arrays)
- {
- if (arrays.length == 0)
- throw new IllegalArgumentException("Cannot concatenate 0 arrays.");
-
- int length = 0;
- for (T[] array : arrays)
- length += array.length;
-
- T[] newArray = Arrays.copyOf(arrays[0], length);
- int appendIndex = arrays[0].length;
- for (int i = 1; i < arrays.length; i++)
- {
- System.arraycopy(arrays[i], 0, newArray, appendIndex, arrays[i].length);
- appendIndex += arrays[i].length;
- }
-
- return newArray;
- }
-
-// @SuppressWarnings("unchecked")
-// public static <T> T[][] split(T[] array, int... lengths)
-// {
-// //TODO: implement array split again; This version contains an illegal cast
-// int totalLength = 0;
-// for(int length : lengths)
-// totalLength += length;
-//
-// if(totalLength != array.length)
-// throw new IllegalArgumentException(); //TODO: add proper error message
-//
-// Object[][] newArray = new Object[lengths.length][];
-// int splitIndex = 0;
-// for(int i = 0; i < lengths.length; i++)
-// {
-// System.arraycopy(array, splitIndex, newArray, 0, lengths[i]);
-// splitIndex += lengths[i];
-// }
-//
-// return (T[][]) newArray;
-// }
-
- public static Bit[] and(Bit[] a, Bit[] b)
- {
- return binBitOp(a, b, (bA, bB) -> Bit.and(bA, bB));
- }
-
- public static Bit[] or(Bit[] a, Bit[] b)
- {
- return binBitOp(a, b, (bA, bB) -> Bit.or(bA, bB));
- }
-
- public static Bit[] xor(Bit[] a, Bit[] b)
- {
- return binBitOp(a, b, (bA, bB) -> Bit.xor(bA, bB));
- }
-
- private static Bit[] binBitOp(Bit[] a, Bit[] b, BitOp op)
- {
- if (a.length != b.length)
- throw new IllegalArgumentException("Bit Arrays were not of equal length.");
- Bit[] out = new Bit[a.length];
- for (int i = 0; i < a.length; i++)
- {
- out[i] = op.execute(a[i], b[i]);
- }
- return out;
- }
-
- public static Bit[] not(Bit[] a)
- {
- Bit[] out = new Bit[a.length];
- for (int i = 0; i < a.length; i++)
- {
- out[i] = a[i].not();
- }
- return out;
- }
-
- /**
- * uses the {@link Bit#combineWith(Bit)} method, does not create a new array,
- * the result is stored in the first array.
- *
- * @author Christian Femers
- */
- public static Bit[] combineInto(Bit[] dest, Bit[] addition)
- {
- if (dest.length != addition.length)
- throw new IllegalArgumentException("Bit Arrays were not of equal length.");
- for (int i = 0; i < addition.length; i++) {
- dest[i] = dest[i].combineWith(addition[i]);
- }
- return dest;
- }
-
- interface BitOp
- {
- Bit execute(Bit a, Bit b);
- }
-}
+package era.mi.logic;\r
+\r
+import java.util.Arrays;\r
+\r
+public final class Util {\r
+\r
+ @SuppressWarnings("unchecked")\r
+ public static <T> T[] concat(T[]... arrays) {\r
+ if (arrays.length == 0)\r
+ throw new IllegalArgumentException("Cannot concatenate 0 arrays.");\r
+\r
+ int length = 0;\r
+ for (T[] array : arrays)\r
+ length += array.length;\r
+\r
+ T[] newArray = Arrays.copyOf(arrays[0], length);\r
+ int appendIndex = arrays[0].length;\r
+ for (int i = 1; i < arrays.length; i++) {\r
+ System.arraycopy(arrays[i], 0, newArray, appendIndex, arrays[i].length);\r
+ appendIndex += arrays[i].length;\r
+ }\r
+\r
+ return newArray;\r
+ }\r
+\r
+// @SuppressWarnings("unchecked")\r
+// public static <T> T[][] split(T[] array, int... lengths)\r
+// {\r
+// //TODO: implement array split again; This version contains an illegal cast\r
+// int totalLength = 0;\r
+// for(int length : lengths)\r
+// totalLength += length;\r
+// \r
+// if(totalLength != array.length)\r
+// throw new IllegalArgumentException(); //TODO: add proper error message\r
+// \r
+// Object[][] newArray = new Object[lengths.length][];\r
+// int splitIndex = 0;\r
+// for(int i = 0; i < lengths.length; i++)\r
+// {\r
+// System.arraycopy(array, splitIndex, newArray, 0, lengths[i]);\r
+// splitIndex += lengths[i];\r
+// }\r
+// \r
+// return (T[][]) newArray;\r
+// }\r
+\r
+ public static Bit[] and(Bit[] a, Bit[] b) {\r
+ return binBitOp(a, b, (bA, bB) -> Bit.and(bA, bB));\r
+ }\r
+\r
+ public static Bit[] or(Bit[] a, Bit[] b) {\r
+ return binBitOp(a, b, (bA, bB) -> Bit.or(bA, bB));\r
+ }\r
+\r
+ public static Bit[] xor(Bit[] a, Bit[] b) {\r
+ return binBitOp(a, b, (bA, bB) -> Bit.xor(bA, bB));\r
+ }\r
+\r
+ private static Bit[] binBitOp(Bit[] a, Bit[] b, BitOp op) {\r
+ if (a.length != b.length)\r
+ throw new IllegalArgumentException("Bit Arrays were not of equal length.");\r
+ Bit[] out = new Bit[a.length];\r
+ for (int i = 0; i < a.length; i++) {\r
+ out[i] = op.execute(a[i], b[i]);\r
+ }\r
+ return out;\r
+ }\r
+\r
+ public static Bit[] not(Bit[] a) {\r
+ Bit[] out = new Bit[a.length];\r
+ for (int i = 0; i < a.length; i++) {\r
+ out[i] = a[i].not();\r
+ }\r
+ return out;\r
+ }\r
+\r
+ /**\r
+ * uses the {@link Bit#combineWith(Bit)} method, does not create a new array, the result is stored in the first array.\r
+ * \r
+ * @author Christian Femers\r
+ */\r
+ public static Bit[] combineInto(Bit[] dest, Bit[] addition) {\r
+ if (dest.length != addition.length)\r
+ throw new IllegalArgumentException("Bit Arrays were not of equal length.");\r
+ for (int i = 0; i < addition.length; i++) {\r
+ dest[i] = dest[i].combineWith(addition[i]);\r
+ }\r
+ return dest;\r
+ }\r
+\r
+ interface BitOp {\r
+ Bit execute(Bit a, Bit b);\r
+ }\r
+}\r
-package era.mi.logic.components;
-
-import era.mi.logic.Bit;
-import era.mi.logic.Simulation;
-import era.mi.logic.wires.WireArray;
-import era.mi.logic.wires.WireArrayObserver;
-
-/**
- * A basic component that recomputes all outputs (with a delay), when it is updated.
- * @author Fabian Stemmler
- */
-public abstract class BasicComponent implements WireArrayObserver, Component
-{
- private int processTime;
-
- /**
- *
- * @param processTime Amount of time this component takes to update its outputs. Must be more than 0, otherwise 1 is assumed.
- *
- * @author Fabian Stemmler
- */
- public BasicComponent(int processTime)
- {
- this.processTime = processTime > 0 ? processTime : 1;
- }
-
- @Override
- public void update(WireArray initiator, Bit[] oldValues)
- {
- Simulation.TIMELINE.addEvent((e) -> {compute();}, processTime);
- }
-
- protected abstract void compute();
-}
+package era.mi.logic.components;\r
+\r
+import era.mi.logic.Bit;\r
+import era.mi.logic.Simulation;\r
+import era.mi.logic.wires.WireArray;\r
+import era.mi.logic.wires.WireArrayObserver;\r
+\r
+/**\r
+ * A basic component that recomputes all outputs (with a delay), when it is updated.\r
+ * \r
+ * @author Fabian Stemmler\r
+ */\r
+public abstract class BasicComponent implements WireArrayObserver, Component {\r
+ private int processTime;\r
+\r
+ /**\r
+ * \r
+ * @param processTime Amount of time this component takes to update its outputs. Must be more than 0, otherwise 1 is assumed.\r
+ * \r
+ * @author Fabian Stemmler\r
+ */\r
+ public BasicComponent(int processTime) {\r
+ this.processTime = processTime > 0 ? processTime : 1;\r
+ }\r
+\r
+ @Override\r
+ public void update(WireArray initiator, Bit[] oldValues) {\r
+ Simulation.TIMELINE.addEvent((e) -> {\r
+ compute();\r
+ }, processTime);\r
+ }\r
+\r
+ protected abstract void compute();\r
+}\r
import era.mi.logic.Bit;\r
import era.mi.logic.wires.WireArray;\r
\r
-public class BitDisplay extends BasicComponent\r
-{\r
+public class BitDisplay extends BasicComponent {\r
private final WireArray in;\r
private Bit[] displayedValue;\r
\r
- public BitDisplay(WireArray in)\r
- {\r
+ public BitDisplay(WireArray in) {\r
super(1);\r
this.in = in;\r
in.addObserver(this);\r
}\r
\r
@Override\r
- protected void compute()\r
- {\r
+ protected void compute() {\r
displayedValue = in.getValues();\r
}\r
\r
- public Bit[] getDisplayedValue()\r
- {\r
+ public Bit[] getDisplayedValue() {\r
return displayedValue;\r
}\r
\r
- public boolean isDisplaying(Bit... values)\r
- {\r
+ public boolean isDisplaying(Bit... values) {\r
return Arrays.equals(displayedValue, values);\r
}\r
\r
@Override\r
- public List<WireArray> getAllInputs()\r
- {\r
+ public List<WireArray> getAllInputs() {\r
return Collections.unmodifiableList(Arrays.asList(in));\r
}\r
\r
@Override\r
- public List<WireArray> getAllOutputs()\r
- {\r
+ public List<WireArray> getAllOutputs() {\r
return Collections.unmodifiableList(new ArrayList<WireArray>());\r
}\r
}\r
-package era.mi.logic.components;
-
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.List;
-
-import era.mi.logic.Bit;
-import era.mi.logic.Simulation;
-import era.mi.logic.timeline.TimelineEvent;
-import era.mi.logic.timeline.TimelineEventHandler;
-import era.mi.logic.wires.WireArray;
-import era.mi.logic.wires.WireArray.WireArrayInput;
-
-public class Clock implements TimelineEventHandler, Component
-{
- private boolean toggle = false;
- private WireArrayInput outI;
- private int delta;
-
- /**
- *
- * @param out {@link WireArray} the clock's impulses are fed into
- * @param delta ticks between rising and falling edge
- */
- public Clock(WireArray out, int delta)
- {
- this.delta = delta;
- this.outI = out.createInput();
- Simulation.TIMELINE.addEvent(this, 50);
- }
-
- @Override
- public void handle(TimelineEvent e)
- {
- addToTimeline();
- outI.feedSignals(new Bit[] { toggle ? Bit.ONE : Bit.ZERO });
- toggle = !toggle;
- }
-
- public WireArray getOut()
- {
- return outI.owner;
- }
-
- private void addToTimeline()
- {
- Simulation.TIMELINE.addEvent(this, delta);
- }
-
- @Override
- public List<WireArray> getAllInputs()
- {
- return Collections.unmodifiableList(Arrays.asList());
- }
-
- @Override
- public List<WireArray> getAllOutputs()
- {
- return Collections.unmodifiableList(Arrays.asList(outI.owner));
- }
-}
+package era.mi.logic.components;\r
+\r
+import java.util.Arrays;\r
+import java.util.Collections;\r
+import java.util.List;\r
+\r
+import era.mi.logic.Bit;\r
+import era.mi.logic.Simulation;\r
+import era.mi.logic.timeline.TimelineEvent;\r
+import era.mi.logic.timeline.TimelineEventHandler;\r
+import era.mi.logic.wires.WireArray;\r
+import era.mi.logic.wires.WireArray.WireArrayInput;\r
+\r
+public class Clock implements TimelineEventHandler, Component {\r
+ private boolean toggle = false;\r
+ private WireArrayInput outI;\r
+ private int delta;\r
+\r
+ /**\r
+ * \r
+ * @param out {@link WireArray} the clock's impulses are fed into\r
+ * @param delta ticks between rising and falling edge\r
+ */\r
+ public Clock(WireArray out, int delta) {\r
+ this.delta = delta;\r
+ this.outI = out.createInput();\r
+ Simulation.TIMELINE.addEvent(this, 50);\r
+ }\r
+\r
+ @Override\r
+ public void handle(TimelineEvent e) {\r
+ addToTimeline();\r
+ outI.feedSignals(new Bit[] { toggle ? Bit.ONE : Bit.ZERO });\r
+ toggle = !toggle;\r
+ }\r
+\r
+ public WireArray getOut() {\r
+ return outI.owner;\r
+ }\r
+\r
+ private void addToTimeline() {\r
+ Simulation.TIMELINE.addEvent(this, delta);\r
+ }\r
+\r
+ @Override\r
+ public List<WireArray> getAllInputs() {\r
+ return Collections.unmodifiableList(Arrays.asList());\r
+ }\r
+\r
+ @Override\r
+ public List<WireArray> getAllOutputs() {\r
+ return Collections.unmodifiableList(Arrays.asList(outI.owner));\r
+ }\r
+}\r
\r
import era.mi.logic.wires.WireArray;\r
\r
-public interface Component\r
-{\r
+public interface Component {\r
\r
/**\r
- * Returns immutable list of all inputs to the {@link Component} (including e.g. the select bits to a MUX).\r
- * Intended for visualization in the UI.\r
+ * Returns immutable list of all inputs to the {@link Component} (including e.g. the select bits to a MUX). Intended for visualization\r
+ * in the UI.\r
*/\r
public List<WireArray> getAllInputs();\r
- \r
+\r
/**\r
- * Returns immutable list of all outputs to the {@link Component}.\r
- * Intended for visualization in the UI.\r
+ * Returns immutable list of all outputs to the {@link Component}. Intended for visualization in the UI.\r
*/\r
public List<WireArray> getAllOutputs();\r
}\r
-package era.mi.logic.components;
-
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.List;
-
-import era.mi.logic.wires.WireArray;
-import era.mi.logic.wires.WireArray.WireArrayInput;
-
-/**
- * Models a multiplexer. Takes an arbitrary amount of input {@link WireArray}s, one of which,
- * as determined by select, is put through to the output.
- * @author Fabian Stemmler
- *
- */
-public class Demux extends BasicComponent
-{
- private final WireArray select, in;
- private final WireArray[] outputs;
- private final WireArrayInput[] outputsI;
- private final int outputSize;
- private int selected = -1;
-
- /**
- * Input {@link WireArray}s and out must be of uniform length
- * @param out Must be of uniform length with all inputs.
- * @param select Indexes the input array which is to be mapped to the output. Must have enough bits
- * to index all inputs.
- * @param outputs One of these inputs is mapped to the output, depending on the select bits
- */
- public Demux(int processTime, WireArray in, WireArray select, WireArray... outputs)
- {
- super(processTime);
- outputSize = in.length;
-
- this.in = in;
- this.outputs = outputs;
- this.outputsI = new WireArrayInput[outputs.length];
- for(int i = 0; i < this.outputsI.length; i++)
- {
- if(outputs[i].length != outputSize)
- throw new IllegalArgumentException("All DEMUX wire arrays must be of uniform length!");
- this.outputsI[i] = outputs[i].createInput();
- }
-
- this.select = select;
- select.addObserver(this);
-
- int maxInputs = 1 << select.length;
- if(this.outputsI.length > maxInputs)
- throw new IllegalArgumentException("There are more outputs ("
- + this.outputsI.length + ") to the DEMUX than supported by "
- + select.length + " select bits (" + maxInputs + ").");
- in.addObserver(this);
- }
-
- @Override
- public void compute() {
- int selectValue = select.hasNumericValue() ? (int) select.getUnsignedValue() : -1;
- if(selectValue >= outputsI.length)
- selectValue = -1;
-
- if(selected != selectValue && selected != -1)
- outputsI[selected].clearSignals();
-
- selected = selectValue;
-
- if(selectValue != -1)
- outputsI[selectValue].feedSignals(in.getValues());
- }
-
- @Override
- public List<WireArray> getAllInputs()
- {
- return Collections.unmodifiableList(Arrays.asList(in, select));
- }
-
- @Override
- public List<WireArray> getAllOutputs()
- {
- return Collections.unmodifiableList(Arrays.asList(outputs));
- }
-}
+package era.mi.logic.components;\r
+\r
+import java.util.Arrays;\r
+import java.util.Collections;\r
+import java.util.List;\r
+\r
+import era.mi.logic.wires.WireArray;\r
+import era.mi.logic.wires.WireArray.WireArrayInput;\r
+\r
+/**\r
+ * Models a multiplexer. Takes an arbitrary amount of input {@link WireArray}s, one of which, as determined by select, is put through to the\r
+ * output.\r
+ * \r
+ * @author Fabian Stemmler\r
+ *\r
+ */\r
+public class Demux extends BasicComponent {\r
+ private final WireArray select, in;\r
+ private final WireArray[] outputs;\r
+ private final WireArrayInput[] outputsI;\r
+ private final int outputSize;\r
+ private int selected = -1;\r
+\r
+ /**\r
+ * Input {@link WireArray}s and out must be of uniform length\r
+ * \r
+ * @param out Must be of uniform length with all inputs.\r
+ * @param select Indexes the input array which is to be mapped to the output. Must have enough bits to index all inputs.\r
+ * @param outputs One of these inputs is mapped to the output, depending on the select bits\r
+ */\r
+ public Demux(int processTime, WireArray in, WireArray select, WireArray... outputs) {\r
+ super(processTime);\r
+ outputSize = in.length;\r
+\r
+ this.in = in;\r
+ this.outputs = outputs;\r
+ this.outputsI = new WireArrayInput[outputs.length];\r
+ for (int i = 0; i < this.outputsI.length; i++) {\r
+ if (outputs[i].length != outputSize)\r
+ throw new IllegalArgumentException("All DEMUX wire arrays must be of uniform length!");\r
+ this.outputsI[i] = outputs[i].createInput();\r
+ }\r
+\r
+ this.select = select;\r
+ select.addObserver(this);\r
+\r
+ int maxInputs = 1 << select.length;\r
+ if (this.outputsI.length > maxInputs)\r
+ throw new IllegalArgumentException("There are more outputs (" + this.outputsI.length + ") to the DEMUX than supported by "\r
+ + select.length + " select bits (" + maxInputs + ").");\r
+ in.addObserver(this);\r
+ }\r
+\r
+ @Override\r
+ public void compute() {\r
+ int selectValue = select.hasNumericValue() ? (int) select.getUnsignedValue() : -1;\r
+ if (selectValue >= outputsI.length)\r
+ selectValue = -1;\r
+\r
+ if (selected != selectValue && selected != -1)\r
+ outputsI[selected].clearSignals();\r
+\r
+ selected = selectValue;\r
+\r
+ if (selectValue != -1)\r
+ outputsI[selectValue].feedSignals(in.getValues());\r
+ }\r
+\r
+ @Override\r
+ public List<WireArray> getAllInputs() {\r
+ return Collections.unmodifiableList(Arrays.asList(in, select));\r
+ }\r
+\r
+ @Override\r
+ public List<WireArray> getAllOutputs() {\r
+ return Collections.unmodifiableList(Arrays.asList(outputs));\r
+ }\r
+}\r
* @author Christian Femers\r
*\r
*/\r
-public class ManualSwitch implements Component \r
-{\r
+public class ManualSwitch implements Component {\r
private WireArray output;\r
private WireArrayInput outputI;\r
private boolean isOn;\r
- \r
- public ManualSwitch(WireArray output) \r
- {\r
- if(output.length != 1)\r
+\r
+ public ManualSwitch(WireArray output) {\r
+ if (output.length != 1)\r
throw new IllegalArgumentException("Switch output can be only a single wire");\r
this.output = output;\r
this.outputI = output.createInput();\r
}\r
- \r
- public void switchOn()\r
- {\r
+\r
+ public void switchOn() {\r
setState(true);\r
}\r
- \r
- public void switchOff()\r
- {\r
+\r
+ public void switchOff() {\r
setState(false);\r
}\r
- \r
- public void toggle()\r
- {\r
+\r
+ public void toggle() {\r
setState(!isOn);\r
}\r
- \r
- public void setState(boolean isOn)\r
- {\r
- if(this.isOn == isOn)\r
+\r
+ public void setState(boolean isOn) {\r
+ if (this.isOn == isOn)\r
return;\r
this.isOn = isOn;\r
outputI.feedSignals(getValue());\r
}\r
- \r
- public boolean isOn()\r
- {\r
+\r
+ public boolean isOn() {\r
return isOn;\r
}\r
- \r
- public Bit getValue()\r
- {\r
+\r
+ public Bit getValue() {\r
return isOn ? Bit.ONE : Bit.ZERO;\r
}\r
\r
-package era.mi.logic.components;
-
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.List;
-
-import era.mi.logic.Bit;
-import era.mi.logic.wires.WireArray;
-import era.mi.logic.wires.WireArray.WireArrayInput;
-import era.mi.logic.wires.WireArrayObserver;
-
-public class Merger implements WireArrayObserver, Component
-{
- private WireArrayInput outI;
- private WireArray[] inputs;
- private int[] beginningIndex;
-
- /**
- *
- * @param union The output of merging n {@link WireArray}s into one. Must have
- * length = a1.length() + a2.length() + ... + an.length().
- * @param inputs The inputs to be merged into the union
- */
- public Merger(WireArray union, WireArray... inputs)
- {
- this.inputs = inputs;
- this.outI = union.createInput();
- this.beginningIndex = new int[inputs.length];
-
- int length = 0;
- for (int i = 0; i < inputs.length; i++)
- {
- beginningIndex[i] = length;
- length += inputs[i].length;
- inputs[i].addObserver(this);
- }
-
- if (length != union.length)
- throw new IllegalArgumentException(
- "The output of merging n WireArrays into one must have length = a1.length() + a2.length() + ... + an.length().");
- }
-
- public WireArray getInput(int index)
- {
- return inputs[index];
- }
-
- public WireArray getUnion()
- {
- return outI.owner;
- }
-
- @Override
- public void update(WireArray initiator, Bit[] oldValues)
- {
- int index = find(initiator);
- int beginning = beginningIndex[index];
- outI.feedSignals(beginning, initiator.getValues());
- }
-
- private int find(WireArray w)
- {
- for (int i = 0; i < inputs.length; i++)
- if (inputs[i] == w)
- return i;
- return -1;
- }
-
- public WireArray[] getInputs()
- {
- return inputs.clone();
- }
-
- @Override
- public List<WireArray> getAllInputs()
- {
- return Collections.unmodifiableList(Arrays.asList(inputs));
- }
-
- @Override
- public List<WireArray> getAllOutputs()
- {
- return Collections.unmodifiableList(Arrays.asList(outI.owner));
- }
-}
+package era.mi.logic.components;\r
+\r
+import java.util.Arrays;\r
+import java.util.Collections;\r
+import java.util.List;\r
+\r
+import era.mi.logic.Bit;\r
+import era.mi.logic.wires.WireArray;\r
+import era.mi.logic.wires.WireArray.WireArrayInput;\r
+import era.mi.logic.wires.WireArrayObserver;\r
+\r
+public class Merger implements WireArrayObserver, Component {\r
+ private WireArrayInput outI;\r
+ private WireArray[] inputs;\r
+ private int[] beginningIndex;\r
+\r
+ /**\r
+ * \r
+ * @param union The output of merging n {@link WireArray}s into one. Must have length = a1.length() + a2.length() + ... + an.length().\r
+ * @param inputs The inputs to be merged into the union\r
+ */\r
+ public Merger(WireArray union, WireArray... inputs) {\r
+ this.inputs = inputs;\r
+ this.outI = union.createInput();\r
+ this.beginningIndex = new int[inputs.length];\r
+\r
+ int length = 0;\r
+ for (int i = 0; i < inputs.length; i++) {\r
+ beginningIndex[i] = length;\r
+ length += inputs[i].length;\r
+ inputs[i].addObserver(this);\r
+ }\r
+\r
+ if (length != union.length)\r
+ throw new IllegalArgumentException(\r
+ "The output of merging n WireArrays into one must have length = a1.length() + a2.length() + ... + an.length().");\r
+ }\r
+\r
+ public WireArray getInput(int index) {\r
+ return inputs[index];\r
+ }\r
+\r
+ public WireArray getUnion() {\r
+ return outI.owner;\r
+ }\r
+\r
+ @Override\r
+ public void update(WireArray initiator, Bit[] oldValues) {\r
+ int index = find(initiator);\r
+ int beginning = beginningIndex[index];\r
+ outI.feedSignals(beginning, initiator.getValues());\r
+ }\r
+\r
+ private int find(WireArray w) {\r
+ for (int i = 0; i < inputs.length; i++)\r
+ if (inputs[i] == w)\r
+ return i;\r
+ return -1;\r
+ }\r
+\r
+ public WireArray[] getInputs() {\r
+ return inputs.clone();\r
+ }\r
+\r
+ @Override\r
+ public List<WireArray> getAllInputs() {\r
+ return Collections.unmodifiableList(Arrays.asList(inputs));\r
+ }\r
+\r
+ @Override\r
+ public List<WireArray> getAllOutputs() {\r
+ return Collections.unmodifiableList(Arrays.asList(outI.owner));\r
+ }\r
+}\r
-package era.mi.logic.components;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.List;
-
-import era.mi.logic.wires.WireArray;
-import era.mi.logic.wires.WireArray.WireArrayInput;
-
-/**
- * Models a multiplexer. Takes an arbitrary amount of input {@link WireArray}s, one of which,
- * as determined by select, is put through to the output.
- * @author Fabian Stemmler
- *
- */
-public class Mux extends BasicComponent
-{
- private WireArray select;
- private WireArrayInput outI;
- private WireArray[] inputs;
- private final int outputSize;
- /**
- * Input {@link WireArray}s and out must be of uniform length
- * @param out Must be of uniform length with all inputs.
- * @param select Indexes the input array which is to be mapped to the output. Must have enough bits
- * to index all inputs.
- * @param inputs One of these inputs is mapped to the output, depending on the select bits
- */
- public Mux(int processTime, WireArray out, WireArray select, WireArray... inputs)
- {
- super(processTime);
- outputSize = out.length;
-
- this.inputs = inputs.clone();
- for(int i = 0; i < this.inputs.length; i++)
- {
- if(inputs[i].length != outputSize)
- throw new IllegalArgumentException("All MUX wire arrays must be of uniform length!");
- inputs[i].addObserver(this);
- }
-
- this.select = select;
- select.addObserver(this);
-
- int maxInputs = 1 << select.length;
- if(this.inputs.length > maxInputs)
- throw new IllegalArgumentException("There are more inputs ("
- + this.inputs.length + ") to the MUX than supported by "
- + select.length + " select bits (" + maxInputs + ").");
-
- outI = out.createInput();
- }
-
- public WireArray getOut()
- {
- return outI.owner;
- }
-
- public WireArray getSelect()
- {
- return select;
- }
-
- @Override
- public void compute() {
- int selectValue;
- if(!select.hasNumericValue() || (selectValue = (int) select.getUnsignedValue()) >= inputs.length)
- {
- outI.clearSignals();
- return;
- }
-
- WireArray active = inputs[selectValue];
- outI.feedSignals(active.getValues());
- }
-
- @Override
- public List<WireArray> getAllInputs()
- {
- ArrayList<WireArray> wires = new ArrayList<WireArray>(Arrays.asList(inputs));
- wires.add(select);
- return Collections.unmodifiableList(wires);
- }
-
- @Override
- public List<WireArray> getAllOutputs()
- {
- return Collections.unmodifiableList(Arrays.asList(outI.owner));
- }
-}
+package era.mi.logic.components;\r
+\r
+import java.util.ArrayList;\r
+import java.util.Arrays;\r
+import java.util.Collections;\r
+import java.util.List;\r
+\r
+import era.mi.logic.wires.WireArray;\r
+import era.mi.logic.wires.WireArray.WireArrayInput;\r
+\r
+/**\r
+ * Models a multiplexer. Takes an arbitrary amount of input {@link WireArray}s, one of which, as determined by select, is put through to the\r
+ * output.\r
+ * \r
+ * @author Fabian Stemmler\r
+ *\r
+ */\r
+public class Mux extends BasicComponent {\r
+ private WireArray select;\r
+ private WireArrayInput outI;\r
+ private WireArray[] inputs;\r
+ private final int outputSize;\r
+\r
+ /**\r
+ * Input {@link WireArray}s and out must be of uniform length\r
+ * \r
+ * @param out Must be of uniform length with all inputs.\r
+ * @param select Indexes the input array which is to be mapped to the output. Must have enough bits to index all inputs.\r
+ * @param inputs One of these inputs is mapped to the output, depending on the select bits\r
+ */\r
+ public Mux(int processTime, WireArray out, WireArray select, WireArray... inputs) {\r
+ super(processTime);\r
+ outputSize = out.length;\r
+\r
+ this.inputs = inputs.clone();\r
+ for (int i = 0; i < this.inputs.length; i++) {\r
+ if (inputs[i].length != outputSize)\r
+ throw new IllegalArgumentException("All MUX wire arrays must be of uniform length!");\r
+ inputs[i].addObserver(this);\r
+ }\r
+\r
+ this.select = select;\r
+ select.addObserver(this);\r
+\r
+ int maxInputs = 1 << select.length;\r
+ if (this.inputs.length > maxInputs)\r
+ throw new IllegalArgumentException("There are more inputs (" + this.inputs.length + ") to the MUX than supported by "\r
+ + select.length + " select bits (" + maxInputs + ").");\r
+\r
+ outI = out.createInput();\r
+ }\r
+\r
+ public WireArray getOut() {\r
+ return outI.owner;\r
+ }\r
+\r
+ public WireArray getSelect() {\r
+ return select;\r
+ }\r
+\r
+ @Override\r
+ public void compute() {\r
+ int selectValue;\r
+ if (!select.hasNumericValue() || (selectValue = (int) select.getUnsignedValue()) >= inputs.length) {\r
+ outI.clearSignals();\r
+ return;\r
+ }\r
+\r
+ WireArray active = inputs[selectValue];\r
+ outI.feedSignals(active.getValues());\r
+ }\r
+\r
+ @Override\r
+ public List<WireArray> getAllInputs() {\r
+ ArrayList<WireArray> wires = new ArrayList<WireArray>(Arrays.asList(inputs));\r
+ wires.add(select);\r
+ return Collections.unmodifiableList(wires);\r
+ }\r
+\r
+ @Override\r
+ public List<WireArray> getAllOutputs() {\r
+ return Collections.unmodifiableList(Arrays.asList(outI.owner));\r
+ }\r
+}\r
-package era.mi.logic.components;
-
-import era.mi.logic.Bit;
-import era.mi.logic.wires.WireArray;
-import era.mi.logic.wires.WireArray.WireArrayInput;
-import era.mi.logic.wires.WireArrayObserver;
-
-public class Splitter implements WireArrayObserver
-{
- private WireArray input;
- private WireArrayInput[] outputs;
-
- public Splitter(WireArray input, WireArray... outputs)
- {
- this.input = input;
- this.outputs = WireArray.extractInputs(outputs);
- input.addObserver(this);
- int length = 0;
- for(WireArray out : outputs)
- length += out.length;
-
- if(input.length != length)
- throw new IllegalArgumentException("The input of splitting one into n WireArrays must have length = a1.length() + a2.length() + ... + an.length().");
- }
-
- protected void compute()
- {
- int startIndex = 0;
- Bit[] inputBits = input.getValues();
- for(int i = 0; i < outputs.length; i++)
- {
- Bit[] outputBits = new Bit[outputs[i].owner.length];
- System.arraycopy(inputBits, startIndex, outputBits, 0, outputs[i].owner.length);
- outputs[i].feedSignals(outputBits);
- startIndex += outputs[i].owner.length;
- }
- }
-
- @Override
- public void update(WireArray initiator, Bit[] oldValues)
- {
- compute();
- }
-}
+package era.mi.logic.components;\r
+\r
+import era.mi.logic.Bit;\r
+import era.mi.logic.wires.WireArray;\r
+import era.mi.logic.wires.WireArray.WireArrayInput;\r
+import era.mi.logic.wires.WireArrayObserver;\r
+\r
+public class Splitter implements WireArrayObserver {\r
+ private WireArray input;\r
+ private WireArrayInput[] outputs;\r
+\r
+ public Splitter(WireArray input, WireArray... outputs) {\r
+ this.input = input;\r
+ this.outputs = WireArray.extractInputs(outputs);\r
+ input.addObserver(this);\r
+ int length = 0;\r
+ for (WireArray out : outputs)\r
+ length += out.length;\r
+\r
+ if (input.length != length)\r
+ throw new IllegalArgumentException(\r
+ "The input of splitting one into n WireArrays must have length = a1.length() + a2.length() + ... + an.length().");\r
+ }\r
+\r
+ protected void compute() {\r
+ int startIndex = 0;\r
+ Bit[] inputBits = input.getValues();\r
+ for (int i = 0; i < outputs.length; i++) {\r
+ Bit[] outputBits = new Bit[outputs[i].owner.length];\r
+ System.arraycopy(inputBits, startIndex, outputBits, 0, outputs[i].owner.length);\r
+ outputs[i].feedSignals(outputBits);\r
+ startIndex += outputs[i].owner.length;\r
+ }\r
+ }\r
+\r
+ @Override\r
+ public void update(WireArray initiator, Bit[] oldValues) {\r
+ compute();\r
+ }\r
+}\r
-package era.mi.logic.components;
-
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.List;
-
-import era.mi.logic.Bit;
-import era.mi.logic.wires.WireArray;
-import era.mi.logic.wires.WireArray.WireArrayInput;
-
-public class TriStateBuffer extends BasicComponent{
- WireArray in, enable;
- WireArrayInput outI;
-
- public TriStateBuffer(int processTime, WireArray in, WireArray out, WireArray enable) {
- super(processTime);
- if(in.length != out.length)
- throw new IllegalArgumentException("Tri-state output must have the same amount of bits as the input. Input: " + in.length + " Output: " + out.length);
- if(enable.length != 1)
- throw new IllegalArgumentException("Tri-state enable must have exactly one bit, not " + enable.length + ".");
- this.in = in;
- in.addObserver(this);
- this.enable = enable;
- enable.addObserver(this);
- outI = out.createInput();
- }
-
- @Override
- protected void compute()
- {
- if(enable.getValue() == Bit.ONE)
- outI.feedSignals(in.getValues());
- else
- outI.clearSignals();
- }
-
- @Override
- public List<WireArray> getAllInputs()
- {
- return Collections.unmodifiableList(Arrays.asList(in, enable));
- }
-
- @Override
- public List<WireArray> getAllOutputs()
- {
- return Collections.unmodifiableList(Arrays.asList(outI.owner));
- }
-
-}
+package era.mi.logic.components;\r
+\r
+import java.util.Arrays;\r
+import java.util.Collections;\r
+import java.util.List;\r
+\r
+import era.mi.logic.Bit;\r
+import era.mi.logic.wires.WireArray;\r
+import era.mi.logic.wires.WireArray.WireArrayInput;\r
+\r
+public class TriStateBuffer extends BasicComponent {\r
+ WireArray in, enable;\r
+ WireArrayInput outI;\r
+\r
+ public TriStateBuffer(int processTime, WireArray in, WireArray out, WireArray enable) {\r
+ super(processTime);\r
+ if (in.length != out.length)\r
+ throw new IllegalArgumentException(\r
+ "Tri-state output must have the same amount of bits as the input. Input: " + in.length + " Output: " + out.length);\r
+ if (enable.length != 1)\r
+ throw new IllegalArgumentException("Tri-state enable must have exactly one bit, not " + enable.length + ".");\r
+ this.in = in;\r
+ in.addObserver(this);\r
+ this.enable = enable;\r
+ enable.addObserver(this);\r
+ outI = out.createInput();\r
+ }\r
+\r
+ @Override\r
+ protected void compute() {\r
+ if (enable.getValue() == Bit.ONE)\r
+ outI.feedSignals(in.getValues());\r
+ else\r
+ outI.clearSignals();\r
+ }\r
+\r
+ @Override\r
+ public List<WireArray> getAllInputs() {\r
+ return Collections.unmodifiableList(Arrays.asList(in, enable));\r
+ }\r
+\r
+ @Override\r
+ public List<WireArray> getAllOutputs() {\r
+ return Collections.unmodifiableList(Arrays.asList(outI.owner));\r
+ }\r
+\r
+}\r
-package era.mi.logic.components.gates;
-
-import era.mi.logic.Util;
-import era.mi.logic.wires.WireArray;
-
-public class AndGate extends MultiInputGate
-{
- public AndGate(int processTime, WireArray out, WireArray... in)
- {
- super(processTime, Util::and, out, in);
- }
-}
+package era.mi.logic.components.gates;\r
+\r
+import era.mi.logic.Util;\r
+import era.mi.logic.wires.WireArray;\r
+\r
+public class AndGate extends MultiInputGate {\r
+ public AndGate(int processTime, WireArray out, WireArray... in) {\r
+ super(processTime, Util::and, out, in);\r
+ }\r
+}\r
import era.mi.logic.wires.WireArray;\r
import era.mi.logic.wires.WireArray.WireArrayInput;\r
\r
-public abstract class MultiInputGate extends BasicComponent\r
-{\r
+public abstract class MultiInputGate extends BasicComponent {\r
protected WireArray[] in;\r
protected WireArray out;\r
protected WireArrayInput outI;\r
protected final int length;\r
protected Operation op;\r
- \r
- protected MultiInputGate(int processTime, Operation op, WireArray out, WireArray... in)\r
- {\r
+\r
+ protected MultiInputGate(int processTime, Operation op, WireArray out, WireArray... in) {\r
super(processTime);\r
this.op = op;\r
length = out.length;\r
this.in = in.clone();\r
- if(in.length < 1)\r
+ if (in.length < 1)\r
throw new IllegalArgumentException(String.format("Cannot create gate with %d wires.", in.length));\r
- for(WireArray w : in)\r
- {\r
- if(w.length != length)\r
+ for (WireArray w : in) {\r
+ if (w.length != length)\r
throw new IllegalArgumentException("All wires connected to the gate must be of uniform length.");\r
w.addObserver(this);\r
}\r
outI = out.createInput();\r
}\r
\r
-\r
@Override\r
- public List<WireArray> getAllInputs()\r
- {\r
+ public List<WireArray> getAllInputs() {\r
return Collections.unmodifiableList(Arrays.asList(in));\r
}\r
\r
@Override\r
- public List<WireArray> getAllOutputs()\r
- {\r
+ public List<WireArray> getAllOutputs() {\r
return Collections.unmodifiableList(Arrays.asList(out));\r
}\r
- \r
- protected void compute()\r
- {\r
+\r
+ protected void compute() {\r
Bit[] result = in[0].getValues();\r
- for(int i = 1; i < in.length; i++)\r
+ for (int i = 1; i < in.length; i++)\r
result = op.execute(result, in[i].getValues());\r
outI.feedSignals(result);\r
}\r
- \r
- protected interface Operation\r
- {\r
+\r
+ protected interface Operation {\r
public Bit[] execute(Bit[] a, Bit[] b);\r
}\r
}\r
-package era.mi.logic.components.gates;
-
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.List;
-
-import era.mi.logic.Util;
-import era.mi.logic.components.BasicComponent;
-import era.mi.logic.wires.WireArray;
-import era.mi.logic.wires.WireArray.WireArrayInput;
-
-public class NotGate extends BasicComponent
-{
- private WireArray in, out;
- private WireArrayInput outI;
-
-
- public NotGate(int processTime, WireArray in, WireArray out)
- {
- super(processTime);
- this.in = in;
- in.addObserver(this);
- this.out = out;
- outI = out.createInput();
- }
-
- public void compute()
- {
- outI.feedSignals(Util.not(in.getValues()));
- }
-
- public WireArray getIn()
- {
- return in;
- }
-
- public WireArray getOut()
- {
- return out;
- }
-
- @Override
- public List<WireArray> getAllInputs()
- {
- return Collections.unmodifiableList(Arrays.asList(in));
- }
-
- @Override
- public List<WireArray> getAllOutputs()
- {
- return Collections.unmodifiableList(Arrays.asList(out));
- }
-}
+package era.mi.logic.components.gates;\r
+\r
+import java.util.Arrays;\r
+import java.util.Collections;\r
+import java.util.List;\r
+\r
+import era.mi.logic.Util;\r
+import era.mi.logic.components.BasicComponent;\r
+import era.mi.logic.wires.WireArray;\r
+import era.mi.logic.wires.WireArray.WireArrayInput;\r
+\r
+public class NotGate extends BasicComponent {\r
+ private WireArray in, out;\r
+ private WireArrayInput outI;\r
+\r
+ public NotGate(int processTime, WireArray in, WireArray out) {\r
+ super(processTime);\r
+ this.in = in;\r
+ in.addObserver(this);\r
+ this.out = out;\r
+ outI = out.createInput();\r
+ }\r
+\r
+ public void compute() {\r
+ outI.feedSignals(Util.not(in.getValues()));\r
+ }\r
+\r
+ public WireArray getIn() {\r
+ return in;\r
+ }\r
+\r
+ public WireArray getOut() {\r
+ return out;\r
+ }\r
+\r
+ @Override\r
+ public List<WireArray> getAllInputs() {\r
+ return Collections.unmodifiableList(Arrays.asList(in));\r
+ }\r
+\r
+ @Override\r
+ public List<WireArray> getAllOutputs() {\r
+ return Collections.unmodifiableList(Arrays.asList(out));\r
+ }\r
+}\r
-package era.mi.logic.components.gates;
-
-import era.mi.logic.Util;
-import era.mi.logic.wires.WireArray;
-
-public class OrGate extends MultiInputGate
-{
- public OrGate(int processTime, WireArray out, WireArray... in)
- {
- super(processTime, Util::or, out, in);
- }
-}
+package era.mi.logic.components.gates;\r
+\r
+import era.mi.logic.Util;\r
+import era.mi.logic.wires.WireArray;\r
+\r
+public class OrGate extends MultiInputGate {\r
+ public OrGate(int processTime, WireArray out, WireArray... in) {\r
+ super(processTime, Util::or, out, in);\r
+ }\r
+}\r
-package era.mi.logic.components.gates;
-
-import era.mi.logic.Util;
-import era.mi.logic.wires.WireArray;
-
-/**
- * Outputs 1 when the number of 1 inputs is odd.
- * @author Fabian Stemmler
- */
-public class XorGate extends MultiInputGate
-{
- public XorGate(int processTime, WireArray out, WireArray... in)
- {
- super(processTime, Util::xor, out, in);
- }
-
-}
+package era.mi.logic.components.gates;\r
+\r
+import era.mi.logic.Util;\r
+import era.mi.logic.wires.WireArray;\r
+\r
+/**\r
+ * Outputs 1 when the number of 1 inputs is odd.\r
+ * \r
+ * @author Fabian Stemmler\r
+ */\r
+public class XorGate extends MultiInputGate {\r
+ public XorGate(int processTime, WireArray out, WireArray... in) {\r
+ super(processTime, Util::xor, out, in);\r
+ }\r
+\r
+}\r
import era.mi.logic.wires.WireArray;\r
import era.mi.logic.wires.WireArray.WireArrayInput;\r
\r
-class ComponentTest\r
-{\r
- \r
+class ComponentTest {\r
+\r
@Test\r
- void circuitExampleTest()\r
- {\r
+ void circuitExampleTest() {\r
Simulation.TIMELINE.reset();\r
- WireArray a = new WireArray(1, 1), b = new WireArray(1, 1), c = new WireArray(1, 10), d = new WireArray(2, 1), e = new WireArray(1, 1),\r
- f = new WireArray(1, 1), g = new WireArray(1, 1), h = new WireArray(2, 1), i = new WireArray(2, 1), j = new WireArray(1, 1), k = new WireArray(1, 1);\r
+ WireArray a = new WireArray(1, 1), b = new WireArray(1, 1), c = new WireArray(1, 10), d = new WireArray(2, 1),\r
+ e = new WireArray(1, 1), f = new WireArray(1, 1), g = new WireArray(1, 1), h = new WireArray(2, 1), i = new WireArray(2, 1),\r
+ j = new WireArray(1, 1), k = new WireArray(1, 1);\r
new AndGate(1, f, a, b);\r
new NotGate(1, f, g);\r
new Merger(h, c, g);\r
new Mux(1, i, e, h, d);\r
new Splitter(i, k, j);\r
- \r
+\r
a.createInput().feedSignals(Bit.ZERO);\r
b.createInput().feedSignals(Bit.ONE);\r
c.createInput().feedSignals(Bit.ZERO);\r
d.createInput().feedSignals(Bit.ONE, Bit.ONE);\r
e.createInput().feedSignals(Bit.ZERO);\r
- \r
+\r
Simulation.TIMELINE.executeAll();\r
- \r
+\r
assertEquals(Bit.ONE, j.getValue());\r
assertEquals(Bit.ZERO, k.getValue());\r
}\r
\r
- @Test\r
- void splitterTest()\r
- {\r
- Simulation.TIMELINE.reset();\r
- WireArray a = new WireArray(3, 1), b = new WireArray(2, 1), c = new WireArray(3, 1), in = new WireArray(8, 1);\r
- in.createInput().feedSignals(Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE);\r
- new Splitter(in, a, b, c);\r
+ @Test\r
+ void splitterTest() {\r
+ Simulation.TIMELINE.reset();\r
+ WireArray a = new WireArray(3, 1), b = new WireArray(2, 1), c = new WireArray(3, 1), in = new WireArray(8, 1);\r
+ in.createInput().feedSignals(Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE);\r
+ new Splitter(in, a, b, c);\r
+\r
+ Simulation.TIMELINE.executeAll();\r
+\r
+ assertBitArrayEquals(a.getValues(), Bit.ZERO, Bit.ONE, Bit.ZERO);\r
+ assertBitArrayEquals(b.getValues(), Bit.ONE, Bit.ZERO);\r
+ assertBitArrayEquals(c.getValues(), Bit.ONE, Bit.ZERO, Bit.ONE);\r
+ }\r
+\r
+ @Test\r
+ void mergerTest() {\r
+ Simulation.TIMELINE.reset();\r
+ WireArray a = new WireArray(3, 1), b = new WireArray(2, 1), c = new WireArray(3, 1), out = new WireArray(8, 1);\r
+ a.createInput().feedSignals(Bit.ZERO, Bit.ONE, Bit.ZERO);\r
+ b.createInput().feedSignals(Bit.ONE, Bit.ZERO);\r
+ c.createInput().feedSignals(Bit.ONE, Bit.ZERO, Bit.ONE);\r
+\r
+ new Merger(out, a, b, c);\r
+\r
+ Simulation.TIMELINE.executeAll();\r
+\r
+ assertTrue(\r
+ Arrays.equals(out.getValues(), new Bit[] { Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE }));\r
+ }\r
+\r
+ @Test\r
+ void triStateBufferTest() {\r
+ WireArray a = new WireArray(1, 1), b = new WireArray(1, 1), en = new WireArray(1, 1), notEn = new WireArray(1, 1);\r
+ new NotGate(1, en, notEn);\r
+ new TriStateBuffer(1, a, b, en);\r
+ new TriStateBuffer(1, b, a, notEn);\r
+\r
+ WireArrayInput enI = en.createInput(), aI = a.createInput(), bI = b.createInput();\r
+ enI.feedSignals(Bit.ONE);\r
+ aI.feedSignals(Bit.ONE);\r
+\r
+ Simulation.TIMELINE.executeAll();\r
+\r
+ assertEquals(Bit.ONE, b.getValue());\r
+\r
+ bI.feedSignals(Bit.ZERO);\r
+\r
+ Simulation.TIMELINE.executeAll();\r
+\r
+ assertEquals(Bit.X, b.getValue());\r
+ assertEquals(Bit.ONE, a.getValue());\r
+\r
+ aI.clearSignals();\r
+ enI.feedSignals(Bit.ZERO);\r
+\r
+ Simulation.TIMELINE.executeAll();\r
+\r
+ assertEquals(Bit.ZERO, a.getValue());\r
+\r
+ }\r
+\r
+ @Test\r
+ void muxTest() {\r
+ Simulation.TIMELINE.reset();\r
+ WireArray a = new WireArray(4, 3), b = new WireArray(4, 6), c = new WireArray(4, 4), select = new WireArray(2, 5),\r
+ out = new WireArray(4, 1);\r
+ WireArrayInput selectIn = select.createInput();\r
+\r
+ selectIn.feedSignals(Bit.ZERO, Bit.ZERO);\r
+ a.createInput().feedSignals(Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO);\r
+ c.createInput().feedSignals(Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE);\r
+\r
+ new Mux(1, out, select, a, b, c);\r
+ Simulation.TIMELINE.executeAll();\r
+\r
+ assertBitArrayEquals(out.getValues(), Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO);\r
+ selectIn.feedSignals(Bit.ZERO, Bit.ONE);\r
+ Simulation.TIMELINE.executeAll();\r
+\r
+ assertBitArrayEquals(out.getValues(), Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE);\r
+\r
+ selectIn.feedSignals(Bit.ONE, Bit.ONE);\r
+ Simulation.TIMELINE.executeAll();\r
+\r
+ assertBitArrayEquals(out.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
+\r
+ }\r
+\r
+ @Test\r
+ void demuxTest() {\r
+ Simulation.TIMELINE.reset();\r
+ WireArray a = new WireArray(4, 3), b = new WireArray(4, 6), c = new WireArray(4, 4), select = new WireArray(2, 5),\r
+ in = new WireArray(4, 1);\r
+ WireArrayInput selectIn = select.createInput();\r
+\r
+ selectIn.feedSignals(Bit.ZERO, Bit.ZERO);\r
+ in.createInput().feedSignals(Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO);\r
+\r
+ new Demux(1, in, select, a, b, c);\r
+ Simulation.TIMELINE.executeAll();\r
+\r
+ assertBitArrayEquals(a.getValues(), Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO);\r
+ assertBitArrayEquals(b.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
+ assertBitArrayEquals(c.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
+ selectIn.feedSignals(Bit.ZERO, Bit.ONE);\r
+ Simulation.TIMELINE.executeAll();\r
\r
- Simulation.TIMELINE.executeAll();\r
+ assertBitArrayEquals(a.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
+ assertBitArrayEquals(b.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
+ assertBitArrayEquals(c.getValues(), Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO);\r
\r
- assertBitArrayEquals(a.getValues(), Bit.ZERO, Bit.ONE, Bit.ZERO);\r
- assertBitArrayEquals(b.getValues(), Bit.ONE, Bit.ZERO);\r
- assertBitArrayEquals(c.getValues(), Bit.ONE, Bit.ZERO, Bit.ONE);\r
- }\r
+ selectIn.feedSignals(Bit.ONE, Bit.ONE);\r
+ Simulation.TIMELINE.executeAll();\r
+\r
+ assertBitArrayEquals(a.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
+ assertBitArrayEquals(b.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
+ assertBitArrayEquals(c.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
+\r
+ }\r
+\r
+ @Test\r
+ void andTest() {\r
+ Simulation.TIMELINE.reset();\r
+ WireArray a = new WireArray(4, 1), b = new WireArray(4, 3), c = new WireArray(4, 1);\r
+ new AndGate(1, c, a, b);\r
+ a.createInput().feedSignals(Bit.ONE, Bit.ONE, Bit.ZERO, Bit.ZERO);\r
+ b.createInput().feedSignals(Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE);\r
+\r
+ Simulation.TIMELINE.executeAll();\r
+\r
+ assertBitArrayEquals(c.getValues(), Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ZERO);\r
+ }\r
+\r
+ @Test\r
+ void orTest() {\r
+ Simulation.TIMELINE.reset();\r
+ WireArray a = new WireArray(4, 1), b = new WireArray(4, 3), c = new WireArray(4, 1);\r
+ new OrGate(1, c, a, b);\r
+ a.createInput().feedSignals(Bit.ONE, Bit.ONE, Bit.ZERO, Bit.ZERO);\r
+ b.createInput().feedSignals(Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE);\r
+\r
+ Simulation.TIMELINE.executeAll();\r
+\r
+ assertBitArrayEquals(c.getValues(), Bit.ONE, Bit.ONE, Bit.ZERO, Bit.ONE);\r
+ }\r
\r
- @Test\r
- void mergerTest()\r
- {\r
- Simulation.TIMELINE.reset();\r
- WireArray a = new WireArray(3, 1), b = new WireArray(2, 1), c = new WireArray(3, 1), out = new WireArray(8, 1);\r
- a.createInput().feedSignals(Bit.ZERO, Bit.ONE, Bit.ZERO);\r
- b.createInput().feedSignals(Bit.ONE, Bit.ZERO);\r
- c.createInput().feedSignals(Bit.ONE, Bit.ZERO, Bit.ONE);\r
+ @Test\r
+ void xorTest() {\r
+ Simulation.TIMELINE.reset();\r
+ WireArray a = new WireArray(3, 1), b = new WireArray(3, 2), c = new WireArray(3, 1), d = new WireArray(3, 1);\r
+ new XorGate(1, d, a, b, c);\r
+ a.createInput().feedSignals(Bit.ZERO, Bit.ONE, Bit.ONE);\r
+ b.createInput().feedSignals(Bit.ONE, Bit.ZERO, Bit.ONE);\r
+ c.createInput().feedSignals(Bit.ONE, Bit.ZERO, Bit.ONE);\r
\r
- new Merger(out, a, b, c);\r
+ Simulation.TIMELINE.executeAll();\r
\r
- Simulation.TIMELINE.executeAll();\r
+ assertBitArrayEquals(d.getValues(), Bit.ZERO, Bit.ONE, Bit.ONE);\r
+ }\r
\r
- assertTrue(Arrays.equals(out.getValues(),\r
- new Bit[] { Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE }));\r
- }\r
+ @Test\r
+ void rsLatchCircuitTest() {\r
+ Simulation.TIMELINE.reset();\r
+ WireArray r = new WireArray(1, 1), s = new WireArray(1, 1), t1 = new WireArray(1, 15), t2 = new WireArray(1, 1),\r
+ q = new WireArray(1, 1), nq = new WireArray(1, 1);\r
\r
- @Test\r
- void triStateBufferTest()\r
- {\r
- WireArray a = new WireArray(1, 1), b = new WireArray(1, 1), en = new WireArray(1, 1),\r
- notEn = new WireArray(1, 1);\r
- new NotGate(1, en, notEn);\r
- new TriStateBuffer(1, a, b, en);\r
- new TriStateBuffer(1, b, a, notEn);\r
+ new OrGate(1, t2, r, nq);\r
+ new OrGate(1, t1, s, q);\r
+ new NotGate(1, t2, q);\r
+ new NotGate(1, t1, nq);\r
\r
- WireArrayInput enI = en.createInput(), aI = a.createInput(), bI = b.createInput();\r
- enI.feedSignals(Bit.ONE);\r
- aI.feedSignals(Bit.ONE);\r
+ WireArrayInput sIn = s.createInput(), rIn = r.createInput();\r
\r
- Simulation.TIMELINE.executeAll();\r
-\r
- assertEquals(Bit.ONE, b.getValue());\r
+ sIn.feedSignals(Bit.ONE);\r
+ rIn.feedSignals(Bit.ZERO);\r
\r
- bI.feedSignals(Bit.ZERO);\r
+ Simulation.TIMELINE.executeAll();\r
\r
- Simulation.TIMELINE.executeAll();\r
+ assertEquals(Bit.ONE, q.getValue());\r
+ assertEquals(Bit.ZERO, nq.getValue());\r
\r
- assertEquals(Bit.X, b.getValue());\r
- assertEquals(Bit.ONE, a.getValue());\r
-\r
- aI.clearSignals();\r
- enI.feedSignals(Bit.ZERO);\r
-\r
- Simulation.TIMELINE.executeAll();\r
-\r
- assertEquals(Bit.ZERO, a.getValue());\r
-\r
- }\r
-\r
- @Test\r
- void muxTest()\r
- {\r
- Simulation.TIMELINE.reset();\r
- WireArray a = new WireArray(4, 3), b = new WireArray(4, 6), c = new WireArray(4, 4),\r
- select = new WireArray(2, 5), out = new WireArray(4, 1);\r
- WireArrayInput selectIn = select.createInput();\r
-\r
- selectIn.feedSignals(Bit.ZERO, Bit.ZERO);\r
- a.createInput().feedSignals(Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO);\r
- c.createInput().feedSignals(Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE);\r
-\r
- new Mux(1, out, select, a, b, c);\r
- Simulation.TIMELINE.executeAll();\r
-\r
- assertBitArrayEquals(out.getValues(), Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO);\r
- selectIn.feedSignals(Bit.ZERO, Bit.ONE);\r
- Simulation.TIMELINE.executeAll();\r
-\r
- assertBitArrayEquals(out.getValues(), Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE);\r
-\r
- selectIn.feedSignals(Bit.ONE, Bit.ONE);\r
- Simulation.TIMELINE.executeAll();\r
-\r
- assertBitArrayEquals(out.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
-\r
- }\r
+ sIn.feedSignals(Bit.ZERO);\r
\r
- @Test\r
- void demuxTest()\r
- {\r
- Simulation.TIMELINE.reset();\r
- WireArray a = new WireArray(4, 3), b = new WireArray(4, 6), c = new WireArray(4, 4),\r
- select = new WireArray(2, 5), in = new WireArray(4, 1);\r
- WireArrayInput selectIn = select.createInput();\r
+ Simulation.TIMELINE.executeAll();\r
+ assertEquals(Bit.ONE, q.getValue());\r
+ assertEquals(Bit.ZERO, nq.getValue());\r
\r
- selectIn.feedSignals(Bit.ZERO, Bit.ZERO);\r
- in.createInput().feedSignals(Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO);\r
+ rIn.feedSignals(Bit.ONE);\r
\r
- new Demux(1, in, select, a, b, c);\r
- Simulation.TIMELINE.executeAll();\r
+ Simulation.TIMELINE.executeAll();\r
\r
- assertBitArrayEquals(a.getValues(), Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO);\r
- assertBitArrayEquals(b.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
- assertBitArrayEquals(c.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
- selectIn.feedSignals(Bit.ZERO, Bit.ONE);\r
- Simulation.TIMELINE.executeAll();\r
+ assertEquals(Bit.ZERO, q.getValue());\r
+ assertEquals(Bit.ONE, nq.getValue());\r
+ }\r
\r
- assertBitArrayEquals(a.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
- assertBitArrayEquals(b.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
- assertBitArrayEquals(c.getValues(), Bit.ONE, Bit.ZERO, Bit.ONE, Bit.ZERO);\r
+ @Test\r
+ void numericValueTest() {\r
+ Simulation.TIMELINE.reset();\r
\r
- selectIn.feedSignals(Bit.ONE, Bit.ONE);\r
- Simulation.TIMELINE.executeAll();\r
+ WireArray a = new WireArray(4, 1);\r
+ a.createInput().feedSignals(Bit.ONE, Bit.ONE, Bit.ONE, Bit.ONE);\r
\r
- assertBitArrayEquals(a.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
- assertBitArrayEquals(b.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
- assertBitArrayEquals(c.getValues(), Bit.Z, Bit.Z, Bit.Z, Bit.Z);\r
+ Simulation.TIMELINE.executeAll();\r
\r
- }\r
- \r
- @Test\r
- void andTest()\r
- {\r
- Simulation.TIMELINE.reset();\r
- WireArray a = new WireArray(4, 1), b = new WireArray(4, 3), c = new WireArray(4, 1);\r
- new AndGate(1, c, a, b);\r
- a.createInput().feedSignals(Bit.ONE, Bit.ONE, Bit.ZERO, Bit.ZERO);\r
- b.createInput().feedSignals(Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE);\r
+ assertEquals(15, a.getUnsignedValue());\r
+ assertEquals(-1, a.getSignedValue());\r
+ }\r
\r
- Simulation.TIMELINE.executeAll();\r
- \r
- assertBitArrayEquals(c.getValues(), Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ZERO);\r
- }\r
+ @Test\r
+ void multipleInputs() {\r
+ Simulation.TIMELINE.reset();\r
+ WireArray w = new WireArray(2, 1);\r
+ WireArrayInput wI1 = w.createInput(), wI2 = w.createInput();\r
+ wI1.feedSignals(Bit.ONE, Bit.Z);\r
+ wI2.feedSignals(Bit.Z, Bit.X);\r
+ Simulation.TIMELINE.executeAll();\r
+ assertBitArrayEquals(w.getValues(), Bit.ONE, Bit.X);\r
\r
- @Test\r
- void orTest()\r
- {\r
- Simulation.TIMELINE.reset();\r
- WireArray a = new WireArray(4, 1), b = new WireArray(4, 3), c = new WireArray(4, 1);\r
- new OrGate(1, c, a, b);\r
- a.createInput().feedSignals(Bit.ONE, Bit.ONE, Bit.ZERO, Bit.ZERO);\r
- b.createInput().feedSignals(Bit.ZERO, Bit.ONE, Bit.ZERO, Bit.ONE);\r
+ wI2.feedSignals(Bit.ZERO, Bit.Z);\r
+ Simulation.TIMELINE.executeAll();\r
+ assertBitArrayEquals(w.getValues(), Bit.X, Bit.Z);\r
\r
- Simulation.TIMELINE.executeAll();\r
+ wI2.feedSignals(Bit.Z, Bit.Z);\r
+ Simulation.TIMELINE.executeAll();\r
+ assertBitArrayEquals(w.getValues(), Bit.ONE, Bit.Z);\r
\r
- assertBitArrayEquals(c.getValues(), Bit.ONE, Bit.ONE, Bit.ZERO, Bit.ONE);\r
- }\r
- \r
- @Test\r
- void xorTest()\r
- {\r
- Simulation.TIMELINE.reset();\r
- WireArray a = new WireArray(3, 1), b = new WireArray(3, 2), c = new WireArray(3, 1), d = new WireArray(3, 1);\r
- new XorGate(1, d, a, b, c);\r
- a.createInput().feedSignals(Bit.ZERO, Bit.ONE, Bit.ONE);\r
- b.createInput().feedSignals(Bit.ONE, Bit.ZERO, Bit.ONE);\r
- c.createInput().feedSignals(Bit.ONE, Bit.ZERO, Bit.ONE);\r
-\r
- Simulation.TIMELINE.executeAll();\r
-\r
- assertBitArrayEquals(d.getValues(), Bit.ZERO, Bit.ONE, Bit.ONE);\r
- }\r
-\r
- @Test\r
- void rsLatchCircuitTest()\r
- {\r
- Simulation.TIMELINE.reset();\r
- WireArray r = new WireArray(1, 1), s = new WireArray(1, 1), t1 = new WireArray(1, 15), t2 = new WireArray(1, 1),\r
- q = new WireArray(1, 1), nq = new WireArray(1, 1);\r
-\r
- new OrGate(1, t2, r, nq);\r
- new OrGate(1, t1, s, q);\r
- new NotGate(1, t2, q);\r
- new NotGate(1, t1, nq);\r
-\r
- WireArrayInput sIn = s.createInput(), rIn = r.createInput();\r
-\r
- sIn.feedSignals(Bit.ONE);\r
- rIn.feedSignals(Bit.ZERO);\r
-\r
- Simulation.TIMELINE.executeAll();\r
-\r
- assertEquals(Bit.ONE, q.getValue());\r
- assertEquals(Bit.ZERO, nq.getValue());\r
-\r
- sIn.feedSignals(Bit.ZERO);\r
-\r
- Simulation.TIMELINE.executeAll();\r
- assertEquals(Bit.ONE, q.getValue());\r
- assertEquals(Bit.ZERO, nq.getValue());\r
-\r
- rIn.feedSignals(Bit.ONE);\r
-\r
- Simulation.TIMELINE.executeAll();\r
-\r
- assertEquals(Bit.ZERO, q.getValue());\r
- assertEquals(Bit.ONE, nq.getValue());\r
- }\r
-\r
- @Test\r
- void numericValueTest()\r
- {\r
- Simulation.TIMELINE.reset();\r
-\r
- WireArray a = new WireArray(4, 1);\r
- a.createInput().feedSignals(Bit.ONE, Bit.ONE, Bit.ONE, Bit.ONE);\r
-\r
- Simulation.TIMELINE.executeAll();\r
-\r
- assertEquals(15, a.getUnsignedValue());\r
- assertEquals(-1, a.getSignedValue());\r
- }\r
-\r
- @Test\r
- void multipleInputs()\r
- {\r
- Simulation.TIMELINE.reset();\r
- WireArray w = new WireArray(2, 1);\r
- WireArrayInput wI1 = w.createInput(), wI2 = w.createInput();\r
- wI1.feedSignals(Bit.ONE, Bit.Z);\r
- wI2.feedSignals(Bit.Z, Bit.X);\r
- Simulation.TIMELINE.executeAll();\r
- assertBitArrayEquals(w.getValues(), Bit.ONE, Bit.X);\r
-\r
- wI2.feedSignals(Bit.ZERO, Bit.Z);\r
- Simulation.TIMELINE.executeAll();\r
- assertBitArrayEquals(w.getValues(), Bit.X, Bit.Z);\r
-\r
- wI2.feedSignals(Bit.Z, Bit.Z);\r
- Simulation.TIMELINE.executeAll();\r
- assertBitArrayEquals(w.getValues(), Bit.ONE, Bit.Z);\r
-\r
- wI2.feedSignals(Bit.ONE, Bit.Z);\r
- w.addObserver((i, oldValues) -> fail("WireArray notified observer, although value did not change."));\r
- Simulation.TIMELINE.executeAll();\r
- assertBitArrayEquals(w.getValues(), Bit.ONE, Bit.Z);\r
- }\r
+ wI2.feedSignals(Bit.ONE, Bit.Z);\r
+ w.addObserver((i, oldValues) -> fail("WireArray notified observer, although value did not change."));\r
+ Simulation.TIMELINE.executeAll();\r
+ assertBitArrayEquals(w.getValues(), Bit.ONE, Bit.Z);\r
+ }\r
\r
@Test\r
- void wireConnections()\r
- {\r
+ void wireConnections() {\r
// Nur ein Experiment, was über mehrere 'passive' Bausteine hinweg passieren würde\r
- \r
+\r
Simulation.TIMELINE.reset();\r
\r
WireArray a = new WireArray(1, 2);\r
System.err.println("Z");\r
bI.feedSignals(Bit.Z);\r
test.assertAfterSimulationIs(print, Bit.Z);\r
- \r
+\r
new Connector(a, b);\r
System.err.println("Z 2");\r
aI.feedSignals(Bit.Z);\r
aI.feedSignals(Bit.Z);\r
test.assertAfterSimulationIs(print, Bit.Z);\r
test2.assertAfterSimulationIs(Bit.Z);\r
- \r
+\r
System.err.println("No Conflict yet");\r
bI.feedSignals(Bit.ONE);\r
test.assertAfterSimulationIs(print, Bit.ONE);\r
test2.assertAfterSimulationIs(Bit.ONE);\r
}\r
\r
- private static void assertBitArrayEquals(Bit[] actual, Bit... expected)\r
- {\r
- assertArrayEquals(expected, actual);\r
- }\r
+ private static void assertBitArrayEquals(Bit[] actual, Bit... expected) {\r
+ assertArrayEquals(expected, actual);\r
+ }\r
}\r
import era.mi.logic.wires.WireArray.WireArrayInput;\r
import era.mi.logic.wires.WireArrayObserver;\r
\r
-public class Connector implements WireArrayObserver\r
-{\r
+public class Connector implements WireArrayObserver {\r
private final WireArray a;\r
// private final WireArray b;\r
private final WireArrayInput aI;\r
private final WireArrayInput bI;\r
\r
- public Connector(WireArray a, WireArray b)\r
- {\r
+ public Connector(WireArray a, WireArray b) {\r
if (a.length != b.length)\r
throw new IllegalArgumentException(String.format("WireArray width does not match: %d, %d", a.length, b.length));\r
this.a = a;\r
}\r
\r
@Override\r
- public void update(WireArray initiator, Bit[] oldValues)\r
- {\r
- Simulation.TIMELINE.addEvent((e) ->\r
- {\r
+ public void update(WireArray initiator, Bit[] oldValues) {\r
+ Simulation.TIMELINE.addEvent((e) -> {\r
if (initiator == a)\r
bI.feedSignals(aI.wireValuesExcludingMe());\r
else\r
\r
}\r
\r
- private void drawSwitch(Graphics g, ManualSwitch ms, String text, double posX1, double posY1, double posX2,\r
- double posY2) {\r
+ private void drawSwitch(Graphics g, ManualSwitch ms, String text, double posX1, double posY1, double posX2, double posY2) {\r
int x1 = gX(posX1) - 5;\r
int x2 = gX(posX2) + 5;\r
int y1 = gY(posY1) - 5;\r
import era.mi.logic.components.BitDisplay;\r
import era.mi.logic.wires.WireArray;\r
\r
-public final class TestBitDisplay extends BitDisplay\r
-{\r
+public final class TestBitDisplay extends BitDisplay {\r
\r
- public TestBitDisplay(WireArray in)\r
- {\r
+ public TestBitDisplay(WireArray in) {\r
super(in);\r
}\r
\r
- public void assertDisplays(Bit... expected)\r
- {\r
+ public void assertDisplays(Bit... expected) {\r
assertArrayEquals(expected, getDisplayedValue());\r
}\r
\r
- public void assertAfterSimulationIs(Bit... expected)\r
- {\r
+ public void assertAfterSimulationIs(Bit... expected) {\r
Simulation.TIMELINE.executeAll();\r
assertDisplays(expected);\r
}\r
\r
- public void assertAfterSimulationIs(LongConsumer r, Bit... expected)\r
- {\r
- while (Simulation.TIMELINE.hasNext())\r
- {\r
- Simulation.TIMELINE.executeNext();\r
- r.accept(Simulation.TIMELINE.getSimulationTime());\r
- }\r
+ public void assertAfterSimulationIs(LongConsumer r, Bit... expected) {\r
+ while (Simulation.TIMELINE.hasNext()) {\r
+ Simulation.TIMELINE.executeNext();\r
+ r.accept(Simulation.TIMELINE.getSimulationTime());\r
+ }\r
assertDisplays(expected);\r
}\r
\r
@Override\r
- protected void compute()\r
- {\r
+ protected void compute() {\r
super.compute();\r
System.out.println("update: value is " + Arrays.toString(getDisplayedValue()));\r
}\r
\r
/**\r
* Orders Events by the time they are due to be executed. Can execute Events individually.\r
+ * \r
* @author Fabian Stemmler\r
*\r
*/\r
-public class Timeline\r
-{\r
+public class Timeline {\r
private PriorityQueue<InnerEvent> events;\r
private long currentTime = 0;\r
- \r
+\r
private final List<Consumer<TimelineEvent>> eventAddedListener;\r
- \r
- public Timeline(int initCapacity)\r
- {\r
+\r
+ public Timeline(int initCapacity) {\r
events = new PriorityQueue<InnerEvent>(initCapacity, (a, b) -> {\r
long difference = a.getTiming() - b.getTiming();\r
- if(difference == 0)\r
+ if (difference == 0)\r
return 0;\r
return difference < 0 ? -1 : 1;\r
});\r
- \r
+\r
eventAddedListener = new ArrayList<>();\r
}\r
- \r
- public boolean hasNext()\r
- {\r
+\r
+ public boolean hasNext() {\r
return !events.isEmpty();\r
}\r
\r
- public void executeNext()\r
- {\r
+ public void executeNext() {\r
InnerEvent first = events.poll();\r
currentTime = first.getTiming();\r
first.run();\r
}\r
- \r
- public void executeAll()\r
- {\r
+\r
+ public void executeAll() {\r
while (hasNext())\r
executeNext();\r
}\r
- \r
+\r
/**\r
- * Executes all events up to a given simulation timestamp. The simulation\r
- * process can be constrained by a real world timestamp.\r
+ * Executes all events up to a given simulation timestamp. The simulation process can be constrained by a real world timestamp.\r
* \r
- * @param timestamp the simulation timestamp up to which the events will be\r
- * processed\r
- * @param stopMillis the System.currentTimeMillis() when simulation definitely\r
- * needs to stop.\r
+ * @param timestamp the simulation timestamp up to which the events will be processed\r
+ * @param stopMillis the System.currentTimeMillis() when simulation definitely needs to stop.\r
* @return if it was possible to fulfil the goal in the given real world time.\r
* @author Christian Femers\r
*/\r
- public ExecutionResult executeUpTo(long timestamp, long stopMillis)\r
- {\r
- if (events.isEmpty())\r
- {\r
+ public ExecutionResult executeUpTo(long timestamp, long stopMillis) {\r
+ if (events.isEmpty()) {\r
currentTime = timestamp;\r
return ExecutionResult.NOTHING_DONE;\r
}\r
int checkStop = 0;\r
InnerEvent first = events.peek();\r
- while (first != null && first.getTiming() <= timestamp)\r
- {\r
+ while (first != null && first.getTiming() <= timestamp) {\r
events.remove();\r
currentTime = first.getTiming();\r
first.run();\r
return ExecutionResult.DONE_IN_TIME;\r
}\r
\r
- public long getSimulationTime()\r
- {\r
+ public long getSimulationTime() {\r
return currentTime;\r
}\r
\r
- public long nextEventTime()\r
- {\r
- if(!hasNext())\r
+ public long nextEventTime() {\r
+ if (!hasNext())\r
return -1;\r
else\r
return events.peek().timing;\r
}\r
- \r
- public void reset()\r
- {\r
+\r
+ public void reset() {\r
events.clear();\r
currentTime = 0;\r
}\r
\r
- public void addEventAddedListener(Consumer<TimelineEvent> listener)\r
- {\r
+ public void addEventAddedListener(Consumer<TimelineEvent> listener) {\r
eventAddedListener.add(listener);\r
}\r
- public void removeEventAddedListener(Consumer<TimelineEvent> listener)\r
- {\r
+\r
+ public void removeEventAddedListener(Consumer<TimelineEvent> listener) {\r
eventAddedListener.remove(listener);\r
}\r
- \r
+\r
/**\r
* Adds an Event to the {@link Timeline}\r
- * @param function The {@link TimelineEventHandler} that will be executed, when the {@link InnerEvent} occurs on the timeline.\r
+ * \r
+ * @param function The {@link TimelineEventHandler} that will be executed, when the {@link InnerEvent} occurs on the timeline.\r
* @param relativeTiming The amount of MI ticks in which the {@link InnerEvent} is called, starting from the current time.\r
*/\r
- public void addEvent(TimelineEventHandler function, int relativeTiming)\r
- {\r
+ public void addEvent(TimelineEventHandler function, int relativeTiming) {\r
long timing = currentTime + relativeTiming;\r
TimelineEvent event = new TimelineEvent(timing);\r
events.add(new InnerEvent(function, event, timing));\r
eventAddedListener.forEach(l -> l.accept(event));\r
}\r
- \r
- private class InnerEvent\r
- {\r
+\r
+ private class InnerEvent {\r
\r
private final long timing;\r
private final TimelineEventHandler function;\r
private final TimelineEvent event;\r
- \r
+\r
/**\r
* Creates an {@link InnerEvent}\r
+ * \r
* @param function {@link TimelineEventHandler} to be executed when the {@link InnerEvent} occurs\r
- * @param timing Point in the MI simulation {@link Timeline}, at which the {@link InnerEvent} is executed;\r
+ * @param timing Point in the MI simulation {@link Timeline}, at which the {@link InnerEvent} is executed;\r
*/\r
- InnerEvent(TimelineEventHandler function, TimelineEvent event, long timing)\r
- {\r
+ InnerEvent(TimelineEventHandler function, TimelineEvent event, long timing) {\r
this.function = function;\r
this.event = event;\r
this.timing = timing;\r
}\r
\r
- public long getTiming()\r
- {\r
+ public long getTiming() {\r
return timing;\r
}\r
- \r
- public void run()\r
- {\r
+\r
+ public void run() {\r
function.handle(event);\r
}\r
- \r
+\r
@Override\r
- public String toString()\r
- {\r
+ public String toString() {\r
return event.toString();\r
}\r
}\r
- \r
+\r
@Override\r
- public String toString()\r
- {\r
+ public String toString() {\r
return "simulation time: " + currentTime + ", " + events.toString();\r
}\r
- \r
- public static long toNanoseconds(long ticks)\r
- {\r
- return ticks; //TODO: Alter this when it has been determined how ticks should relate to real time.\r
+\r
+ public static long toNanoseconds(long ticks) {\r
+ return ticks; // TODO: Alter this when it has been determined how ticks should relate to real time.\r
}\r
- \r
- public enum ExecutionResult\r
- {\r
- NOTHING_DONE, DONE_IN_TIME, RAN_OUT_OF_TIME \r
+\r
+ public enum ExecutionResult {\r
+ NOTHING_DONE, DONE_IN_TIME, RAN_OUT_OF_TIME\r
}\r
}
\ No newline at end of file
package era.mi.logic.timeline;\r
\r
/**\r
- * A class that stores all relevant information about an event in the {@link Timeline}. Currently, there is not much relevant information to store.\r
+ * A class that stores all relevant information about an event in the {@link Timeline}. Currently, there is not much relevant information to\r
+ * store.\r
+ * \r
* @author Fabian Stemmler\r
*\r
*/\r
-public class TimelineEvent\r
-{\r
+public class TimelineEvent {\r
private final long timing;\r
- \r
- TimelineEvent(long timing)\r
- {\r
+\r
+ TimelineEvent(long timing) {\r
super();\r
this.timing = timing;\r
}\r
\r
- public long getTiming()\r
- {\r
+ public long getTiming() {\r
return timing;\r
}\r
- \r
- public String toString()\r
- {\r
+\r
+ public String toString() {\r
return "timestamp: " + timing;\r
}\r
}
\ No newline at end of file
-package era.mi.logic.timeline;
-
-public interface TimelineEventHandler
-{
- public void handle(TimelineEvent e);
+package era.mi.logic.timeline;\r
+\r
+public interface TimelineEventHandler {\r
+ public void handle(TimelineEvent e);\r
}
\ No newline at end of file
* @author Fabian Stemmler\r
*\r
*/\r
-public class WireArray\r
-{\r
+public class WireArray {\r
private Bit[] values;\r
public final int travelTime;\r
private List<WireArrayObserver> observers = new ArrayList<WireArrayObserver>();\r
public final int length;\r
private List<WireArrayInput> inputs = new ArrayList<WireArrayInput>();\r
\r
- public WireArray(int length, int travelTime)\r
- {\r
+ public WireArray(int length, int travelTime) {\r
if (length < 1)\r
- throw new IllegalArgumentException(String.format("Tried to create an array of wires with length %d, but a length of less than 1 makes no sense.", length));\r
+ throw new IllegalArgumentException(\r
+ String.format("Tried to create an array of wires with length %d, but a length of less than 1 makes no sense.", length));\r
this.length = length;\r
this.travelTime = travelTime;\r
initValues();\r
}\r
\r
- private void initValues()\r
- {\r
+ private void initValues() {\r
values = Bit.Z.makeArray(length);\r
}\r
\r
- private void recalculateSingleInput()\r
- {\r
+ private void recalculateSingleInput() {\r
WireArrayInput input = inputs.get(0);\r
- if (!Arrays.equals(input.getValues(), values))\r
- {\r
+ if (!Arrays.equals(input.getValues(), values)) {\r
Bit[] oldValues = values.clone();\r
System.arraycopy(input.getValues(), 0, values, 0, length);\r
notifyObservers(oldValues);\r
}\r
}\r
\r
- private void recalculateMultipleInputs()\r
- {\r
+ private void recalculateMultipleInputs() {\r
Iterator<WireArrayInput> it = inputs.iterator();\r
Bit[] newValues = it.next().inputValues.clone();\r
\r
- while (it.hasNext())\r
- {\r
+ while (it.hasNext()) {\r
WireArrayInput input = it.next();\r
Bit[] bits = input.getValues();\r
- for (int i = 0; i < length; i++)\r
- {\r
+ for (int i = 0; i < length; i++) {\r
if (Bit.Z.equals(bits[i]) || newValues[i].equals(bits[i]))\r
continue;\r
else if (Bit.Z.equals(newValues[i]))\r
}\r
}\r
\r
- if (!Arrays.equals(newValues, values))\r
- {\r
+ if (!Arrays.equals(newValues, values)) {\r
Bit[] oldValues = values;\r
values = newValues;\r
notifyObservers(oldValues);\r
}\r
}\r
\r
- private void recalculate()\r
- {\r
- switch (inputs.size())\r
- {\r
+ private void recalculate() {\r
+ switch (inputs.size()) {\r
case 0:\r
return;\r
case 1:\r
/**\r
* The WireArray is interpreted as an unsigned integer with n bits.\r
* \r
- * @return <code>true</code> if all bits are either <code>Bit.ONE</code> or\r
- * <code>Bit.ZERO</code> (they do not all have to have the same value),\r
- * not <code>Bit.X</code> or <code>Bit.Z</code>. <code>false</code> is\r
- * returned otherwise.\r
+ * @return <code>true</code> if all bits are either <code>Bit.ONE</code> or <code>Bit.ZERO</code> (they do not all have to have the same\r
+ * value), not <code>Bit.X</code> or <code>Bit.Z</code>. <code>false</code> is returned otherwise.\r
* \r
* @author Fabian Stemmler\r
*/\r
- public boolean hasNumericValue()\r
- {\r
- for (Bit b : values)\r
- {\r
+ public boolean hasNumericValue() {\r
+ for (Bit b : values) {\r
if (b != Bit.ZERO && b != Bit.ONE)\r
return false;\r
}\r
/**\r
* The WireArray is interpreted as an unsigned integer with n bits.\r
* \r
- * @return The unsigned value of the {@link WireArray}'s bits, where value 0\r
- * corresponds with 2^0, value 1 is 2^1 and so on.\r
+ * @return The unsigned value of the {@link WireArray}'s bits, where value 0 corresponds with 2^0, value 1 is 2^1 and so on.\r
* \r
* @author Fabian Stemmler\r
*/\r
- public long getUnsignedValue()\r
- {\r
+ public long getUnsignedValue() {\r
long val = 0;\r
long mask = 1;\r
- for (int i = 0; i < length; i++)\r
- {\r
- switch (values[i])\r
- {\r
+ for (int i = 0; i < length; i++) {\r
+ switch (values[i]) {\r
default:\r
case Z:\r
case X:\r
/**\r
* The WireArray is interpreted as a signed integer with n bits.\r
* \r
- * @return The signed value of the {@link WireArray}'s bits, where value 0\r
- * corresponds with 2^0, value 1 is 2^1 and so on.\r
+ * @return The signed value of the {@link WireArray}'s bits, where value 0 corresponds with 2^0, value 1 is 2^1 and so on.\r
* \r
* @author Fabian Stemmler\r
*/\r
- public long getSignedValue()\r
- {\r
+ public long getSignedValue() {\r
long val = getUnsignedValue();\r
long mask = 1 << (length - 1);\r
- if ((mask & val) != 0)\r
- {\r
+ if ((mask & val) != 0) {\r
int shifts = 64 - length;\r
return (val << shifts) >> shifts;\r
}\r
* \r
* @author Fabian Stemmler\r
*/\r
- public Bit getValue()\r
- {\r
+ public Bit getValue() {\r
return getValue(0);\r
}\r
\r
* \r
* @author Fabian Stemmler\r
*/\r
- public Bit getValue(int index)\r
- {\r
+ public Bit getValue(int index) {\r
return values[index];\r
}\r
\r
- public Bit[] getValues(int start, int end)\r
- {\r
+ public Bit[] getValues(int start, int end) {\r
int length = end - start;\r
Bit[] bits = new Bit[length];\r
System.arraycopy(values, start, bits, 0, length);\r
}\r
\r
/**\r
- * @return An array of length n containing the values of the n bits in the\r
- * {@link WireArray}. Can be safely modified.\r
+ * @return An array of length n containing the values of the n bits in the {@link WireArray}. Can be safely modified.\r
* \r
* @author Fabian Stemmler\r
*/\r
- public Bit[] getValues()\r
- {\r
+ public Bit[] getValues() {\r
return values.clone();\r
}\r
\r
/**\r
- * Adds an {@link WireArrayObserver}, who will be notified when the value of the\r
- * {@link WireArray} is updated.\r
+ * Adds an {@link WireArrayObserver}, who will be notified when the value of the {@link WireArray} is updated.\r
* \r
* @param ob The {@link WireArrayObserver} to be notified of changes.\r
- * @return true if the given {@link WireArrayObserver} was not already\r
- * registered, false otherwise\r
+ * @return true if the given {@link WireArrayObserver} was not already registered, false otherwise\r
* \r
* @author Fabian Stemmler\r
*/\r
- public boolean addObserver(WireArrayObserver ob)\r
- {\r
+ public boolean addObserver(WireArrayObserver ob) {\r
return observers.add(ob);\r
}\r
\r
- private void notifyObservers(Bit[] oldValues)\r
- {\r
+ private void notifyObservers(Bit[] oldValues) {\r
for (WireArrayObserver o : observers)\r
o.update(this, oldValues);\r
}\r
\r
/**\r
- * Create and register a {@link WireArrayInput} object, which is tied to this\r
- * {@link WireArray}.\r
+ * Create and register a {@link WireArrayInput} object, which is tied to this {@link WireArray}.\r
*/\r
- public WireArrayInput createInput()\r
- {\r
+ public WireArrayInput createInput() {\r
return new WireArrayInput(this);\r
}\r
\r
- private void registerInput(WireArrayInput toRegister)\r
- {\r
+ private void registerInput(WireArrayInput toRegister) {\r
inputs.add(toRegister);\r
}\r
\r
/**\r
- * A {@link WireArrayInput} feeds a constant signal into the {@link WireArray}\r
- * it is tied to. The combination of all inputs determines the\r
- * {@link WireArray}s final value. X dominates all other inputs Z does not\r
- * affect the final value, unless there are no other inputs than Z 0 and 1 turn\r
- * into X when they are mixed\r
+ * A {@link WireArrayInput} feeds a constant signal into the {@link WireArray} it is tied to. The combination of all inputs determines\r
+ * the {@link WireArray}s final value. X dominates all other inputs Z does not affect the final value, unless there are no other inputs\r
+ * than Z 0 and 1 turn into X when they are mixed\r
* \r
* @author Fabian Stemmler\r
*/\r
- public class WireArrayInput\r
- {\r
+ public class WireArrayInput {\r
public final WireArray owner;\r
private Bit[] inputValues;\r
\r
- private WireArrayInput(WireArray owner)\r
- {\r
+ private WireArrayInput(WireArray owner) {\r
super();\r
this.owner = owner;\r
initValues();\r
owner.registerInput(this);\r
}\r
\r
- private void initValues()\r
- {\r
+ private void initValues() {\r
inputValues = Bit.Z.makeArray(length);\r
}\r
\r
/**\r
- * Sets the wires values. This takes up time, as specified by the\r
- * {@link WireArray}s travel time.\r
+ * Sets the wires values. This takes up time, as specified by the {@link WireArray}s travel time.\r
* \r
* @param newValues The new values the wires should take on.\r
* \r
* @author Fabian Stemmler\r
*/\r
- public void feedSignals(Bit... newValues)\r
- {\r
- if (newValues.length == length)\r
- {\r
+ public void feedSignals(Bit... newValues) {\r
+ if (newValues.length == length) {\r
feedSignals(0, newValues);\r
} else\r
- throw new IllegalArgumentException(String.format("Attempted to input %o bits instead of %o bits.", newValues.length, length));\r
+ throw new IllegalArgumentException(\r
+ String.format("Attempted to input %o bits instead of %o bits.", newValues.length, length));\r
}\r
\r
/**\r
- * Sets values of a subarray of wires. This takes up time, as specified by the\r
- * {@link WireArray}s travel time.\r
+ * Sets values of a subarray of wires. This takes up time, as specified by the {@link WireArray}s travel time.\r
* \r
* @param newValues The new values the wires should take on.\r
* @param startingBit The first index of the subarray of wires.\r
* \r
* @author Fabian Stemmler\r
*/\r
- public void feedSignals(int startingBit, Bit... newValues)\r
- {\r
+ public void feedSignals(int startingBit, Bit... newValues) {\r
Simulation.TIMELINE.addEvent((e) -> setValues(startingBit, newValues), travelTime);\r
}\r
\r
- private void setValues(int startingBit, Bit... newValues)\r
- {\r
+ private void setValues(int startingBit, Bit... newValues) {\r
int exclLastIndex = startingBit + newValues.length;\r
if (length < exclLastIndex)\r
- throw new ArrayIndexOutOfBoundsException(String.format("Attempted to input bits from index %o to %o when there are only %o wires.", startingBit, exclLastIndex - 1, length));\r
- if (!Arrays.equals(inputValues, startingBit, exclLastIndex, newValues, 0, newValues.length))\r
- {\r
+ throw new ArrayIndexOutOfBoundsException(\r
+ String.format("Attempted to input bits from index %o to %o when there are only %o wires.", startingBit,\r
+ exclLastIndex - 1, length));\r
+ if (!Arrays.equals(inputValues, startingBit, exclLastIndex, newValues, 0, newValues.length)) {\r
System.arraycopy(newValues, 0, inputValues, startingBit, newValues.length);\r
owner.recalculate();\r
}\r
}\r
\r
/**\r
- * Returns a copy (safe to modify) of the values the {@link WireArrayInput} is currently feeding into the associated {@link WireArray}.\r
+ * Returns a copy (safe to modify) of the values the {@link WireArrayInput} is currently feeding into the associated\r
+ * {@link WireArray}.\r
*/\r
- public Bit[] getValues()\r
- {\r
+ public Bit[] getValues() {\r
return inputValues.clone();\r
}\r
\r
/**\r
* {@link WireArrayInput} now feeds Z into the associated {@link WireArray}.\r
*/\r
- public void clearSignals()\r
- {\r
+ public void clearSignals() {\r
feedSignals(Bit.Z.makeArray(length));\r
}\r
\r
- public Bit[] wireValuesExcludingMe() \r
- {\r
+ public Bit[] wireValuesExcludingMe() {\r
Bit[] bits = Bit.Z.makeArray(length);\r
- for (WireArrayInput wai : inputs) \r
- {\r
- if(wai == this)\r
+ for (WireArrayInput wai : inputs) {\r
+ if (wai == this)\r
continue;\r
Util.combineInto(bits, wai.getValues());\r
}\r
return bits;\r
}\r
- \r
+\r
@Override\r
- public String toString()\r
- {\r
+ public String toString() {\r
return Arrays.toString(inputValues);\r
}\r
}\r
\r
@Override\r
- public String toString()\r
- {\r
+ public String toString() {\r
return String.format("wire 0x%08x value: %s inputs: %s", hashCode(), Arrays.toString(values), inputs);\r
}\r
\r
- public static WireArrayInput[] extractInputs(WireArray[] w)\r
- {\r
+ public static WireArrayInput[] extractInputs(WireArray[] w) {\r
WireArrayInput[] inputs = new WireArrayInput[w.length];\r
for (int i = 0; i < w.length; i++)\r
inputs[i] = w[i].createInput();\r
-package era.mi.logic.wires;
-
-import era.mi.logic.Bit;
-
-public interface WireArrayObserver
-{
- public void update(WireArray initiator, Bit[] oldValues);
-}
+package era.mi.logic.wires;\r
+\r
+import era.mi.logic.Bit;\r
+\r
+public interface WireArrayObserver {\r
+ public void update(WireArray initiator, Bit[] oldValues);\r
+}\r