From c6c509d623e5e64e021fa311018b8ace2f3f8969 Mon Sep 17 00:00:00 2001 From: Albert Magyar Date: Wed, 7 Aug 2019 16:33:45 -0700 Subject: Check mems for legal latencies; ban zero write latency. (#1147) * Check mems for legal latencies; ban zero write latency. * Trigger --- spec/spec.pdf | Bin 269138 -> 269128 bytes spec/spec.tex | 2 +- src/main/scala/firrtl/passes/Checks.scala | 4 ++++ src/test/scala/firrtlTests/CheckSpec.scala | 19 +++++++++++++++++++ 4 files changed, 24 insertions(+), 1 deletion(-) diff --git a/spec/spec.pdf b/spec/spec.pdf index 42395661..9242011e 100644 Binary files a/spec/spec.pdf and b/spec/spec.pdf differ diff --git a/spec/spec.tex b/spec/spec.tex index fd1f045c..8685de45 100644 --- a/spec/spec.tex +++ b/spec/spec.tex @@ -756,7 +756,7 @@ A memory is an abstract representation of a hardware memory. It is characterized \item A positive integer representing the number of elements in the memory. \item A variable number of named ports, each being a read port, a write port, or readwrite port. \item A non-negative integer indicating the read latency, which is the number of cycles after setting the port's read address before the corresponding element's value can be read from the port's data field. -\item A non-negative integer indicating the write latency, which is the number of cycles after setting the port's write address and data before the corresponding element within the memory holds the new value. +\item A positive integer indicating the write latency, which is the number of cycles after setting the port's write address and data before the corresponding element within the memory holds the new value. \item A read-under-write flag indicating the behaviour when a memory location is written to while a read to that location is in progress. \end{enumerate} diff --git a/src/main/scala/firrtl/passes/Checks.scala b/src/main/scala/firrtl/passes/Checks.scala index 471fe216..4bcfad9c 100644 --- a/src/main/scala/firrtl/passes/Checks.scala +++ b/src/main/scala/firrtl/passes/Checks.scala @@ -27,6 +27,8 @@ trait CheckHighFormLike { s"$info: [module $mname] Memory $name has not been properly lowered from Chirrtl IR.") class MemWithFlipException(info: Info, mname: String, name: String) extends PassException( s"$info: [module $mname] Memory $name cannot be a bundle type with flips.") + class IllegalMemLatencyException(info: Info, mname: String, name: String) extends PassException( + s"$info: [module $mname] Memory $name must have non-negative read latency and positive write latency.") class RegWithFlipException(info: Info, mname: String, name: String) extends PassException( s"$info: [module $mname] Register $name cannot be a bundle type with flips.") class InvalidAccessException(info: Info, mname: String) extends PassException( @@ -191,6 +193,8 @@ trait CheckHighFormLike { if (reset.tpe == AsyncResetType && !init.isInstanceOf[Literal]) errors.append(new NonLiteralAsyncResetValueException(info, mname, name, init.serialize)) case sx: DefMemory => + if (sx.readLatency < 0 || sx.writeLatency <= 0) + errors.append(new IllegalMemLatencyException(info, mname, sx.name)) if (hasFlip(sx.dataType)) errors.append(new MemWithFlipException(info, mname, sx.name)) if (sx.depth <= 0) diff --git a/src/test/scala/firrtlTests/CheckSpec.scala b/src/test/scala/firrtlTests/CheckSpec.scala index 93bc2cab..54dc60ab 100644 --- a/src/test/scala/firrtlTests/CheckSpec.scala +++ b/src/test/scala/firrtlTests/CheckSpec.scala @@ -41,6 +41,25 @@ class CheckSpec extends FlatSpec with Matchers { } } + "Memories with zero write latency" should "throw an exception" in { + val passes = Seq( + ToWorkingIR, + CheckHighForm) + val input = + """circuit Unit : + | module Unit : + | mem m : + | data-type => UInt<32> + | depth => 32 + | read-latency => 0 + | write-latency => 0""".stripMargin + intercept[CheckHighForm.IllegalMemLatencyException] { + passes.foldLeft(Parser.parse(input.split("\n").toIterator)) { + (c: Circuit, p: Pass) => p.run(c) + } + } + } + "Registers with flip in the type" should "throw an exception" in { val input = """circuit Unit : -- cgit v1.2.3