xref: /XiangShan/src/main/scala/xiangshan/backend/issue/MultiWakeupQueue.scala (revision 8dd322207ff851bc7045d19d2aa746039d1fdf51)
125bcff47SXuan Hupackage xiangshan.backend.issue
225bcff47SXuan Hu
325bcff47SXuan Huimport chisel3._
425bcff47SXuan Huimport chisel3.util._
525bcff47SXuan Huimport utils.PipeWithFlush
6ec1fea84SzhanglyGitimport xiangshan.backend.Bundles.{ExuInput, connectSamePort}
70c7ebb58Sxiaofeibao-xjtuimport xiangshan.backend.exu.ExeUnitParams
825bcff47SXuan Hu
9ec1fea84SzhanglyGitclass MultiWakeupQueueIO[T <: Bundle, TFlush <: Data](
102aaa83c0Sxiaofeibao-xjtu  gen       : ExuInput,
112aaa83c0Sxiaofeibao-xjtu  lastGen   : ExuInput,
1225bcff47SXuan Hu  flushGen  : TFlush,
1325bcff47SXuan Hu  latWidth  : Int,
1425bcff47SXuan Hu) extends Bundle {
1525bcff47SXuan Hu  class EnqBundle extends Bundle {
1625bcff47SXuan Hu    val uop = Output(gen)
1725bcff47SXuan Hu    val lat = Output(UInt(latWidth.W))
1825bcff47SXuan Hu  }
1925bcff47SXuan Hu
20493a9370SHaojin Tang  val flush = Input(flushGen)
2125bcff47SXuan Hu  val enq = Flipped(Valid(new EnqBundle))
220c7ebb58Sxiaofeibao-xjtu  val deq = Output(Valid(lastGen))
2325bcff47SXuan Hu}
2425bcff47SXuan Hu
25ec1fea84SzhanglyGitclass MultiWakeupQueue[T <: Bundle, TFlush <: Data](
262aaa83c0Sxiaofeibao-xjtu  val gen       : ExuInput,
272aaa83c0Sxiaofeibao-xjtu  val lastGen   : ExuInput,
2825bcff47SXuan Hu  val flushGen  : TFlush,
2925bcff47SXuan Hu  val latencySet: Set[Int],
302aaa83c0Sxiaofeibao-xjtu  flushFunc : (ExuInput, TFlush, Int) => Bool,
312aaa83c0Sxiaofeibao-xjtu  modificationFunc: ExuInput => ExuInput = { x: ExuInput => x },
322aaa83c0Sxiaofeibao-xjtu  lastConnectFunc: (ExuInput, ExuInput) => ExuInput,
3325bcff47SXuan Hu) extends Module {
3425bcff47SXuan Hu  require(latencySet.min >= 0)
3525bcff47SXuan Hu
36ec1fea84SzhanglyGit  val io = IO(new MultiWakeupQueueIO(gen, lastGen, flushGen, log2Up(latencySet.max) + 1))
3725bcff47SXuan Hu
38ec1fea84SzhanglyGit  val pipes = latencySet.map(x => Module(new PipeWithFlush[T, TFlush](gen, flushGen, x, flushFunc, modificationFunc))).toSeq
39ec1fea84SzhanglyGit
40ec1fea84SzhanglyGit  val pipesOut = Wire(Valid(gen))
41ec1fea84SzhanglyGit  val lastConnect = Reg(Valid(lastGen))
4225bcff47SXuan Hu
43493a9370SHaojin Tang  pipes.zip(latencySet).foreach {
44493a9370SHaojin Tang    case (pipe, lat) =>
4525bcff47SXuan Hu      pipe.io.flush := io.flush
46493a9370SHaojin Tang      pipe.io.enq.valid := io.enq.valid && io.enq.bits.lat === lat.U
4725bcff47SXuan Hu      pipe.io.enq.bits := io.enq.bits.uop
4825bcff47SXuan Hu  }
4925bcff47SXuan Hu
50ec1fea84SzhanglyGit  private val pipesValidVec = VecInit(pipes.map(_.io.deq).zip(latencySet).map(_ match {
515f4ac341Sxiaofeibao-xjtu    case (deq, 0) => deq.valid
52ec1fea84SzhanglyGit    case (deq, i) => deq.valid && !flushFunc(deq.bits, io.flush, i)
53ec1fea84SzhanglyGit  }))
54ec49b127Ssinsanction  private val pipesBitsVec = VecInit(pipes.map(_.io.deq.bits).zip(latencySet).map(_ match {
55ec49b127Ssinsanction    case (deq, 0) => deq
56ec49b127Ssinsanction    case (deq, i) => modificationFunc(deq)
57ec49b127Ssinsanction  }))
5825bcff47SXuan Hu
59ec1fea84SzhanglyGit  pipesOut.valid := pipesValidVec.asUInt.orR
60ec1fea84SzhanglyGit  pipesOut.bits := Mux1H(pipesValidVec, pipesBitsVec)
612aaa83c0Sxiaofeibao-xjtu  pipesOut.bits.rfWen .foreach(_ := pipesValidVec.zip(pipesBitsVec.map(_.rfWen .get)).map{case(valid,wen) => valid && wen}.reduce(_||_))
622aaa83c0Sxiaofeibao-xjtu  pipesOut.bits.fpWen .foreach(_ := pipesValidVec.zip(pipesBitsVec.map(_.fpWen .get)).map{case(valid,wen) => valid && wen}.reduce(_||_))
632aaa83c0Sxiaofeibao-xjtu  pipesOut.bits.vecWen.foreach(_ := pipesValidVec.zip(pipesBitsVec.map(_.vecWen.get)).map{case(valid,wen) => valid && wen}.reduce(_||_))
64*8dd32220Ssinsanction  pipesOut.bits.v0Wen .foreach(_ := pipesValidVec.zip(pipesBitsVec.map(_.v0Wen .get)).map{case(valid,wen) => valid && wen}.reduce(_||_))
65*8dd32220Ssinsanction  pipesOut.bits.vlWen .foreach(_ := pipesValidVec.zip(pipesBitsVec.map(_.vlWen .get)).map{case(valid,wen) => valid && wen}.reduce(_||_))
66ec1fea84SzhanglyGit
67ec1fea84SzhanglyGit  lastConnect.valid := pipesOut.valid
68ec1fea84SzhanglyGit  lastConnect.bits := lastConnectFunc(pipesOut.bits, lastConnect.bits)
69ec1fea84SzhanglyGit
70ec1fea84SzhanglyGit  io.deq.valid := lastConnect.valid
71ec1fea84SzhanglyGit  io.deq.bits := lastConnect.bits
7225bcff47SXuan Hu
738e208fb5SXuan Hu  assert(PopCount(pipesValidVec) <= 1.U, "PopCount(pipesValidVec) should be no more than 1")
7425bcff47SXuan Hu}
75