tilelink2: track interrupt connectivity like in TL2
This commit is contained in:
		@@ -21,9 +21,19 @@ object IntRange
 | 
				
			|||||||
  implicit def apply(end: Int): IntRange = apply(0, end)
 | 
					  implicit def apply(end: Int): IntRange = apply(0, end)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
case class IntSourceParameters(device: String, range: IntRange)
 | 
					case class IntSourceParameters(
 | 
				
			||||||
 | 
					  range:    IntRange,
 | 
				
			||||||
 | 
					  nodePath: Seq[IntBaseNode] = Seq())
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					  val name = nodePath.lastOption.map(_.lazyModule.name).getOrElse("disconnected")
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					case class IntSinkParameters(
 | 
				
			||||||
 | 
					  nodePath: Seq[IntBaseNode] = Seq())
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					  val name = nodePath.lastOption.map(_.lazyModule.name).getOrElse("disconnected")
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
case class IntSinkPortParameters()
 | 
					 | 
				
			||||||
case class IntSourcePortParameters(sources: Seq[IntSourceParameters])
 | 
					case class IntSourcePortParameters(sources: Seq[IntSourceParameters])
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
  val num = sources.map(_.range.size).sum
 | 
					  val num = sources.map(_.range.size).sum
 | 
				
			||||||
@@ -32,6 +42,9 @@ case class IntSourcePortParameters(sources: Seq[IntSourceParameters])
 | 
				
			|||||||
  // The interrupts must perfectly cover the range
 | 
					  // The interrupts must perfectly cover the range
 | 
				
			||||||
  require (sources.map(_.range.end).max == num)
 | 
					  require (sources.map(_.range.end).max == num)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					case class IntSinkPortParameters(sinks: Seq[IntSinkParameters])
 | 
				
			||||||
 | 
					
 | 
				
			||||||
case class IntEdge(source: IntSourcePortParameters, sink: IntSinkPortParameters)
 | 
					case class IntEdge(source: IntSourcePortParameters, sink: IntSinkPortParameters)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
object IntImp extends NodeImp[IntSourcePortParameters, IntSinkPortParameters, IntEdge, IntEdge, Vec[Bool]]
 | 
					object IntImp extends NodeImp[IntSourcePortParameters, IntSinkPortParameters, IntEdge, IntEdge, Vec[Bool]]
 | 
				
			||||||
@@ -52,16 +65,21 @@ object IntImp extends NodeImp[IntSourcePortParameters, IntSinkPortParameters, In
 | 
				
			|||||||
    // Cannot use bulk connect, because the widths could differ
 | 
					    // Cannot use bulk connect, because the widths could differ
 | 
				
			||||||
    (bo zip bi) foreach { case (o, i) => i := o }
 | 
					    (bo zip bi) foreach { case (o, i) => i := o }
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  override def mixO(po: IntSourcePortParameters, node: IntBaseNode): IntSourcePortParameters =
 | 
				
			||||||
 | 
					   po.copy(sources = po.sources.map  { s => s.copy (nodePath = node +: s.nodePath) })
 | 
				
			||||||
 | 
					  override def mixI(pi: IntSinkPortParameters,  node: IntBaseNode): IntSinkPortParameters =
 | 
				
			||||||
 | 
					   pi.copy(sinks   = pi.sinks.map    { s => s.copy (nodePath = node +: s.nodePath) })
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
case class IntIdentityNode() extends IdentityNode(IntImp)
 | 
					case class IntIdentityNode() extends IdentityNode(IntImp)
 | 
				
			||||||
case class IntOutputNode() extends OutputNode(IntImp)
 | 
					case class IntOutputNode() extends OutputNode(IntImp)
 | 
				
			||||||
case class IntInputNode() extends InputNode(IntImp)
 | 
					case class IntInputNode() extends InputNode(IntImp)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
case class IntSourceNode(device: String, num: Int) extends SourceNode(IntImp)(
 | 
					case class IntSourceNode(num: Int) extends SourceNode(IntImp)(
 | 
				
			||||||
  IntSourcePortParameters(Seq(IntSourceParameters(device, num))),
 | 
					  IntSourcePortParameters(Seq(IntSourceParameters(num))), (if (num == 0) 0 else 1) to 1)
 | 
				
			||||||
  (if (num == 0) 0 else 1) to 1)
 | 
					case class IntSinkNode() extends SinkNode(IntImp)(
 | 
				
			||||||
case class IntSinkNode() extends SinkNode(IntImp)(IntSinkPortParameters())
 | 
					  IntSinkPortParameters(Seq(IntSinkParameters())))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
case class IntAdapterNode(
 | 
					case class IntAdapterNode(
 | 
				
			||||||
  sourceFn:       Seq[IntSourcePortParameters] => IntSourcePortParameters,
 | 
					  sourceFn:       Seq[IntSourcePortParameters] => IntSourcePortParameters,
 | 
				
			||||||
@@ -75,7 +93,7 @@ class IntXbar extends LazyModule
 | 
				
			|||||||
  val intnode = IntAdapterNode(
 | 
					  val intnode = IntAdapterNode(
 | 
				
			||||||
    numSourcePorts = 1 to 1, // does it make sense to have more than one interrupt sink?
 | 
					    numSourcePorts = 1 to 1, // does it make sense to have more than one interrupt sink?
 | 
				
			||||||
    numSinkPorts   = 1 to 128,
 | 
					    numSinkPorts   = 1 to 128,
 | 
				
			||||||
    sinkFn         = { _ => IntSinkPortParameters() },
 | 
					    sinkFn         = { _ => IntSinkPortParameters(Seq(IntSinkParameters())) },
 | 
				
			||||||
    sourceFn       = { seq =>
 | 
					    sourceFn       = { seq =>
 | 
				
			||||||
      IntSourcePortParameters((seq zip seq.map(_.num).scanLeft(0)(_+_).init).map {
 | 
					      IntSourcePortParameters((seq zip seq.map(_.num).scanLeft(0)(_+_).init).map {
 | 
				
			||||||
        case (s, o) => s.sources.map(z => z.copy(range = z.range.offset(o)))
 | 
					        case (s, o) => s.sources.map(z => z.copy(range = z.range.offset(o)))
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -75,7 +75,7 @@ object TLRegisterNode
 | 
				
			|||||||
abstract class TLRegisterRouterBase(address: AddressSet, interrupts: Int, concurrency: Option[Int], beatBytes: Int, undefZero: Boolean) extends LazyModule
 | 
					abstract class TLRegisterRouterBase(address: AddressSet, interrupts: Int, concurrency: Option[Int], beatBytes: Int, undefZero: Boolean) extends LazyModule
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
  val node = TLRegisterNode(address, concurrency, beatBytes, undefZero)
 | 
					  val node = TLRegisterNode(address, concurrency, beatBytes, undefZero)
 | 
				
			||||||
  val intnode = IntSourceNode(name + s" @ ${address.base}", interrupts)
 | 
					  val intnode = IntSourceNode(interrupts)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
case class TLRegBundleArg(interrupts: Vec[Vec[Bool]], in: Vec[TLBundle])
 | 
					case class TLRegBundleArg(interrupts: Vec[Vec[Bool]], in: Vec[TLBundle])
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user