From 1bb38863914a1c8b11f2a4587638d8f8603ae8f4 Mon Sep 17 00:00:00 2001 From: Albert Magyar Date: Mon, 13 Apr 2020 23:29:36 -0700 Subject: Avoid infinite loops on async-reset self-inits in CheckResets * Fixes #1516 * Tighten up logic for "casted literal" checking --- src/main/scala/firrtl/checks/CheckResets.scala | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) (limited to 'src/main') diff --git a/src/main/scala/firrtl/checks/CheckResets.scala b/src/main/scala/firrtl/checks/CheckResets.scala index facd5c01..4f7f7060 100644 --- a/src/main/scala/firrtl/checks/CheckResets.scala +++ b/src/main/scala/firrtl/checks/CheckResets.scala @@ -47,6 +47,7 @@ class CheckResets extends Transform with PreservesAll[Transform] { stmt match { case DefNode(_, name, expr) => drivers += we(WRef(name)) -> expr case Connect(_, lhs, rhs) => drivers += we(lhs) -> rhs + case reg @ DefRegister(_, name, _,_,_, init) if weq(WRef(name), init) => // Self-reset, allowed! case reg @ DefRegister(_,_,_,_, reset, init) if reset.tpe == AsyncResetType => regCheck += init -> reg case _ => // Do nothing @@ -54,14 +55,16 @@ class CheckResets extends Transform with PreservesAll[Transform] { stmt.foreach(onStmt(regCheck, drivers)) } + private def wireOrNode(kind: Kind) = (kind == WireKind || kind == NodeKind) + @tailrec private def findDriver(drivers: DirectDriverMap)(expr: Expression): Expression = expr match { - case lit: Literal => lit - case DoPrim(op, args, _,_) if isCast(op) => findDriver(drivers)(args.head) - case other => drivers.get(we(other)) match { - case Some(e) => findDriver(drivers)(e) - case None => other - } + case lit: Literal => lit + case DoPrim(op, args, _,_) if isCast(op) => findDriver(drivers)(args.head) + case other => drivers.get(we(other)) match { + case Some(e) if wireOrNode(Utils.kind(other)) => findDriver(drivers)(e) + case _ => other + } } private def onMod(errors: Errors)(mod: DefModule): Unit = { -- cgit v1.2.3