diff --git a/src/main/dig/74xx/lib/7474.dig b/src/main/dig/74xx/lib/7474.dig index 183804de1..db5c225bd 100644 --- a/src/main/dig/74xx/lib/7474.dig +++ b/src/main/dig/74xx/lib/7474.dig @@ -16,26 +16,6 @@ - - NAnd - - - Inputs - 3 - - - - - - NAnd - - - Inputs - 3 - - - - Out @@ -48,7 +28,7 @@ 5 - + Out @@ -62,27 +42,7 @@ 6 - - - - NAnd - - - Inputs - 3 - - - - - - NAnd - - - Inputs - 3 - - - + In @@ -100,27 +60,7 @@ 1 - - - - NAnd - - - Inputs - 3 - - - - - - NAnd - - - Inputs - 3 - - - + In @@ -134,7 +74,7 @@ 2 - + In @@ -148,7 +88,7 @@ 3 - + In @@ -166,27 +106,7 @@ 1 - - - - NAnd - - - Inputs - 3 - - - - - - NAnd - - - Inputs - 3 - - - + Out @@ -200,7 +120,7 @@ 9 - + Out @@ -214,27 +134,7 @@ 8 - - - - NAnd - - - Inputs - 3 - - - - - - NAnd - - - Inputs - 3 - - - + In @@ -252,27 +152,7 @@ 1 - - - - NAnd - - - Inputs - 3 - - - - - - NAnd - - - Inputs - 3 - - - + In @@ -286,7 +166,7 @@ 12 - + In @@ -300,7 +180,7 @@ 11 - + In @@ -318,489 +198,103 @@ 1 - + + + + D_FF_AS + + + + + D_FF_AS + + + + + Not + + + + + Not + + + + + Not + + + + + Not + + - - + + - - + + - - + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + - - + + - - + + - - + + - - + + - - + + - - + + - - + + - - + + - - + + - - + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + \ No newline at end of file diff --git a/src/main/dig/74xx/lib/7476.dig b/src/main/dig/74xx/lib/7476.dig index b60f6dd30..467556888 100644 --- a/src/main/dig/74xx/lib/7476.dig +++ b/src/main/dig/74xx/lib/7476.dig @@ -10,62 +10,8 @@ Description DUAL J-K FLIP-FLOPS WITH PRESET AND CLEAR - - lockedMode - true - - - And - - - - - Not - - - - - And - - - Inputs - 3 - - - - - - And - - - Inputs - 3 - - - - - - NOr - - - Inputs - 3 - - - - - - NOr - - - Inputs - 3 - - - - In @@ -86,7 +32,7 @@ 1 - + Out @@ -100,7 +46,7 @@ 15 - + Out @@ -114,12 +60,7 @@ 14 - - - - Delay - - + In @@ -137,7 +78,7 @@ 1 - + In @@ -159,7 +100,7 @@ 1 - + In @@ -181,12 +122,12 @@ 1 - + Not - + In @@ -208,62 +149,12 @@ 1 - + Not - - - - And - - - - - Not - - - - - And - - - Inputs - 3 - - - - - - And - - - Inputs - 3 - - - - - - NOr - - - Inputs - 3 - - - - - - NOr - - - Inputs - 3 - - - + In @@ -285,7 +176,7 @@ 1 - + Out @@ -299,7 +190,7 @@ 11 - + Out @@ -313,12 +204,7 @@ 10 - - - - Delay - - + In @@ -336,7 +222,7 @@ 6 - + In @@ -358,7 +244,7 @@ 1 - + In @@ -380,12 +266,7 @@ 1 - - - - Not - - + In @@ -407,366 +288,165 @@ 1 - + + + + JK_FF_AS + + Not - + + + + Not + + + + + JK_FF_AS + + - - + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + - - + + - - + + - - + + - - + + - - + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + - - + + - - + + - - + + - - + + - - + + - - + + - - + + - - + + - - + + + + + + + + + + + + + + + + + + - + - - + + - - + + - - + + - - + + - - + + - - + + - - + + - - + + - - + + - - + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + \ No newline at end of file diff --git a/src/main/java/de/neemann/digital/core/flipflops/FlipflopDAsync.java b/src/main/java/de/neemann/digital/core/flipflops/FlipflopDAsync.java new file mode 100644 index 000000000..5d97c1b3e --- /dev/null +++ b/src/main/java/de/neemann/digital/core/flipflops/FlipflopDAsync.java @@ -0,0 +1,116 @@ +package de.neemann.digital.core.flipflops; + +import de.neemann.digital.core.*; +import de.neemann.digital.core.element.Element; +import de.neemann.digital.core.element.ElementAttributes; +import de.neemann.digital.core.element.ElementTypeDescription; +import de.neemann.digital.core.element.Keys; + +import static de.neemann.digital.core.ObservableValues.ovs; +import static de.neemann.digital.core.element.PinInfo.input; + +/** + * The D Flipflop + * + * @author hneemann + */ +public class FlipflopDAsync extends Node implements Element { + + /** + * The D-FF description + */ + public static final ElementTypeDescription DESCRIPTION + = new ElementTypeDescription("D_FF_AS", FlipflopDAsync.class, input("Set"), input("D"), input("C"), input("Clr")) + .addAttribute(Keys.ROTATE) + .addAttribute(Keys.BITS) + .addAttribute(Keys.LABEL) + .addAttribute(Keys.DEFAULT) + .addAttribute(Keys.VALUE_IS_PROBE); + + private final int bits; + private final boolean isProbe; + private final String label; + private ObservableValue setVal; + private ObservableValue clrVal; + private ObservableValue dVal; + private ObservableValue clockVal; + private ObservableValue q; + private ObservableValue qn; + private boolean lastClock; + private long value; + + /** + * Creates a new instance + * + * @param attributes the attributes + */ + public FlipflopDAsync(ElementAttributes attributes) { + this(attributes, + new ObservableValue("Q", attributes.getBits()).setPinDescription(DESCRIPTION), + new ObservableValue("\u00ACQ", attributes.getBits()).setPinDescription(DESCRIPTION)); + } + + /** + * Creates a new D-FF with the given outputs! + * + * @param label the label + * @param q output + * @param qn inverted output + */ + public FlipflopDAsync(String label, ObservableValue q, ObservableValue qn) { + this(new ElementAttributes().set(Keys.LABEL, label).setBits(q.getBits()), q, qn); + if (qn.getBits() != q.getBits()) + throw new RuntimeException("wrong bit count given!"); + } + + private FlipflopDAsync(ElementAttributes attributes, ObservableValue q, ObservableValue qn) { + super(true); + bits = attributes.getBits(); + this.q = q; + this.qn = qn; + isProbe = attributes.get(Keys.VALUE_IS_PROBE); + label = attributes.getCleanLabel(); + + value = attributes.get(Keys.DEFAULT); + q.setValue(value); + qn.setValue(~value); + } + + @Override + public void readInputs() throws NodeException { + boolean clock = clockVal.getBool(); + if (clock && !lastClock) + value = dVal.getValue(); + lastClock = clock; + + if (setVal.getBool()) value = -1; + else if (clrVal.getBool()) value = 0; + } + + @Override + public void writeOutputs() throws NodeException { + q.setValue(value); + qn.setValue(~value); + } + + @Override + public void setInputs(ObservableValues inputs) throws BitsException { + setVal = inputs.get(0).addObserverToValue(this).checkBits(1, this, 0); + dVal = inputs.get(1).addObserverToValue(this).checkBits(bits, this, 1); + clockVal = inputs.get(2).addObserverToValue(this).checkBits(1, this, 2); + clrVal = inputs.get(3).addObserverToValue(this).checkBits(1, this, 3); + } + + @Override + public ObservableValues getOutputs() { + return ovs(q, qn); + } + + @Override + public void registerNodes(Model model) { + super.registerNodes(model); + if (isProbe) + model.addSignal(new Signal(label, q)); + } + +} diff --git a/src/main/java/de/neemann/digital/core/flipflops/FlipflopJKAsync.java b/src/main/java/de/neemann/digital/core/flipflops/FlipflopJKAsync.java new file mode 100644 index 000000000..83c14b10b --- /dev/null +++ b/src/main/java/de/neemann/digital/core/flipflops/FlipflopJKAsync.java @@ -0,0 +1,108 @@ +package de.neemann.digital.core.flipflops; + +import de.neemann.digital.core.*; +import de.neemann.digital.core.element.Element; +import de.neemann.digital.core.element.ElementAttributes; +import de.neemann.digital.core.element.ElementTypeDescription; +import de.neemann.digital.core.element.Keys; + +import static de.neemann.digital.core.ObservableValues.ovs; +import static de.neemann.digital.core.element.PinInfo.input; + +/** + * The JK Flipflop + * + * @author hneemann + */ +public class FlipflopJKAsync extends Node implements Element { + + /** + * The JK-FF description + */ + public static final ElementTypeDescription DESCRIPTION + = new ElementTypeDescription("JK_FF_AS", FlipflopJKAsync.class, + input("Set"), + input("J"), + input("C"), + input("K"), + input("Clr")) + .addAttribute(Keys.ROTATE) + .addAttribute(Keys.LABEL) + .addAttribute(Keys.DEFAULT) + .addAttribute(Keys.VALUE_IS_PROBE); + + private final Boolean isProbe; + private final String label; + private ObservableValue setVal; + private ObservableValue clrVal; + private ObservableValue jVal; + private ObservableValue kVal; + private ObservableValue clockVal; + private ObservableValue q; + private ObservableValue qn; + private boolean lastClock; + private boolean out; + + /** + * Creates a new instance + * + * @param attributes the attributes + */ + public FlipflopJKAsync(ElementAttributes attributes) { + super(true); + this.q = new ObservableValue("Q", 1).setPinDescription(DESCRIPTION); + this.qn = new ObservableValue("\u00ACQ", 1).setPinDescription(DESCRIPTION); + isProbe = attributes.get(Keys.VALUE_IS_PROBE); + label = attributes.getCleanLabel(); + + int def = attributes.get(Keys.DEFAULT); + out = def > 0; + q.setBool(out); + qn.setBool(!out); + } + + @Override + public void readInputs() throws NodeException { + boolean clock = clockVal.getBool(); + if (clock && !lastClock) { + boolean j = jVal.getBool(); + boolean k = kVal.getBool(); + + if (j && k) out = !out; + else if (j) out = true; + else if (k) out = false; + } + lastClock = clock; + + if (setVal.getBool()) out = true; + else if (clrVal.getBool()) out = false; + } + + @Override + public void writeOutputs() throws NodeException { + q.setBool(out); + qn.setBool(!out); + } + + @Override + public void setInputs(ObservableValues inputs) throws BitsException { + setVal = inputs.get(0).addObserverToValue(this).checkBits(1, this, 0); + jVal = inputs.get(1).addObserverToValue(this).checkBits(1, this, 1); + clockVal = inputs.get(2).addObserverToValue(this).checkBits(1, this, 2); + kVal = inputs.get(3).addObserverToValue(this).checkBits(1, this, 3); + clrVal = inputs.get(4).addObserverToValue(this).checkBits(1, this, 4); + } + + @Override + public ObservableValues getOutputs() { + return ovs(q, qn); + } + + @Override + public void registerNodes(Model model) { + super.registerNodes(model); + if (isProbe) + model.addSignal(new Signal(label, q)); + } + +} diff --git a/src/main/java/de/neemann/digital/draw/library/ElementLibrary.java b/src/main/java/de/neemann/digital/draw/library/ElementLibrary.java index 069fc8d41..96b13c0ec 100644 --- a/src/main/java/de/neemann/digital/draw/library/ElementLibrary.java +++ b/src/main/java/de/neemann/digital/draw/library/ElementLibrary.java @@ -4,10 +4,7 @@ import de.neemann.digital.core.arithmetic.*; import de.neemann.digital.core.arithmetic.Comparator; import de.neemann.digital.core.basic.*; import de.neemann.digital.core.element.*; -import de.neemann.digital.core.flipflops.FlipflopD; -import de.neemann.digital.core.flipflops.FlipflopJK; -import de.neemann.digital.core.flipflops.FlipflopRS; -import de.neemann.digital.core.flipflops.FlipflopT; +import de.neemann.digital.core.flipflops.*; import de.neemann.digital.core.io.*; import de.neemann.digital.core.memory.*; import de.neemann.digital.core.pld.DiodeBackward; @@ -106,7 +103,9 @@ public class ElementLibrary implements Iterable .add(FlipflopRS.DESCRIPTION) .add(FlipflopJK.DESCRIPTION) .add(FlipflopD.DESCRIPTION) - .add(FlipflopT.DESCRIPTION)) + .add(FlipflopT.DESCRIPTION) + .add(FlipflopJKAsync.DESCRIPTION) + .add(FlipflopDAsync.DESCRIPTION)) .add(new LibraryNode(Lang.get("lib_memory")) .add(Register.DESCRIPTION) .add(ROM.DESCRIPTION) diff --git a/src/main/resources/lang/lang_de.xml b/src/main/resources/lang/lang_de.xml index 36968cd8d..256b00590 100644 --- a/src/main/resources/lang/lang_de.xml +++ b/src/main/resources/lang/lang_de.xml @@ -165,6 +165,31 @@ Es können sowohl komplette Takte als auch einzelne Gatter-Veränderungen angeze Der Rücksetzen-Eingang des Flipflops. Gibt den gespeicherten Wert aus. Gibt den gespeicherten Wert negiert aus. + + JK-FlipFlop, asynchron + JK-AS + Bietet die Funktionen zum + Speichern (J=K=0), Setzen (J=1, K=0), Rücksetzen (J=0, K=1) und Wechseln (J=K=1). + Übernommen werden die Eingänge bei einer steigenden Flanke am Eingang C. + Der Setzen-Eingang des Flipflops. + Takteingang Eine steigende Flanke initiiert den Zustandswechsel. + Der Rücksetzen-Eingang des Flipflops. + Gibt den gespeicherten Wert aus. + Gibt den gespeicherten Wert negiert aus. + asynchrones setzen + asynchrones löschen + + D-FlipFLop, asynchron + D-AS + Ein Baustein zum Speichern eines Bits. Der an Eingang D anliegende Wert wird abgespeichert wenn Eingang C auf 1 wechselt. + Das zu speichernde Bit. + Takt des Flipflops. Wechselt dieser Wert auf 1, wird der an D anliegende Wert abgespeichert. + Gibt den gespeicherten Wert zurück. + Gibt den gespeicherten Wert negiert zurück. + asynchrones setzen + asynchrones löschen + + LED Eine Leuchtdiode welche beispielsweise zur Visualisierung eines Ausgangswertes verwendet werden kann. Nimmt ein Bit entgegen. Leuchtet wenn der Eingang auf 1 gesetzt ist. LED Eingang. LED leuchtet wenn Eingang auf 1 gesetzt ist. diff --git a/src/main/resources/lang/lang_en.xml b/src/main/resources/lang/lang_en.xml index 3d87b6b58..eab375a34 100644 --- a/src/main/resources/lang/lang_en.xml +++ b/src/main/resources/lang/lang_en.xml @@ -114,6 +114,7 @@ Resets the counter value if set to 1. Returns the counted value. Overflow output. This pin is set to 1 if the counter has an overflow and returns to zero. + D-FlipFlop D A component used to save two states (one bit). The bit on pin D is stored on a rising edge of pin C. @@ -121,6 +122,17 @@ Control pin to store a bit. The bit on input D is stored on a rising edge of this pin. Returns the stored value. Returns the negated stored value. + + D-FlipFlop, asynchronous + D-AS + A component used to save two states (one bit). The bit on pin D is stored on a rising edge of pin C. + Input of the bit to be stored. + Control pin to store a bit. The bit on input D is stored on a rising edge of this pin. + Returns the stored value. + Returns the negated stored value. + asynchronous set + asynchronous clear + Data graph Shows a data plot inside of the circuit panel. You can plot complete clock steps or single gate changes. @@ -153,6 +165,7 @@ Input This connection outputs the given value. A input which can be used to connect the circuit if it is included in an other circuit. + JK-Flipflop JK Has the possibility to store (J=K=0), set (J=1, K=0), reset (J=0, K=1) or toggle (J=K=1) the stored value. The input values act with a rising edge at input C. @@ -161,6 +174,18 @@ The reset input of the flipflop. Returns the stored value. Returns the negated stored value. + + JK-Flipflop, asynchronous + JK-AS + Has the possibility to store (J=K=0), set (J=1, K=0), reset (J=0, K=1) or toggle (J=K=1) the stored value. The input values act with a rising edge at input C. + The set input of the flipflop. + The Clock input. A rising edge initiates a state change. + The reset input of the flipflop. + Returns the stored value. + Returns the negated stored value. + asynchronous set + asynchronous clear + LED A simple LED can be used to visualize an output value. Accepts a single bit. Lights up when the input is set to 1. LED Input. LED shines when input is set to 1. diff --git a/src/test/java/de/neemann/digital/integration/TestExamples.java b/src/test/java/de/neemann/digital/integration/TestExamples.java index 70cd7e995..5b86d499e 100644 --- a/src/test/java/de/neemann/digital/integration/TestExamples.java +++ b/src/test/java/de/neemann/digital/integration/TestExamples.java @@ -39,8 +39,8 @@ public class TestExamples extends TestCase { */ public void testTestExamples() throws Exception { File examples = new File(Resources.getRoot(), "/dig/test"); - assertEquals(60, new FileScanner(this::check).scan(examples)); - assertEquals(56, testCasesInFiles); + assertEquals(62, new FileScanner(this::check).scan(examples)); + assertEquals(58, testCasesInFiles); } diff --git a/src/test/resources/dig/test/async/d_async.dig b/src/test/resources/dig/test/async/d_async.dig new file mode 100644 index 000000000..cf7fe063e --- /dev/null +++ b/src/test/resources/dig/test/async/d_async.dig @@ -0,0 +1,144 @@ + + + 1 + + + + In + + + Label + CLK + + + + + + In + + + Label + D + + + + + + In + + + Label + S + + + + + + In + + + Label + C + + + + + + Out + + + Label + Q + + + + + + Out + + + Label + ~Q + + + + + + Testcase + + + Testdata + + CLK D S C Q ~Q + 0 0 0 0 0 1 + 0 1 0 0 0 1 + C 1 0 0 1 0 + 0 0 0 0 1 0 + C 0 0 0 0 1 + 0 0 0 1 0 1 + 0 0 0 0 0 1 + 0 0 1 0 1 0 + 0 0 0 0 1 0 + + + + + + + + D_FF_AS + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/test/resources/dig/test/async/jk_async.dig b/src/test/resources/dig/test/async/jk_async.dig new file mode 100644 index 000000000..9a0b80f23 --- /dev/null +++ b/src/test/resources/dig/test/async/jk_async.dig @@ -0,0 +1,171 @@ + + + 1 + + + + JK_FF_AS + + + + + In + + + Label + CLK + + + + + + In + + + Label + J + + + + + + In + + + Label + S + + + + + + In + + + Label + K + + + + + + In + + + Label + C + + + + + + Out + + + Label + Q + + + + + + Out + + + Label + ~Q + + + + + + Testcase + + + Testdata + + CLK J K S C Q ~Q + 0 0 0 0 0 0 1 + C 1 0 0 0 1 0 + 0 1 0 0 0 1 0 + 0 0 0 0 0 1 0 + 0 0 1 0 0 1 0 + C 0 1 0 0 0 1 + 0 0 0 0 0 0 1 + C 1 0 0 0 1 0 + 0 0 0 1 0 1 0 + 0 0 0 0 1 0 1 + C 1 1 0 0 1 0 + C 1 1 0 0 0 1 + C 1 1 0 0 1 0 + C 1 1 0 0 0 1 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file