aboutsummaryrefslogtreecommitdiff
path: root/src/test
diff options
context:
space:
mode:
Diffstat (limited to 'src/test')
-rw-r--r--src/test/scala/firrtlTests/InferReadWriteSpec.scala51
-rw-r--r--src/test/scala/firrtlTests/InfoSpec.scala10
-rw-r--r--src/test/scala/firrtlTests/SeparateWriteClocksSpec.scala68
3 files changed, 124 insertions, 5 deletions
diff --git a/src/test/scala/firrtlTests/InferReadWriteSpec.scala b/src/test/scala/firrtlTests/InferReadWriteSpec.scala
index 1fb24297..62969df5 100644
--- a/src/test/scala/firrtlTests/InferReadWriteSpec.scala
+++ b/src/test/scala/firrtlTests/InferReadWriteSpec.scala
@@ -177,4 +177,55 @@ circuit sram6t :
// Check correctness of firrtl
res should containLine(s"mem.rw.wmode <= wen")
}
+
+ def sameAddr(ruw: String): String = {
+ s"""
+ |circuit sram6t :
+ | module sram6t :
+ | input clock : Clock
+ | output io : { flip addr : UInt<11>, flip valid : UInt<1>, flip write : UInt<1>, flip dataIn : UInt<32>, dataOut : UInt<32>}
+ |
+ | mem mem:
+ | data-type => UInt<4>
+ | depth => 64
+ | reader => r
+ | writer => w
+ | read-latency => 1
+ | write-latency => 1
+ | read-under-write => ${ruw}
+ |
+ | mem.r.clk <= clock
+ | mem.r.addr <= io.addr
+ | mem.r.en <= io.valid
+ | io.dataOut <= mem.r.data
+ |
+ | node wen = and(io.valid, io.write)
+ | mem.w.clk <= clock
+ | mem.w.addr <= io.addr
+ | mem.w.en <= wen
+ | mem.w.mask <= UInt(1)
+ | mem.w.data <= io.dataIn""".stripMargin
+ }
+
+ "Infer ReadWrite Ports" should "infer readwrite ports from shared addresses with undefined readUnderWrite" in {
+ val input = sameAddr("undefined")
+ val annos = Seq(memlib.InferReadWriteAnnotation)
+ val res = compileAndEmit(CircuitState(parse(input), HighForm, annos))
+ // Check correctness of firrtl
+ res should containLine(s"mem.rw.wmode <= wen")
+ }
+
+ Seq("old", "new").foreach { ruw =>
+ "Infer ReadWrite Ports" should s"not infer readwrite ports from shared addresses with '${ruw}' readUnderWrite" in {
+ val input = sameAddr(ruw)
+ val annos = Seq(memlib.InferReadWriteAnnotation)
+ intercept[Exception] {
+ compileAndEmit(CircuitState(parse(input), ChirrtlForm, annos))
+ } match {
+ case CustomTransformException(_: InferReadWriteCheckException) => // success
+ case _ => fail()
+ }
+ }
+ }
+
}
diff --git a/src/test/scala/firrtlTests/InfoSpec.scala b/src/test/scala/firrtlTests/InfoSpec.scala
index 43fb6ee1..db4828f6 100644
--- a/src/test/scala/firrtlTests/InfoSpec.scala
+++ b/src/test/scala/firrtlTests/InfoSpec.scala
@@ -91,11 +91,11 @@ class InfoSpec extends FirrtlFlatSpec with FirrtlMatchers {
result should containTree { case DefMemory(Info1, "m", _, _, _, _, _, _, _, _) => true }
result should containLine(s"reg [7:0] m [0:31]; //$Info1")
result should containLine(s"wire [7:0] m_r_data; //$Info1")
- result should containLine(s"wire [4:0] m_r_addr; //$Info1")
- result should containLine(s"wire [7:0] m_w_data; //$Info1")
- result should containLine(s"wire [4:0] m_w_addr; //$Info1")
- result should containLine(s"wire m_w_mask; //$Info1")
- result should containLine(s"wire m_w_en; //$Info1")
+ result should containLine(s"wire [4:0] m_r_addr = addr; //$Info1")
+ result should containLine(s"wire [7:0] m_w_data = 8'h0; //$Info1")
+ result should containLine(s"wire [4:0] m_w_addr = addr; //$Info1")
+ result should containLine(s"wire m_w_mask = 1'h0; //$Info1")
+ result should containLine(s"wire m_w_en = 1'h0; //$Info1")
result should containLine(s"assign m_r_data = m[m_r_addr]; //$Info1")
result should containLine(s"m[m_w_addr] <= m_w_data; //$Info1")
}
diff --git a/src/test/scala/firrtlTests/SeparateWriteClocksSpec.scala b/src/test/scala/firrtlTests/SeparateWriteClocksSpec.scala
new file mode 100644
index 00000000..476a3ae2
--- /dev/null
+++ b/src/test/scala/firrtlTests/SeparateWriteClocksSpec.scala
@@ -0,0 +1,68 @@
+// SPDX-License-Identifier: Apache-2.0
+
+package firrtlTests
+
+import firrtl._
+import firrtl.ir._
+import firrtl.passes.memlib.SeparateWriteClocks
+import firrtl.testutils._
+import firrtl.testutils.FirrtlCheckers._
+
+class SeparateWriteClocksSpec extends FirrtlFlatSpec {
+ def transform(input: String): CircuitState = {
+ val csx = (new SeparateWriteClocks).execute(CircuitState(parse(input), MidForm))
+ val emittedCirc = EmittedFirrtlCircuit("top", csx.circuit.serialize, ".fir")
+ csx.copy(annotations = Seq(EmittedFirrtlCircuitAnnotation(emittedCirc)))
+ }
+
+ behavior.of("SeparateWriteClocks")
+
+ it should "add intermediate wires to clocks of multi-write sync-read memories" in {
+ val result = transform(s"""
+ |circuit top:
+ | module top:
+ | input clk: Clock
+ | input raddr: UInt<10>
+ | output rdata: UInt<8>[4]
+ | input waddr_a: UInt<10>
+ | input we_a: UInt<1>
+ | input wdata_a: UInt<8>[4]
+ | input waddr_a: UInt<10>
+ | input we_a: UInt<1>
+ | input wdata_a: UInt<8>[4]
+ |
+ | mem m:
+ | data-type => UInt<8>
+ | depth => 1024
+ | reader => r
+ | writer => w_a
+ | writer => w_b
+ | read-latency => 1
+ | write-latency => 1
+ | read-under-write => undefined
+ |
+ | m.r.clk <= clk
+ | m.r.addr <= raddr
+ | m.r.en <= UInt(1)
+ | rdata <= m.r.data
+ |
+ | m.w_a.clk <= clk
+ | m.w_a.addr <= waddr_a
+ | m.w_a.en <= we_a
+ | m.w_a.mask <= UInt(1)
+ | m.w_a.data <= wdata_a
+ |
+ | m.w_b.clk <= clk
+ | m.w_b.addr <= waddr_b
+ | m.w_b.en <= we_b
+ | m.w_b.mask <= UInt(1)
+ | m.w_b.data <= wdata_b""".stripMargin)
+
+ println(result.circuit.serialize)
+ result should containLine("m.r.clk <= clk")
+ result should containLine("m.w_a.clk <= m_w_a_clk")
+ result should containLine("m.w_b.clk <= m_w_b_clk")
+ result shouldNot containLine("m.w_a.clk <= clk")
+ result shouldNot containLine("m.w_b.clk <= clk")
+ }
+}