135d005dfSXuan Hupackage xiangshan.backend.fu.wrapper 235d005dfSXuan Hu 383ba63b3SXuan Huimport org.chipsalliance.cde.config.Parameters 4cdf8c16cSxgkiriimport chisel3.{VecInit, _} 535d005dfSXuan Huimport chisel3.util._ 6cdf8c16cSxgkiriimport chisel3.util.experimental.decode.{QMCMinimizer, TruthTable, decoder} 7bb2f3f51STang Haojinimport utility.{DelayN, XSError} 835d005dfSXuan Huimport xiangshan.XSCoreParamsKey 9*785e3bfdSXuan Huimport xiangshan.backend.fu.vector.Bundles.{VConfig, VSew} 1030fcc710SZiyue Zhangimport xiangshan.backend.fu.vector.{Mgu, Mgtu, VecPipedFuncUnit} 1135d005dfSXuan Huimport xiangshan.backend.fu.vector.Utils.VecDataToMaskDataVec 12cdf8c16cSxgkiriimport xiangshan.backend.fu.vector.utils.VecDataSplitModule 1335d005dfSXuan Huimport xiangshan.backend.fu.{FuConfig, FuType} 14c33d4a9eSXuan Huimport xiangshan.ExceptionNO 1535d005dfSXuan Huimport yunsuan.{OpType, VialuFixType} 16cdf8c16cSxgkiriimport yunsuan.vector.alu.{VIntFixpAlu64b, VIntFixpDecode, VIntFixpTable} 1735d005dfSXuan Huimport yunsuan.encoding.{VdType, Vs1IntType, Vs2IntType} 1835d005dfSXuan Huimport yunsuan.encoding.Opcode.VialuOpcode 19cdf8c16cSxgkiriimport yunsuan.vector.SewOH 2035d005dfSXuan Hu 2135d005dfSXuan Huclass VIAluSrcTypeIO extends Bundle { 2235d005dfSXuan Hu val in = Input(new Bundle { 2335d005dfSXuan Hu val fuOpType: UInt = OpType() 2435d005dfSXuan Hu val vsew: UInt = VSew() 2535d005dfSXuan Hu val isReverse: Bool = Bool() // vrsub, vrdiv 2635d005dfSXuan Hu val isExt: Bool = Bool() 2735d005dfSXuan Hu val isDstMask: Bool = Bool() // vvm, vvvm, mmm 2835d005dfSXuan Hu val isMove: Bool = Bool() // vmv.s.x, vmv.v.v, vmv.v.x, vmv.v.i 2935d005dfSXuan Hu }) 3035d005dfSXuan Hu val out = Output(new Bundle { 3135d005dfSXuan Hu val vs1Type: UInt = Vs1IntType() 3235d005dfSXuan Hu val vs2Type: UInt = Vs2IntType() 3335d005dfSXuan Hu val vdType: UInt = VdType() 3435d005dfSXuan Hu val illegal: Bool = Bool() 35cdf8c16cSxgkiri val isVextF2: Bool = Bool() 36cdf8c16cSxgkiri val isVextF4: Bool = Bool() 37cdf8c16cSxgkiri val isVextF8: Bool = Bool() 3835d005dfSXuan Hu }) 3935d005dfSXuan Hu} 4035d005dfSXuan Hu 4135d005dfSXuan Huclass VIAluSrcTypeModule extends Module { 4235d005dfSXuan Hu val io: VIAluSrcTypeIO = IO(new VIAluSrcTypeIO) 4335d005dfSXuan Hu 4435d005dfSXuan Hu private val vsew = io.in.vsew 4535d005dfSXuan Hu private val isExt = io.in.isExt 4635d005dfSXuan Hu private val isDstMask = io.in.isDstMask 4735d005dfSXuan Hu 4835d005dfSXuan Hu private val opcode = VialuFixType.getOpcode(io.in.fuOpType) 4935d005dfSXuan Hu private val isSign = VialuFixType.isSigned(io.in.fuOpType) 5035d005dfSXuan Hu private val format = VialuFixType.getFormat(io.in.fuOpType) 5135d005dfSXuan Hu 5235d005dfSXuan Hu private val vsewX2 = vsew + 1.U 5335d005dfSXuan Hu private val vsewF2 = vsew - 1.U 5435d005dfSXuan Hu private val vsewF4 = vsew - 2.U 5535d005dfSXuan Hu private val vsewF8 = vsew - 3.U 5635d005dfSXuan Hu 5735d005dfSXuan Hu private val isAddSub = opcode === VialuOpcode.vadd || opcode === VialuOpcode.vsub 5835d005dfSXuan Hu private val isShiftRight = Seq(VialuOpcode.vsrl, VialuOpcode.vsra, VialuOpcode.vssrl, VialuOpcode.vssra).map(fmt => fmt === format).reduce(_ || _) 5935d005dfSXuan Hu private val isVext = opcode === VialuOpcode.vext 6035d005dfSXuan Hu 6135d005dfSXuan Hu private val isWiden = isAddSub && Seq(VialuFixType.FMT.VVW, VialuFixType.FMT.WVW).map(fmt => fmt === format).reduce(_ || _) 6235d005dfSXuan Hu private val isNarrow = isShiftRight && format === VialuFixType.FMT.WVV 6335d005dfSXuan Hu private val isVextF2 = isVext && format === VialuFixType.FMT.VF2 6435d005dfSXuan Hu private val isVextF4 = isVext && format === VialuFixType.FMT.VF4 6535d005dfSXuan Hu private val isVextF8 = isVext && format === VialuFixType.FMT.VF8 6635d005dfSXuan Hu 6735d005dfSXuan Hu // check illegal 6835d005dfSXuan Hu private val widenIllegal = isWiden && vsewX2 === VSew.e8 6935d005dfSXuan Hu private val narrowIllegal = isNarrow && vsewF2 === VSew.e64 7035d005dfSXuan Hu private val vextIllegal = (isVextF2 && (vsewF2 === VSew.e64)) || 7135d005dfSXuan Hu (isVextF4 && (vsewF4 === VSew.e64)) || 7235d005dfSXuan Hu (isVextF8 && (vsewF8 === VSew.e64)) 7335d005dfSXuan Hu // Todo: use it 7435d005dfSXuan Hu private val illegal = widenIllegal || narrowIllegal || vextIllegal 7535d005dfSXuan Hu 7639c388b5SXuan Hu private val intType = Cat(0.U(1.W), isSign) 7739c388b5SXuan Hu 7835d005dfSXuan Hu private class Vs2Vs1VdSew extends Bundle { 7935d005dfSXuan Hu val vs2 = VSew() 8035d005dfSXuan Hu val vs1 = VSew() 8135d005dfSXuan Hu val vd = VSew() 8235d005dfSXuan Hu } 8335d005dfSXuan Hu 8439c388b5SXuan Hu private class Vs2Vs1VdType extends Bundle { 8539c388b5SXuan Hu val vs2 = Vs2IntType() 8639c388b5SXuan Hu val vs1 = Vs1IntType() 8739c388b5SXuan Hu val vd = VdType() 8839c388b5SXuan Hu } 8939c388b5SXuan Hu 9035d005dfSXuan Hu private val addSubSews = Mux1H(Seq( 9135d005dfSXuan Hu (format === VialuFixType.FMT.VVV) -> Cat(vsew, vsew, vsew), 9235d005dfSXuan Hu (format === VialuFixType.FMT.VVW) -> Cat(vsew, vsew, vsewX2), 9335d005dfSXuan Hu (format === VialuFixType.FMT.WVW) -> Cat(vsewX2, vsew, vsewX2), 9435d005dfSXuan Hu (format === VialuFixType.FMT.WVV) -> Cat(vsewX2, vsew, vsew), 9535d005dfSXuan Hu )).asTypeOf(new Vs2Vs1VdSew) 9635d005dfSXuan Hu 9735d005dfSXuan Hu private val vextSews = Mux1H(Seq( 9835d005dfSXuan Hu (format === VialuFixType.FMT.VF2) -> Cat(vsewF2, vsewF2, vsew), 9935d005dfSXuan Hu (format === VialuFixType.FMT.VF4) -> Cat(vsewF4, vsewF4, vsew), 10035d005dfSXuan Hu (format === VialuFixType.FMT.VF8) -> Cat(vsewF8, vsewF8, vsew), 10135d005dfSXuan Hu )).asTypeOf(new Vs2Vs1VdSew) 10235d005dfSXuan Hu 10339c388b5SXuan Hu private val maskTypes = Mux1H(Seq( 10439c388b5SXuan Hu (format === VialuFixType.FMT.VVM) -> Cat(Cat(intType, vsew), Cat(intType, vsew), VdType.mask), 1059eaaa75dSXuan Hu (format === VialuFixType.FMT.VVMM) -> Cat(Cat(intType, vsew), Cat(intType, vsew), VdType.mask), 10639c388b5SXuan Hu (format === VialuFixType.FMT.MMM) -> Cat(Vs2IntType.mask, Vs1IntType.mask, VdType.mask), 10739c388b5SXuan Hu )).asTypeOf(new Vs2Vs1VdType) 10835d005dfSXuan Hu 10935d005dfSXuan Hu private val vs2Type = Mux1H(Seq( 11039c388b5SXuan Hu isDstMask -> maskTypes.vs2, 11139c388b5SXuan Hu isExt -> Cat(intType, vextSews.vs2), 11239c388b5SXuan Hu (!isExt && !isDstMask) -> Cat(intType, addSubSews.vs2), 11335d005dfSXuan Hu )) 11435d005dfSXuan Hu private val vs1Type = Mux1H(Seq( 11539c388b5SXuan Hu isDstMask -> maskTypes.vs1, 11639c388b5SXuan Hu isExt -> Cat(intType, vextSews.vs1), 11739c388b5SXuan Hu (!isExt && !isDstMask) -> Cat(intType, addSubSews.vs1), 11835d005dfSXuan Hu )) 11935d005dfSXuan Hu private val vdType = Mux1H(Seq( 12039c388b5SXuan Hu isDstMask -> maskTypes.vd, 12139c388b5SXuan Hu isExt -> Cat(intType, vextSews.vd), 12239c388b5SXuan Hu (!isExt && !isDstMask) -> Cat(intType, addSubSews.vd), 12335d005dfSXuan Hu )) 12435d005dfSXuan Hu 12535d005dfSXuan Hu io.out.vs2Type := vs2Type 12635d005dfSXuan Hu io.out.vs1Type := vs1Type 12735d005dfSXuan Hu io.out.vdType := vdType 12835d005dfSXuan Hu io.out.illegal := illegal 129cdf8c16cSxgkiri io.out.isVextF2 := isVextF2 130cdf8c16cSxgkiri io.out.isVextF4 := isVextF4 131cdf8c16cSxgkiri io.out.isVextF8 := isVextF8 13235d005dfSXuan Hu} 13335d005dfSXuan Hu 13435d005dfSXuan Huclass VIAluFix(cfg: FuConfig)(implicit p: Parameters) extends VecPipedFuncUnit(cfg) { 13535d005dfSXuan Hu XSError(io.in.valid && io.in.bits.ctrl.fuOpType === VialuFixType.dummy, "VialuF OpType not supported") 13635d005dfSXuan Hu 137cdf8c16cSxgkiri // config params 1382d12882cSxiaofeibao private val dataWidth = cfg.destDataBits 139cdf8c16cSxgkiri private val dataWidthOfDataModule = 64 140cdf8c16cSxgkiri private val numVecModule = dataWidth / dataWidthOfDataModule 141cdf8c16cSxgkiri 14235d005dfSXuan Hu // modules 143cdf8c16cSxgkiri private val typeMod = Module(new VIAluSrcTypeModule) 144cdf8c16cSxgkiri private val vs2Split = Module(new VecDataSplitModule(dataWidth, dataWidthOfDataModule)) 145cdf8c16cSxgkiri private val vs1Split = Module(new VecDataSplitModule(dataWidth, dataWidthOfDataModule)) 146cdf8c16cSxgkiri private val oldVdSplit = Module(new VecDataSplitModule(dataWidth, dataWidthOfDataModule)) 147cdf8c16cSxgkiri private val vIntFixpAlus = Seq.fill(numVecModule)(Module(new VIntFixpAlu64b)) 148cdf8c16cSxgkiri private val mgu = Module(new Mgu(dataWidth)) 14930fcc710SZiyue Zhang private val mgtu = Module(new Mgtu(dataWidth)) 15035d005dfSXuan Hu 15135d005dfSXuan Hu /** 152cdf8c16cSxgkiri * [[typeMod]]'s in connection 15335d005dfSXuan Hu */ 154cdf8c16cSxgkiri typeMod.io.in.fuOpType := fuOpType 155cdf8c16cSxgkiri typeMod.io.in.vsew := vsew 156cdf8c16cSxgkiri typeMod.io.in.isReverse := isReverse 157cdf8c16cSxgkiri typeMod.io.in.isExt := isExt 158cdf8c16cSxgkiri typeMod.io.in.isDstMask := vecCtrl.isDstMask 159cdf8c16cSxgkiri typeMod.io.in.isMove := isMove 160cdf8c16cSxgkiri 161cdf8c16cSxgkiri private val vs2GroupedVec32b: Vec[UInt] = VecInit(vs2Split.io.outVec32b.zipWithIndex.groupBy(_._2 % 2).map(x => x._1 -> x._2.map(_._1)).values.map(x => Cat(x.reverse)).toSeq) 162cdf8c16cSxgkiri private val vs2GroupedVec16b: Vec[UInt] = VecInit(vs2Split.io.outVec16b.zipWithIndex.groupBy(_._2 % 2).map(x => x._1 -> x._2.map(_._1)).values.map(x => Cat(x.reverse)).toSeq) 163cdf8c16cSxgkiri private val vs2GroupedVec8b : Vec[UInt] = VecInit(vs2Split.io.outVec8b .zipWithIndex.groupBy(_._2 % 2).map(x => x._1 -> x._2.map(_._1)).values.map(x => Cat(x.reverse)).toSeq) 164fcd66f18SZhaoyang You private val vs1GroupedVec32b: Vec[UInt] = VecInit(vs1Split.io.outVec32b.zipWithIndex.groupBy(_._2 % 2).map(x => x._1 -> x._2.map(_._1)).values.map(x => Cat(x.reverse)).toSeq) 165fcd66f18SZhaoyang You private val vs1GroupedVec16b: Vec[UInt] = VecInit(vs1Split.io.outVec16b.zipWithIndex.groupBy(_._2 % 2).map(x => x._1 -> x._2.map(_._1)).values.map(x => Cat(x.reverse)).toSeq) 166fcd66f18SZhaoyang You private val vs1GroupedVec8b : Vec[UInt] = VecInit(vs1Split.io.outVec8b .zipWithIndex.groupBy(_._2 % 2).map(x => x._1 -> x._2.map(_._1)).values.map(x => Cat(x.reverse)).toSeq) 16735d005dfSXuan Hu 16835d005dfSXuan Hu /** 169cdf8c16cSxgkiri * In connection of [[vs2Split]], [[vs1Split]] and [[oldVdSplit]] 17035d005dfSXuan Hu */ 171cdf8c16cSxgkiri vs2Split.io.inVecData := vs2 172cdf8c16cSxgkiri vs1Split.io.inVecData := vs1 173cdf8c16cSxgkiri oldVdSplit.io.inVecData := oldVd 174cdf8c16cSxgkiri 175cdf8c16cSxgkiri /** 176cdf8c16cSxgkiri * [[vIntFixpAlus]]'s in connection 177cdf8c16cSxgkiri */ 178cdf8c16cSxgkiri private val opcode = VialuFixType.getOpcode(inCtrl.fuOpType).asTypeOf(vIntFixpAlus.head.io.opcode) 179cdf8c16cSxgkiri private val vs1Type = typeMod.io.out.vs1Type 180cdf8c16cSxgkiri private val vs2Type = typeMod.io.out.vs2Type 181cdf8c16cSxgkiri private val vdType = typeMod.io.out.vdType 182cdf8c16cSxgkiri private val isVextF2 = typeMod.io.out.isVextF2 183cdf8c16cSxgkiri private val isVextF4 = typeMod.io.out.isVextF4 184cdf8c16cSxgkiri private val isVextF8 = typeMod.io.out.isVextF8 185cdf8c16cSxgkiri 186cdf8c16cSxgkiri private val truthTable = TruthTable(VIntFixpTable.table, VIntFixpTable.default) 187cdf8c16cSxgkiri private val decoderOut = decoder(QMCMinimizer, Cat(opcode.op), truthTable) 188cdf8c16cSxgkiri private val vIntFixpDecode = decoderOut.asTypeOf(new VIntFixpDecode) 189cdf8c16cSxgkiri private val isFixp = Mux(vIntFixpDecode.misc, opcode.isScalingShift, opcode.isSatAdd || opcode.isAvgAdd) 190cdf8c16cSxgkiri private val widen = opcode.isAddSub && vs1Type(1, 0) =/= vdType(1, 0) 191cdf8c16cSxgkiri private val widen_vs2 = widen && vs2Type(1, 0) =/= vdType(1, 0) 192cdf8c16cSxgkiri private val eewVs1 = SewOH(vs1Type(1, 0)) 193cdf8c16cSxgkiri private val eewVd = SewOH(vdType(1, 0)) 194fcd66f18SZhaoyang You private val isVwsll = opcode.isVwsll 195cdf8c16cSxgkiri 196cdf8c16cSxgkiri // Extension instructions 197cdf8c16cSxgkiri private val vf2 = isVextF2 198cdf8c16cSxgkiri private val vf4 = isVextF4 199cdf8c16cSxgkiri private val vf8 = isVextF8 200cdf8c16cSxgkiri 201fcd66f18SZhaoyang You private val vs1VecUsed: Vec[UInt] = Wire(Vec(numVecModule, UInt(64.W))) 202fcd66f18SZhaoyang You private val vs2VecUsed: Vec[UInt] = Wire(Vec(numVecModule, UInt(64.W))) 203fcd66f18SZhaoyang You private val isVwsllEewVdIs64 = isVwsll && eewVd.is64 204fcd66f18SZhaoyang You private val isVwsllEewVdIs32 = isVwsll && eewVd.is32 205fcd66f18SZhaoyang You private val isVwsllEewVdIs16 = isVwsll && eewVd.is16 206fcd66f18SZhaoyang You when(widen || isNarrow || isVwsllEewVdIs64) { 207fcd66f18SZhaoyang You vs1VecUsed := vs1GroupedVec32b 208fcd66f18SZhaoyang You }.elsewhen(isVwsllEewVdIs32) { 209fcd66f18SZhaoyang You vs1VecUsed := vs1GroupedVec16b 210fcd66f18SZhaoyang You }.elsewhen(isVwsllEewVdIs16) { 211fcd66f18SZhaoyang You vs1VecUsed := vs1GroupedVec8b 212fcd66f18SZhaoyang You }.otherwise { 213fcd66f18SZhaoyang You vs1VecUsed := vs1Split.io.outVec64b 214fcd66f18SZhaoyang You } 215fcd66f18SZhaoyang You when(vf2 || isVwsllEewVdIs64) { 216cdf8c16cSxgkiri vs2VecUsed := vs2GroupedVec32b 217fcd66f18SZhaoyang You }.elsewhen(vf4 || isVwsllEewVdIs32) { 218cdf8c16cSxgkiri vs2VecUsed := vs2GroupedVec16b 219fcd66f18SZhaoyang You }.elsewhen(vf8 || isVwsllEewVdIs16) { 220cdf8c16cSxgkiri vs2VecUsed := vs2GroupedVec8b 221cdf8c16cSxgkiri }.otherwise { 222cdf8c16cSxgkiri vs2VecUsed := vs2Split.io.outVec64b 22335d005dfSXuan Hu } 22435d005dfSXuan Hu 225b1712600SZiyue Zhang private val vs2Adder = Mux(widen_vs2, vs2GroupedVec32b, vs2Split.io.outVec64b) 2268f7a869bSZiyue Zhang 227cdf8c16cSxgkiri // mask 228cdf8c16cSxgkiri private val maskDataVec: Vec[UInt] = VecDataToMaskDataVec(srcMask, vsew) 229cdf8c16cSxgkiri private val maskIdx = Mux(isNarrow, (vuopIdx >> 1.U).asUInt, vuopIdx) 2301a6cfb3dSxgkiri private val eewVd_is_1b = vdType === VdType.mask 231cdf8c16cSxgkiri private val maskUsed = splitMask(maskDataVec(maskIdx), Mux(eewVd_is_1b, eewVs1, eewVd)) 232cdf8c16cSxgkiri 233cdf8c16cSxgkiri private val oldVdUsed = splitMask(VecDataToMaskDataVec(oldVd, vs1Type(1, 0))(vuopIdx), eewVs1) 234cdf8c16cSxgkiri 235cdf8c16cSxgkiri vIntFixpAlus.zipWithIndex.foreach { 236cdf8c16cSxgkiri case (mod, i) => 237e8e02b74SsinceforYy mod.io.fire := io.in.valid 238cdf8c16cSxgkiri mod.io.opcode := opcode 239cdf8c16cSxgkiri 240cdf8c16cSxgkiri mod.io.info.vm := vm 241cdf8c16cSxgkiri mod.io.info.ma := vma 242cdf8c16cSxgkiri mod.io.info.ta := vta 243cdf8c16cSxgkiri mod.io.info.vlmul := vlmul 244cdf8c16cSxgkiri mod.io.info.vl := vl 245cdf8c16cSxgkiri mod.io.info.vstart := vstart 246cdf8c16cSxgkiri mod.io.info.uopIdx := vuopIdx 247cdf8c16cSxgkiri mod.io.info.vxrm := vxrm 248cdf8c16cSxgkiri 249cdf8c16cSxgkiri mod.io.srcType(0) := vs2Type 250cdf8c16cSxgkiri mod.io.srcType(1) := vs1Type 251cdf8c16cSxgkiri mod.io.vdType := vdType 252cdf8c16cSxgkiri mod.io.narrow := isNarrow 253cdf8c16cSxgkiri mod.io.isSub := vIntFixpDecode.sub 254cdf8c16cSxgkiri mod.io.isMisc := vIntFixpDecode.misc 255cdf8c16cSxgkiri mod.io.isFixp := isFixp 256cdf8c16cSxgkiri mod.io.widen := widen 257cdf8c16cSxgkiri mod.io.widen_vs2 := widen_vs2 258cdf8c16cSxgkiri mod.io.vs1 := vs1VecUsed(i) 2598f7a869bSZiyue Zhang mod.io.vs2_adder := vs2Adder(i) 2608f7a869bSZiyue Zhang mod.io.vs2_misc := vs2VecUsed(i) 261cdf8c16cSxgkiri mod.io.vmask := maskUsed(i) 262cdf8c16cSxgkiri mod.io.oldVd := oldVdUsed(i) 263cdf8c16cSxgkiri } 264cdf8c16cSxgkiri 265cdf8c16cSxgkiri /** 266cdf8c16cSxgkiri * [[mgu]]'s in connection 267cdf8c16cSxgkiri */ 268fcd66f18SZhaoyang You private val outIsVwsll = RegEnable(isVwsll, io.in.valid) 269fcd66f18SZhaoyang You private val outIsVwsllEewVdIs64 = RegEnable(isVwsllEewVdIs64, io.in.valid) 270fcd66f18SZhaoyang You private val outIsVwsllEewVdIs32 = RegEnable(isVwsllEewVdIs32, io.in.valid) 271fcd66f18SZhaoyang You private val outIsVwsllEewVdIs16 = RegEnable(isVwsllEewVdIs16, io.in.valid) 27234588aebSlewislzh //private val outEewVs1 = DelayN(eewVs1, latency) 27334588aebSlewislzh private val outEewVs1 = SNReg(eewVs1, latency) 274cdf8c16cSxgkiri 275fcd66f18SZhaoyang You private val outVdTmp = Cat(vIntFixpAlus.reverse.map(_.io.vd)) 276fcd66f18SZhaoyang You private val outVd = Mux1H(Seq( 277fcd66f18SZhaoyang You (outIsVwsllEewVdIs64 || !outIsVwsll) -> outVdTmp, 278fcd66f18SZhaoyang You outIsVwsllEewVdIs32 -> Cat(outVdTmp(127, 96), outVdTmp(63, 32), outVdTmp( 95, 64), outVdTmp(31, 0)), 279fcd66f18SZhaoyang You outIsVwsllEewVdIs16 -> Cat(outVdTmp(127, 112), outVdTmp(63, 48), outVdTmp(111, 96), outVdTmp(47, 32), outVdTmp(95, 80), outVdTmp(31, 16), outVdTmp(79, 64), outVdTmp(15,0)), 280fcd66f18SZhaoyang You )) 2811a6cfb3dSxgkiri private val outCmp = Mux1H(outEewVs1.oneHot, Seq(8, 4, 2, 1).map( 282cdf8c16cSxgkiri k => Cat(vIntFixpAlus.reverse.map(_.io.cmpOut(k - 1, 0))))) 283cdf8c16cSxgkiri private val outNarrow = Cat(vIntFixpAlus.reverse.map(_.io.narrowVd)) 284daae8f22SZiyue Zhang private val outOpcode = VialuFixType.getOpcode(outCtrl.fuOpType).asTypeOf(vIntFixpAlus.head.io.opcode) 285cdf8c16cSxgkiri 2860895fee6SZiyue Zhang private val numBytes = dataWidth / 8 2870895fee6SZiyue Zhang private val maxMaskIdx = numBytes 2880895fee6SZiyue Zhang private val maxVdIdx = 8 2890895fee6SZiyue Zhang private val elementsInOneUop = Mux1H(outEewVs1.oneHot, Seq(1, 2, 4, 8).map(k => (numBytes / k).U(5.W))) 2900895fee6SZiyue Zhang private val vdIdx = outVecCtrl.vuopIdx(2, 0) 2910895fee6SZiyue Zhang private val elementsComputed = Mux1H(Seq.tabulate(maxVdIdx)(i => (vdIdx === i.U) -> (elementsInOneUop * i.U))) 2920895fee6SZiyue Zhang val outCmpWithTail = Wire(Vec(maxMaskIdx, UInt(1.W))) 2930895fee6SZiyue Zhang // set the bits in vd to 1 if the index is larger than vl and vta is true 2940895fee6SZiyue Zhang for (i <- 0 until maxMaskIdx) { 2950895fee6SZiyue Zhang when(elementsComputed +& i.U >= outVl) { 2967ee6b881SZiyue Zhang // always operate under a tail-agnostic policy 2977ee6b881SZiyue Zhang outCmpWithTail(i) := 1.U 2980895fee6SZiyue Zhang }.otherwise { 2990895fee6SZiyue Zhang outCmpWithTail(i) := outCmp(i) 3000895fee6SZiyue Zhang } 3010895fee6SZiyue Zhang } 3020895fee6SZiyue Zhang 30381cbff07Schengguanghui /* insts whose mask is not used to generate 'agnosticEn' and 'activeEn' in mgu: 304cdf8c16cSxgkiri * vadc, vmadc... 305cdf8c16cSxgkiri * vmerge 306cdf8c16cSxgkiri */ 307cdf8c16cSxgkiri private val needNoMask = VialuFixType.needNoMask(outCtrl.fuOpType) 308cdf8c16cSxgkiri private val maskToMgu = Mux(needNoMask, allMaskTrue, outSrcMask) 309cdf8c16cSxgkiri 310cdf8c16cSxgkiri private val outFormat = VialuFixType.getFormat(outCtrl.fuOpType) 311cdf8c16cSxgkiri private val outWiden = (outFormat === VialuFixType.FMT.VVW | outFormat === VialuFixType.FMT.WVW) & !outVecCtrl.isExt & !outVecCtrl.isDstMask 312cdf8c16cSxgkiri private val narrow = outVecCtrl.isNarrow 313cdf8c16cSxgkiri private val dstMask = outVecCtrl.isDstMask 314904d2184SZiyue Zhang private val outVxsat = Mux(narrow, Cat(vIntFixpAlus.reverse.map(_.io.vxsat(3, 0))), Cat(vIntFixpAlus.reverse.map(_.io.vxsat))) 315904d2184SZiyue Zhang 316904d2184SZiyue Zhang // the result of narrow inst which needs concat 317904d2184SZiyue Zhang private val narrowNeedCat = outVecCtrl.vuopIdx(0).asBool && narrow 318e03e0c5bSZiyue Zhang private val outNarrowVd = Mux(narrowNeedCat, Cat(outNarrow, outOldVd(dataWidth / 2 - 1, 0)), Cat(outOldVd(dataWidth - 1, dataWidth / 2), outNarrow)) 319904d2184SZiyue Zhang private val outVxsatReal = Mux(narrowNeedCat, Cat(outVxsat(numBytes / 2 - 1, 0), 0.U((numBytes / 2).W)), outVxsat) 320cdf8c16cSxgkiri 321cdf8c16cSxgkiri private val outEew = Mux(outWiden, outVecCtrl.vsew + 1.U, outVecCtrl.vsew) 322cdf8c16cSxgkiri 323daae8f22SZiyue Zhang /* 324daae8f22SZiyue Zhang * vl of vmv.x.s is 1 325daae8f22SZiyue Zhang */ 326daae8f22SZiyue Zhang private val outIsVmvsx = outOpcode.isVmvsx 327daae8f22SZiyue Zhang 328daae8f22SZiyue Zhang /* 329daae8f22SZiyue Zhang * when vstart >= vl, no need to update vd, the old value should be kept 330daae8f22SZiyue Zhang */ 331daae8f22SZiyue Zhang private val outVstartGeVl = outVstart >= outVl 332daae8f22SZiyue Zhang 333cdf8c16cSxgkiri mgu.io.in.vd := MuxCase(outVd, Seq( 334904d2184SZiyue Zhang narrow -> outNarrowVd, 3350895fee6SZiyue Zhang dstMask -> outCmpWithTail.asUInt, 336cdf8c16cSxgkiri )) 337cdf8c16cSxgkiri mgu.io.in.oldVd := outOldVd 338cdf8c16cSxgkiri mgu.io.in.mask := maskToMgu 339cdf8c16cSxgkiri mgu.io.in.info.ta := outVecCtrl.vta 340cdf8c16cSxgkiri mgu.io.in.info.ma := outVecCtrl.vma 341daae8f22SZiyue Zhang mgu.io.in.info.vl := Mux(outIsVmvsx, 1.U, outVl) 342b3e2881cSxiaofeibao-xjtu mgu.io.in.info.vlmul := outVecCtrl.vlmul 34334588aebSlewislzh mgu.io.in.info.valid := validVec.last 344cdf8c16cSxgkiri mgu.io.in.info.vstart := outVecCtrl.vstart 345cdf8c16cSxgkiri mgu.io.in.info.eew := outEew 346b3e2881cSxiaofeibao-xjtu mgu.io.in.info.vsew := outVecCtrl.vsew 347cdf8c16cSxgkiri mgu.io.in.info.vdIdx := outVecCtrl.vuopIdx 348cdf8c16cSxgkiri mgu.io.in.info.narrow := narrow 349cdf8c16cSxgkiri mgu.io.in.info.dstMask := dstMask 35092c6b7edSzhanglinjuan mgu.io.in.isIndexedVls := false.B 351cdf8c16cSxgkiri 35230fcc710SZiyue Zhang /** 35330fcc710SZiyue Zhang * [[mgtu]]'s in connection, for vmask instructions 35430fcc710SZiyue Zhang */ 3557ee6b881SZiyue Zhang mgtu.io.in.vd := Mux(dstMask && !outVecCtrl.isOpMask, mgu.io.out.vd, outVd) 35630fcc710SZiyue Zhang mgtu.io.in.vl := outVl 35730fcc710SZiyue Zhang 3587ee6b881SZiyue Zhang io.out.bits.res.data := Mux(outVstartGeVl, outOldVd, Mux(dstMask, mgtu.io.out.vd, mgu.io.out.vd)) 35981cbff07Schengguanghui io.out.bits.res.vxsat.get := Mux(outVstartGeVl, false.B, (outVxsatReal & mgu.io.out.active).orR) 360daae8f22SZiyue Zhang io.out.bits.ctrl.exceptionVec.get(ExceptionNO.illegalInstr) := mgu.io.out.illegal && !outVstartGeVl 361cdf8c16cSxgkiri 362cdf8c16cSxgkiri // util function 363cdf8c16cSxgkiri def splitMask(maskIn: UInt, sew: SewOH): Vec[UInt] = { 364cdf8c16cSxgkiri val maskWidth = maskIn.getWidth 365cdf8c16cSxgkiri val result = Wire(Vec(maskWidth / 8, UInt(8.W))) 366cdf8c16cSxgkiri for ((resultData, i) <- result.zipWithIndex) { 367cdf8c16cSxgkiri resultData := Mux1H(Seq( 368cdf8c16cSxgkiri sew.is8 -> maskIn(i * 8 + 7, i * 8), 3691a6cfb3dSxgkiri sew.is16 -> Cat(0.U((8 - 4).W), maskIn(i * 4 + 3, i * 4)), 3701a6cfb3dSxgkiri sew.is32 -> Cat(0.U((8 - 2).W), maskIn(i * 2 + 1, i * 2)), 3711a6cfb3dSxgkiri sew.is64 -> Cat(0.U((8 - 1).W), maskIn(i)), 372cdf8c16cSxgkiri )) 373cdf8c16cSxgkiri } 374cdf8c16cSxgkiri result 375cdf8c16cSxgkiri } 376cdf8c16cSxgkiri 37735d005dfSXuan Hu}