1dd970561SzhanglyGitpackage xiangshan.backend.datapath 2dd970561SzhanglyGit 383ba63b3SXuan Huimport scala.collection.Seq 483ba63b3SXuan Huimport org.chipsalliance.cde.config.Parameters 5dd970561SzhanglyGitimport chisel3._ 6dd970561SzhanglyGitimport chisel3.util._ 77f847969SzhanglyGitimport freechips.rocketchip.diplomacy.{LazyModule, LazyModuleImp} 87f847969SzhanglyGitimport utility._ 9dd970561SzhanglyGitimport utils.OptionWrapper 10dd970561SzhanglyGitimport xiangshan._ 11dd970561SzhanglyGitimport xiangshan.backend._ 12dd970561SzhanglyGitimport xiangshan.backend.datapath.WbConfig._ 13dd970561SzhanglyGitimport xiangshan.backend.exu.ExeUnitParams 1483ba63b3SXuan Huimport xiangshan.backend.implicitCast._ 15dd970561SzhanglyGit 167f847969SzhanglyGitclass WbFuBusyTable(bp: BackendParams)(implicit p: Parameters) extends LazyModule { 171ca4a39dSXuan Hu override def shouldBeInlined: Boolean = false 187f847969SzhanglyGit implicit val params: BackendParams = bp 197f847969SzhanglyGit lazy val module = new WbFuBusyTableImp(this) 207f847969SzhanglyGit} 217f847969SzhanglyGit 227f847969SzhanglyGitclass WbFuBusyTableImp(override val wrapper: WbFuBusyTable)(implicit p: Parameters, params: BackendParams) extends LazyModuleImp(wrapper) { 23dd970561SzhanglyGit val io = IO(new WbFuBusyTableIO) 24dd970561SzhanglyGit 25dd970561SzhanglyGit private val intSchdBusyTable = io.in.intSchdBusyTable 2660f0c5aeSxiaofeibao private val fpSchdBusyTable = io.in.fpSchdBusyTable 27dd970561SzhanglyGit private val vfSchdBusyTable = io.in.vfSchdBusyTable 28dd970561SzhanglyGit private val memSchdBusyTable = io.in.memSchdBusyTable 29dd970561SzhanglyGit private val intRespRead = io.out.intRespRead 3060f0c5aeSxiaofeibao private val fpRespRead = io.out.fpRespRead 31dd970561SzhanglyGit private val vfRespRead = io.out.vfRespRead 32dd970561SzhanglyGit private val memRespRead = io.out.memRespRead 33dd970561SzhanglyGit private val intAllWbConflictFlag = io.out.wbConflictRead.flatten.flatten.map(_.intConflict) 3460f0c5aeSxiaofeibao private val fpAllWbConflictFlag = io.out.wbConflictRead.flatten.flatten.map(_.fpConflict) 35dd970561SzhanglyGit private val vfAllWbConflictFlag = io.out.wbConflictRead.flatten.flatten.map(_.vfConflict) 36*45d40ce7Ssinsanction private val v0AllWbConflictFlag = io.out.wbConflictRead.flatten.flatten.map(_.v0Conflict) 37*45d40ce7Ssinsanction private val vlAllWbConflictFlag = io.out.wbConflictRead.flatten.flatten.map(_.vlConflict) 38dd970561SzhanglyGit 3960f0c5aeSxiaofeibao private val intAllBusyTable = (intSchdBusyTable ++ fpSchdBusyTable ++ vfSchdBusyTable ++ memSchdBusyTable).flatten.map(_.intWbBusyTable) 4060f0c5aeSxiaofeibao private val fpAllBusyTable = (intSchdBusyTable ++ fpSchdBusyTable ++ vfSchdBusyTable ++ memSchdBusyTable).flatten.map(_.fpWbBusyTable) 4160f0c5aeSxiaofeibao private val vfAllBusyTable = (intSchdBusyTable ++ fpSchdBusyTable ++ vfSchdBusyTable ++ memSchdBusyTable).flatten.map(_.vfWbBusyTable) 42*45d40ce7Ssinsanction private val v0AllBusyTable = (intSchdBusyTable ++ fpSchdBusyTable ++ vfSchdBusyTable ++ memSchdBusyTable).flatten.map(_.v0WbBusyTable) 43*45d40ce7Ssinsanction private val vlAllBusyTable = (intSchdBusyTable ++ fpSchdBusyTable ++ vfSchdBusyTable ++ memSchdBusyTable).flatten.map(_.vlWbBusyTable) 44*45d40ce7Ssinsanction 4560f0c5aeSxiaofeibao private val intAllDeqRespSet = (intSchdBusyTable ++ fpSchdBusyTable ++ vfSchdBusyTable ++ memSchdBusyTable).flatten.map(_.intDeqRespSet) 4660f0c5aeSxiaofeibao private val fpAllDeqRespSet = (intSchdBusyTable ++ fpSchdBusyTable ++ vfSchdBusyTable ++ memSchdBusyTable).flatten.map(_.fpDeqRespSet) 4760f0c5aeSxiaofeibao private val vfAllDeqRespSet = (intSchdBusyTable ++ fpSchdBusyTable ++ vfSchdBusyTable ++ memSchdBusyTable).flatten.map(_.vfDeqRespSet) 48*45d40ce7Ssinsanction private val v0AllDeqRespSet = (intSchdBusyTable ++ fpSchdBusyTable ++ vfSchdBusyTable ++ memSchdBusyTable).flatten.map(_.v0DeqRespSet) 49*45d40ce7Ssinsanction private val vlAllDeqRespSet = (intSchdBusyTable ++ fpSchdBusyTable ++ vfSchdBusyTable ++ memSchdBusyTable).flatten.map(_.vlDeqRespSet) 50*45d40ce7Ssinsanction 5160f0c5aeSxiaofeibao private val intAllRespRead = (intRespRead ++ fpRespRead ++ vfRespRead ++ memRespRead).flatten.map(_.intWbBusyTable) 5260f0c5aeSxiaofeibao private val fpAllRespRead = (intRespRead ++ fpRespRead ++ vfRespRead ++ memRespRead).flatten.map(_.fpWbBusyTable) 5360f0c5aeSxiaofeibao private val vfAllRespRead = (intRespRead ++ fpRespRead ++ vfRespRead ++ memRespRead).flatten.map(_.vfWbBusyTable) 54*45d40ce7Ssinsanction private val v0AllRespRead = (intRespRead ++ fpRespRead ++ vfRespRead ++ memRespRead).flatten.map(_.v0WbBusyTable) 55*45d40ce7Ssinsanction private val vlAllRespRead = (intRespRead ++ fpRespRead ++ vfRespRead ++ memRespRead).flatten.map(_.vlWbBusyTable) 56dd970561SzhanglyGit 57dd970561SzhanglyGit private val allExuParams = params.allExuParams 5883ba63b3SXuan Hu private val intAllBusyTableWithParms = intAllBusyTable.zip(allExuParams).toSeq 5960f0c5aeSxiaofeibao private val fpAllBusyTableWithParms = fpAllBusyTable.zip(allExuParams).toSeq 6083ba63b3SXuan Hu private val vfAllBusyTableWithParms = vfAllBusyTable.zip(allExuParams).toSeq 61*45d40ce7Ssinsanction private val v0AllBusyTableWithParms = v0AllBusyTable.zip(allExuParams).toSeq 62*45d40ce7Ssinsanction private val vlAllBusyTableWithParms = vlAllBusyTable.zip(allExuParams).toSeq 63*45d40ce7Ssinsanction 6483ba63b3SXuan Hu private val intAllDeqRespSetWithParms = intAllDeqRespSet.zip(allExuParams).toSeq 6560f0c5aeSxiaofeibao private val fpAllDeqRespSetWithParms = fpAllDeqRespSet.zip(allExuParams).toSeq 6683ba63b3SXuan Hu private val vfAllDeqRespSetWithParms = vfAllDeqRespSet.zip(allExuParams).toSeq 67*45d40ce7Ssinsanction private val v0AllDeqRespSetWithParms = v0AllDeqRespSet.zip(allExuParams).toSeq 68*45d40ce7Ssinsanction private val vlAllDeqRespSetWithParms = vlAllDeqRespSet.zip(allExuParams).toSeq 69dd970561SzhanglyGit 70dd970561SzhanglyGit private val intWbLatencyMax = params.getIntWBExeGroup.map { case (portId, seq) => (portId, seq.map(_.intLatencyValMax).max, seq.forall(_.intLatencyCertain)) } 7160f0c5aeSxiaofeibao private val fpWbLatencyMax = params.getFpWBExeGroup.map { case (portId, seq) => (portId, seq.map(_.fpLatencyValMax).max, seq.forall(_.fpLatencyCertain)) } 72dd970561SzhanglyGit private val vfWbLatencyMax = params.getVfWBExeGroup.map { case (portId, seq) => (portId, seq.map(_.vfLatencyValMax).max, seq.forall(_.vfLatencyCertain)) } 73*45d40ce7Ssinsanction private val v0WbLatencyMax = params.getV0WBExeGroup.map { case (portId, seq) => (portId, seq.map(_.v0LatencyValMax).max, seq.forall(_.v0LatencyCertain)) } 74*45d40ce7Ssinsanction private val vlWbLatencyMax = params.getVlWBExeGroup.map { case (portId, seq) => (portId, seq.map(_.vlLatencyValMax).max, seq.forall(_.vlLatencyCertain)) } 75*45d40ce7Ssinsanction 767f847969SzhanglyGit private val intWbBusyTable: Map[Int, Option[UInt]] = intWbLatencyMax.map { case (portId, latMax, latCertain) => (portId, OptionWrapper(latCertain, Wire(UInt((latMax + 1).W)))) }.toMap 7760f0c5aeSxiaofeibao private val fpWbBusyTable = fpWbLatencyMax.map { case (portId, latMax, latCertain) => (portId, OptionWrapper(latCertain, Wire(UInt((latMax + 1).W)))) }.toMap 787f847969SzhanglyGit private val vfWbBusyTable = vfWbLatencyMax.map { case (portId, latMax, latCertain) => (portId, OptionWrapper(latCertain, Wire(UInt((latMax + 1).W)))) }.toMap 79*45d40ce7Ssinsanction private val v0WbBusyTable = v0WbLatencyMax.map { case (portId, latMax, latCertain) => (portId, OptionWrapper(latCertain, Wire(UInt((latMax + 1).W)))) }.toMap 80*45d40ce7Ssinsanction private val vlWbBusyTable = vlWbLatencyMax.map { case (portId, latMax, latCertain) => (portId, OptionWrapper(latCertain, Wire(UInt((latMax + 1).W)))) }.toMap 81*45d40ce7Ssinsanction 827f847969SzhanglyGit private val intConflict: Map[Int, Option[Bool]] = intWbLatencyMax.map { case (portId, latMax, latCertain) => (portId, OptionWrapper(latCertain, Reg(Bool()))) }.toMap 8360f0c5aeSxiaofeibao private val fpConflict = fpWbLatencyMax.map { case (portId, latMax, latCertain) => (portId, OptionWrapper(latCertain, Reg(Bool()))) }.toMap 847f847969SzhanglyGit private val vfConflict = vfWbLatencyMax.map { case (portId, latMax, latCertain) => (portId, OptionWrapper(latCertain, Reg(Bool()))) }.toMap 85*45d40ce7Ssinsanction private val v0Conflict = v0WbLatencyMax.map { case (portId, latMax, latCertain) => (portId, OptionWrapper(latCertain, Reg(Bool()))) }.toMap 86*45d40ce7Ssinsanction private val vlConflict = vlWbLatencyMax.map { case (portId, latMax, latCertain) => (portId, OptionWrapper(latCertain, Reg(Bool()))) }.toMap 87dd970561SzhanglyGit 8860f0c5aeSxiaofeibao def hitWbPort[T <: Data](source: Option[T], p: ExeUnitParams, portId: Int, wbType: PregWB) = { 8960f0c5aeSxiaofeibao wbType match { 9060f0c5aeSxiaofeibao case IntWB(_, _) => p.wbPortConfigs.collectFirst { case x: IntWB => x.port }.getOrElse(-1) == portId && source.nonEmpty 9160f0c5aeSxiaofeibao case FpWB(_, _) => p.wbPortConfigs.collectFirst { case x: FpWB => x.port }.getOrElse(-1) == portId && source.nonEmpty 9260f0c5aeSxiaofeibao case VfWB(_, _) => p.wbPortConfigs.collectFirst { case x: VfWB => x.port }.getOrElse(-1) == portId && source.nonEmpty 93*45d40ce7Ssinsanction case V0WB(_, _) => p.wbPortConfigs.collectFirst { case x: V0WB => x.port }.getOrElse(-1) == portId && source.nonEmpty 94*45d40ce7Ssinsanction case VlWB(_, _) => p.wbPortConfigs.collectFirst { case x: VlWB => x.port }.getOrElse(-1) == portId && source.nonEmpty 95*45d40ce7Ssinsanction case _ => throw new IllegalArgumentException(s"WbConfig ${wbType} is not permitted") 967f847969SzhanglyGit } 97dd970561SzhanglyGit } 98dd970561SzhanglyGit 9960f0c5aeSxiaofeibao def writeBusyTable(wtBusyTable: Map[Int, Option[UInt]], busyTableWithParams: Seq[(Option[UInt], ExeUnitParams)], wbType: PregWB) = { 1007f847969SzhanglyGit wtBusyTable.foreach { case (portId, busyTable) => 101dd970561SzhanglyGit if (busyTable.nonEmpty) { 10260f0c5aeSxiaofeibao busyTable.get := busyTableWithParams.filter { case (busyTable, p) => hitWbPort(busyTable, p, portId, wbType) }.map(_._1.get).reduce(_ | _) 103dd970561SzhanglyGit } 104dd970561SzhanglyGit } 105dd970561SzhanglyGit } 106dd970561SzhanglyGit 10760f0c5aeSxiaofeibao def writeConflict(wtConflict: Map[Int, Option[Bool]], deqRespSetWithParams: Seq[(Option[UInt], ExeUnitParams)], wbType: PregWB) = { 1087f847969SzhanglyGit wtConflict.foreach { case (portId, conflict) => 1097f847969SzhanglyGit if (conflict.nonEmpty) { 11060f0c5aeSxiaofeibao val deqRespSel = deqRespSetWithParams.filter { case (deqRespSet, p) => hitWbPort(deqRespSet, p, portId, wbType) }.map(_._1.get) 1117f847969SzhanglyGit val width = deqRespSel.map(x => x.getWidth).max 11283ba63b3SXuan Hu val deqRespSelUnify = deqRespSel.map(x => x.asTypeOf(UInt(width.W))).toSeq 1137f847969SzhanglyGit conflict.get := (0 until width).map { case i => 1147f847969SzhanglyGit OnesMoreThan(deqRespSelUnify.map(x => x(i)), 2) 1157f847969SzhanglyGit }.reduce(_ | _) 1167f847969SzhanglyGit } 1177f847969SzhanglyGit } 1187f847969SzhanglyGit } 1197f847969SzhanglyGit 12060f0c5aeSxiaofeibao def readRes[T <: Data](sink: IndexedSeq[Option[T]], source: Map[Int, Option[T]], wbType: PregWB) = { 121dd970561SzhanglyGit for (i <- 0 until sink.size) { 122dd970561SzhanglyGit if (sink(i).nonEmpty) { 1237f847969SzhanglyGit sink(i).get := source.map { case (portId, src) => 12460f0c5aeSxiaofeibao if (hitWbPort(src, allExuParams(i), portId, wbType)) { 125dd970561SzhanglyGit src.get.asTypeOf(sink(i).get).asUInt 126dd970561SzhanglyGit } else { 127dd970561SzhanglyGit 0.U.asTypeOf(sink(i).get).asUInt 128dd970561SzhanglyGit } 1297f847969SzhanglyGit }.reduce(_ | _) 130dd970561SzhanglyGit } 131dd970561SzhanglyGit } 132dd970561SzhanglyGit } 133dd970561SzhanglyGit 1347f847969SzhanglyGit 1357f847969SzhanglyGit 1367f847969SzhanglyGit //per wbPort fuBusyTable 13760f0c5aeSxiaofeibao writeBusyTable(intWbBusyTable, intAllBusyTableWithParms, IntWB()) 13860f0c5aeSxiaofeibao writeBusyTable(fpWbBusyTable, fpAllBusyTableWithParms, FpWB()) 13960f0c5aeSxiaofeibao writeBusyTable(vfWbBusyTable, vfAllBusyTableWithParms, VfWB()) 140*45d40ce7Ssinsanction writeBusyTable(v0WbBusyTable, v0AllBusyTableWithParms, V0WB()) 141*45d40ce7Ssinsanction writeBusyTable(vlWbBusyTable, vlAllBusyTableWithParms, VlWB()) 1427f847969SzhanglyGit //per wbPort conflict 14360f0c5aeSxiaofeibao writeConflict(intConflict, intAllDeqRespSetWithParms, IntWB()) 14460f0c5aeSxiaofeibao writeConflict(fpConflict, fpAllDeqRespSetWithParms, FpWB()) 14560f0c5aeSxiaofeibao writeConflict(vfConflict, vfAllDeqRespSetWithParms, VfWB()) 146*45d40ce7Ssinsanction writeConflict(v0Conflict, v0AllDeqRespSetWithParms, V0WB()) 147*45d40ce7Ssinsanction writeConflict(vlConflict, vlAllDeqRespSetWithParms, VlWB()) 148dd970561SzhanglyGit //read wbPort fuBusyTable to per exe 14960f0c5aeSxiaofeibao readRes(intAllRespRead, intWbBusyTable, IntWB()) 15060f0c5aeSxiaofeibao readRes(fpAllRespRead, fpWbBusyTable, FpWB()) 15160f0c5aeSxiaofeibao readRes(vfAllRespRead, vfWbBusyTable, VfWB()) 152*45d40ce7Ssinsanction readRes(v0AllRespRead, v0WbBusyTable, V0WB()) 153*45d40ce7Ssinsanction readRes(vlAllRespRead, vlWbBusyTable, VlWB()) 154dd970561SzhanglyGit //read wbPort conflict to dataPath 15560f0c5aeSxiaofeibao readRes(intAllWbConflictFlag, intConflict, IntWB()) 15660f0c5aeSxiaofeibao readRes(fpAllWbConflictFlag, fpConflict, FpWB()) 15760f0c5aeSxiaofeibao readRes(vfAllWbConflictFlag, vfConflict, VfWB()) 158*45d40ce7Ssinsanction readRes(v0AllWbConflictFlag, v0Conflict, V0WB()) 159*45d40ce7Ssinsanction readRes(vlAllWbConflictFlag, vlConflict, VlWB()) 160dd970561SzhanglyGit} 161dd970561SzhanglyGit 162dd970561SzhanglyGitclass WbFuBusyTableIO(implicit p: Parameters, params: BackendParams) extends XSBundle { 163dd970561SzhanglyGit val in = new Bundle { 164dd970561SzhanglyGit val intSchdBusyTable = MixedVec(params.intSchdParams.get.issueBlockParams.map(x => Input(x.genWbFuBusyTableWriteBundle))) 16560f0c5aeSxiaofeibao val fpSchdBusyTable = MixedVec(params.fpSchdParams.get.issueBlockParams.map(x => Input(x.genWbFuBusyTableWriteBundle))) 166dd970561SzhanglyGit val vfSchdBusyTable = MixedVec(params.vfSchdParams.get.issueBlockParams.map(x => Input(x.genWbFuBusyTableWriteBundle))) 167dd970561SzhanglyGit val memSchdBusyTable = MixedVec(params.memSchdParams.get.issueBlockParams.map(x => Input(x.genWbFuBusyTableWriteBundle))) 168dd970561SzhanglyGit } 169dd970561SzhanglyGit val out = new Bundle { 170dd970561SzhanglyGit val intRespRead = MixedVec(params.intSchdParams.get.issueBlockParams.map(x => Output(x.genWbFuBusyTableReadBundle))) 17160f0c5aeSxiaofeibao val fpRespRead = MixedVec(params.fpSchdParams.get.issueBlockParams.map(x => Output(x.genWbFuBusyTableReadBundle))) 172dd970561SzhanglyGit val vfRespRead = MixedVec(params.vfSchdParams.get.issueBlockParams.map(x => Output(x.genWbFuBusyTableReadBundle))) 173dd970561SzhanglyGit val memRespRead = MixedVec(params.memSchdParams.get.issueBlockParams.map(x => Output(x.genWbFuBusyTableReadBundle))) 174dd970561SzhanglyGit val wbConflictRead = MixedVec(params.allSchdParams.map(x => MixedVec(x.issueBlockParams.map(x => Output(x.genWbConflictBundle()))))) 175dd970561SzhanglyGit } 176dd970561SzhanglyGit}