diff --git a/src/main/scala/uncore/tilelink2/Parameters.scala b/src/main/scala/uncore/tilelink2/Parameters.scala index ca5fe0e7..997d1f5e 100644 --- a/src/main/scala/uncore/tilelink2/Parameters.scala +++ b/src/main/scala/uncore/tilelink2/Parameters.scala @@ -289,7 +289,10 @@ case class TLClientParameters( val name = nodePath.lastOption.map(_.lazyModule.name).getOrElse("disconnected") } -case class TLClientPortParameters(clients: Seq[TLClientParameters]) { +case class TLClientPortParameters( + clients: Seq[TLClientParameters], + unsafeAtomics: Boolean = false) // Atomics are executed as get+put +{ require (!clients.isEmpty) // Require disjoint ranges for Ids diff --git a/src/main/scala/uncore/tilelink2/Xbar.scala b/src/main/scala/uncore/tilelink2/Xbar.scala index 4a5bbf40..afd01add 100644 --- a/src/main/scala/uncore/tilelink2/Xbar.scala +++ b/src/main/scala/uncore/tilelink2/Xbar.scala @@ -45,24 +45,24 @@ class TLXbar(policy: (Vec[Bool], Bool) => Seq[Bool] = TLXbar.lowestIndex) extend numClientPorts = 1 to 32, numManagerPorts = 1 to 32, clientFn = { seq => - val clients = (mapInputIds(seq) zip seq) flatMap { case (range, port) => + // An unsafe atomic port can not be combined with any other! + require (!seq.exists(_.unsafeAtomics) || seq.size == 1) + seq(0).copy(clients = (mapInputIds(seq) zip seq) flatMap { case (range, port) => port.clients map { client => client.copy( sourceId = client.sourceId.shift(range.start) )} - } - TLClientPortParameters(clients) + }) }, managerFn = { seq => val fifoIdFactory = relabeler() - val managers = (mapOutputIds(seq) zip seq) flatMap { case (range, port) => + seq(0).copy(managers = (mapOutputIds(seq) zip seq) flatMap { case (range, port) => require (port.beatBytes == seq(0).beatBytes) val fifoIdMapper = fifoIdFactory() port.managers map { manager => manager.copy( sinkId = manager.sinkId.shift(range.start), fifoId = manager.fifoId.map(fifoIdMapper(_)) )} - } - TLManagerPortParameters(managers, seq(0).beatBytes) + }) }) lazy val module = new LazyModuleImp(this) {