1/*************************************************************************************** 2* Copyright (c) 2024 Beijing Institute of Open Source Chip (BOSC) 3* Copyright (c) 2020-2024 Institute of Computing Technology, Chinese Academy of Sciences 4* Copyright (c) 2020-2021 Peng Cheng Laboratory 5* 6* XiangShan is licensed under Mulan PSL v2. 7* You can use this software according to the terms and conditions of the Mulan PSL v2. 8* You may obtain a copy of Mulan PSL v2 at: 9* http://license.coscl.org.cn/MulanPSL2 10* 11* THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, 12* EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, 13* MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE. 14* 15* See the Mulan PSL v2 for more details. 16***************************************************************************************/ 17 18// The "SRT4DividerDataModule" in this file is a scala rewrite of SRT4 divider by Yifei He, see 19// https://github.com/OpenXiangShan/XS-Verilog-Library/tree/main/int_div_radix_4_v1 20// Email of original author: [email protected] 21 22package xiangshan.backend.fu 23 24import org.chipsalliance.cde.config.Parameters 25import chisel3._ 26import chisel3.util._ 27import utility.SignExt 28import xiangshan.backend.fu.util.CSA3_2 29 30/** A Radix-4 SRT Integer Divider 31 * 32 * 2 ~ (5 + (len+3)/2) cycles are needed for each division. 33 */ 34class SRT4DividerDataModule(len: Int) extends Module { 35 val io = IO(new Bundle() { 36 val src = Vec(2, Input(UInt(len.W))) 37 val valid, sign, kill_w, kill_r, isHi, isW = Input(Bool()) 38 val in_ready = Output(Bool()) 39 val out_valid = Output(Bool()) 40 val out_data = Output(UInt(len.W)) 41 val out_ready = Input(Bool()) 42 }) 43 44 // consts 45 val lzc_width = log2Up(len) 46 val itn_len = 1 + len + 2 + 1 47 require(lzc_width == 6) 48 49 val (a, d, sign, valid, kill_w, kill_r, isHi, isW) = 50 (io.src(0), io.src(1), io.sign, io.valid, io.kill_w, io.kill_r, io.isHi, io.isW) 51 val in_fire = valid && io.in_ready 52 val out_fire = io.out_ready && io.out_valid 53 val newReq = in_fire 54 val startHandShake = io.in_ready && valid 55 val s_idle :: s_pre_0 :: s_pre_1 :: s_iter :: s_post_0 :: s_post_1 :: s_finish :: Nil = Enum(7) 56 57 val state = RegInit(UIntToOH(s_idle, 7)) 58 59 val quot_neg_2 :: quot_neg_1 :: quot_0 :: quot_pos_1 :: quot_pos_2 :: Nil = Enum(5) 60 61 val finished = state(s_finish) 62 63 // reused wire declarations 64 val aIsZero = Wire(Bool()) 65 val dIsZero = Wire(Bool()) 66 val aTooSmall = Wire(Bool()) // this is output of reg! 67 val noIter = Wire(Bool()) // this is output of reg! 68 val finalIter = Wire(Bool()) 69 val aLZC = Wire(UInt((lzc_width + 1).W)) 70 val dLZC = Wire(UInt((lzc_width + 1).W)) 71 val aNormAbs = Wire(UInt((len + 1).W)) 72 val dNormAbs = Wire(UInt((len + 1).W)) 73 val aInverter = Wire(UInt(len.W)) // results of global inverter 74 val dInverter = Wire(UInt(len.W)) 75 76 val rPreShifted = Wire(UInt((len + 1).W)) 77 78 val quotIter = Wire(UInt(len.W)) 79 val quotM1Iter = Wire(UInt(len.W)) 80 val qIterEnd = Wire(UInt(5.W)) 81 82 val rNext = Wire(UInt(itn_len.W)) 83 val rNextPd = Wire(UInt(itn_len.W)) // non-redundant remainder plus d, 68, 67 84 //reused ctrl regs 85 86 //reused other regs 87 val aNormAbsReg = RegEnable(aNormAbs, startHandShake | state(s_pre_0) | state(s_post_0)) // reg for normalized a & d and rem & rem+d 88 val dNormAbsReg = RegEnable(dNormAbs, startHandShake | state(s_pre_0) | state(s_post_0)) 89 val quotIterReg = RegEnable(quotIter, state(s_pre_1) | state(s_iter) | state(s_post_0)) 90 val quotM1IterReg = RegEnable(quotM1Iter, state(s_pre_1) | state(s_iter) | state(s_post_0)) 91 92 when(kill_r) { 93 state := UIntToOH(s_idle, 7) 94 } .elsewhen(state(s_idle) && in_fire && !kill_w) { 95 state := UIntToOH(s_pre_0, 7) 96 } .elsewhen(state(s_pre_0)) { // leading zero detection 97 state := UIntToOH(s_pre_1, 7) 98 } .elsewhen(state(s_pre_1)) { // shift a/b 99 state := Mux(dIsZero | aTooSmall | noIter, UIntToOH(s_post_0, 7), UIntToOH(s_iter, 7)) 100 } .elsewhen(state(s_iter)) { // (ws[j+1], wc[j+1]) = 4(ws[j],wc[j]) - q(j+1)*d 101 state := Mux(finalIter, UIntToOH(s_post_0, 7), UIntToOH(s_iter, 7)) 102 } .elsewhen(state(s_post_0)) { // if rem < 0, rem = rem + d 103 state := UIntToOH(s_post_1, 7) 104 } .elsewhen(state(s_post_1)) { 105 state := UIntToOH(s_finish, 7) 106 } .elsewhen(state(s_finish) && out_fire) { 107 state := UIntToOH(s_idle, 7) 108 } .otherwise { 109 state := state 110 } 111 112 // First cycle: 113 // State is idle, we gain absolute value of a and b, using global inverter 114 115 io.in_ready := state(s_idle) 116 117 aInverter := -Mux(state(s_idle), a, quotIterReg) // 64, 0 118 dInverter := -Mux(state(s_idle), d, quotM1IterReg) // 64, 0 119 120 val aSign = io.sign && a(len - 1) // 1 121 val dSign = io.sign && d(len - 1) 122 123 val aAbs = Mux(aSign, aInverter, a) // 64, 0 124 val dAbs = Mux(dSign, dInverter, d) 125 val aNorm = (aNormAbsReg(len - 1, 0) << aLZC(lzc_width - 1, 0))(len - 1, 0) // 64, 65 126 val dNorm = (dNormAbsReg(len - 1, 0) << dLZC(lzc_width - 1, 0))(len - 1, 0) 127 128 aNormAbs := Mux1H(Seq( 129 state(s_idle) -> Cat(0.U(1.W), aAbs), // 65, 0 130 state(s_pre_0) -> Cat(0.U(1.W), aNorm), // 65, 0 131 state(s_post_0) -> rNext(len + 3, 3) // remainder 65, 64. highest is sign bit 132 )) 133 dNormAbs := Mux1H(Seq( 134 state(s_idle) -> Cat(0.U(1.W), dAbs), 135 state(s_pre_0) -> Cat(0.U(1.W), dNorm), 136 state(s_post_0) -> rNextPd(len + 3, 3) 137 )) 138 139 // Second cycle, state is pre_0 140 // calculate lzc and move div* and lzc diff check if no_iter_needed 141 142 aLZC := PriorityEncoder(aNormAbsReg(len - 1, 0).asBools.reverse) 143 dLZC := PriorityEncoder(dNormAbsReg(len - 1, 0).asBools.reverse) 144 val aLZCReg = RegEnable(aLZC, state(s_pre_0)) // 7, 0 145 val dLZCReg = RegEnable(dLZC, state(s_pre_0)) 146 147 148 149 val lzcWireDiff = Cat(0.U(1.W), dLZC(lzc_width - 1, 0)) - Cat(0.U(1.W), aLZC(lzc_width - 1, 0)) // 7, 0 150 val lzcRegDiff = Cat(0.U(1.W), dLZCReg(lzc_width - 1, 0)) - Cat(0.U(1.W), aLZCReg(lzc_width - 1, 0)) 151 val lzcDiff = Mux(state(s_pre_0), lzcWireDiff, lzcRegDiff) 152 aIsZero := aLZC(lzc_width) // this is state pre_0 153 dIsZero := dLZCReg(lzc_width) // this is pre_1 and all stages after 154 val dIsOne = dLZC(lzc_width - 1, 0).andR // this is pre_0 155 val noIterReg = RegEnable(dIsOne & aNormAbsReg(len - 1), state(s_pre_0)) // This means dividend has lzc 0 so iter is 17 156 noIter := noIterReg 157 val aTooSmallReg = RegEnable(aIsZero | lzcDiff(lzc_width), state(s_pre_0)) // a is zero or a smaller than d 158 aTooSmall := aTooSmallReg 159 160 val quotSign = Mux(state(s_idle), aSign ^ dSign, true.B) // if not s_idle then must be s_pre_1 & dIsZero, and that we have 161 val rSign = aSign 162 val quotSignReg = RegEnable(quotSign, startHandShake | (state(s_pre_1) & dIsZero)) 163 val rSignReg = RegEnable(rSign, startHandShake) 164 165 val rShift = lzcDiff(0) // odd lzc diff, for SRT4 166 val rightShifted = Wire(UInt(len.W)) 167 val rSumInit = Mux(aTooSmallReg | aIsZero, Cat(0.U(1.W), rightShifted, 0.U(3.W)), // right shift the dividend (which is already l-shifted) 168 Mux(noIterReg, 0.U(itn_len.W), // 169 Cat(0.U(3.W), 170 Mux(rShift, Cat(0.U(1.W), aNormAbsReg(len - 1, 0)), Cat(aNormAbsReg(len - 1, 0), 0.U(1.W))) 171 ) // Normal init value. 68, 67; For even lzcDiff, 0.001xxx0; for odd lzcDiff 0.0001xxx 172 ) 173 ) // state is s_pre_1 174 val rCarryInit = 0.U(itn_len.W) 175 176 val rightShifter = Module(new RightShifter(len, lzc_width)) 177 rightShifter.io.in := Mux(state(s_pre_1), aNormAbsReg(len - 1, 0), rPreShifted(len - 1, 0)) 178 rightShifter.io.shiftNum := Mux(state(s_pre_1), aLZCReg, 179 Mux(aTooSmallReg | dIsZero, 0.U(lzc_width.W), dLZCReg)) 180 rightShifter.io.msb := state(s_post_1) & rSignReg & rPreShifted(len) 181 rightShifted := rightShifter.io.out 182 183 // obtaining 1st quotient 184 val rSumInitTrunc = Cat(0.U(1.W), rSumInit(itn_len - 4, itn_len - 4 - 4 + 1)) // 0.00___ 185 val mInitPos1 = MuxLookup(dNormAbsReg(len - 2, len - 2 - 3 + 1), "b00100".U(5.W))( 186 Seq( 187 0.U -> "b00100".U(5.W), 188 1.U -> "b00100".U(5.W), 189 2.U -> "b00100".U(5.W), 190 3.U -> "b00110".U(5.W), 191 4.U -> "b00110".U(5.W), 192 5.U -> "b00110".U(5.W), 193 6.U -> "b00110".U(5.W), 194 7.U -> "b01000".U(5.W), 195 ) 196 ) 197 val mInitPos2 = MuxLookup(dNormAbsReg(len - 2, len - 2 - 3 + 1), "b01100".U(5.W))( 198 Seq( 199 0.U -> "b01100".U(5.W), 200 1.U -> "b01110".U(5.W), 201 2.U -> "b01111".U(5.W), 202 3.U -> "b10000".U(5.W), 203 4.U -> "b10010".U(5.W), 204 5.U -> "b10100".U(5.W), 205 6.U -> "b10110".U(5.W), 206 7.U -> "b10110".U(5.W), 207 ) 208 ) 209 val initCmpPos1 = rSumInitTrunc >= mInitPos1 210 val initCmpPos2 = rSumInitTrunc >= mInitPos2 211 val qInit = Mux(initCmpPos2, UIntToOH(quot_pos_2, 5), Mux(initCmpPos1, UIntToOH(quot_pos_1, 5), UIntToOH(quot_0, 5))) 212 val qPrev = Mux(state(s_pre_1), qInit, qIterEnd) 213 val qPrevReg = RegEnable(qPrev, state(s_pre_1) | state(s_iter)) 214 val specialDivisorReg = RegEnable(dNormAbsReg(len - 2, len - 2 - 3 + 1) === 0.U, state(s_pre_1)) // d=0.1000xxx 215 // rCarry and rSum in Iteration 216 val qXd = Mux1H(Seq( 217 qPrevReg(quot_neg_2) -> Cat(dNormAbsReg(len - 1, 0), 0.U(4.W)), // 68, 67 1.xxxxx0000 218 qPrevReg(quot_neg_1) -> Cat(0.U(1.W), dNormAbsReg(len - 1, 0), 0.U(3.W)), // 0.1xxxxx000 219 qPrevReg(quot_0) -> 0.U(itn_len.W), 220 qPrevReg(quot_pos_1) -> ~Cat(0.U(1.W), dNormAbsReg(len - 1, 0), 0.U(3.W)), // don't forget to plus 1 later 221 qPrevReg(quot_pos_2) -> ~Cat(dNormAbsReg(len - 1, 0), 0.U(4.W)) // don't forget to plus 1 later 222 )) 223 val csa = Module(new CSA3_2(itn_len)) 224 225 val rSumIter = csa.io.out(0) 226 val rCarryIter = Cat(csa.io.out(1)(itn_len - 2, 0), qPrevReg(quot_pos_1) | qPrevReg(quot_pos_2)) 227 val rSumReg = RegEnable(Mux(state(s_pre_1), rSumInit, rSumIter), state(s_pre_1) | state(s_iter)) // 68, 67 228 val rCarryReg = RegEnable(Mux(state(s_pre_1), rCarryInit, rCarryIter), state(s_pre_1) | state(s_iter)) 229 csa.io.in(0) := rSumReg << 2 230 csa.io.in(1) := rCarryReg << 2 231 csa.io.in(2) := qXd 232 233 val qds = Module(new SRT4QDS(len, itn_len)) 234 qds.io.remSum := rSumReg 235 qds.io.remCarry := rCarryReg 236 qds.io.d := dNormAbsReg(len - 1, 0) // Maybe optimize here to lower power consumption? 237 qds.io.specialDivisor := specialDivisorReg 238 qds.io.qPrev := qPrevReg 239 qIterEnd := qds.io.qIterEnd 240 241 //on the fly conversion 242 val quotIterNext = Wire(UInt(len.W)) 243 val quotIterM1Next = Wire(UInt(len.W)) 244 quotIterNext := Mux1H(Seq( 245 qPrevReg(quot_pos_2) -> (quotIterReg << 2 | "b10".U), 246 qPrevReg(quot_pos_1) -> (quotIterReg << 2 | "b01".U), 247 qPrevReg(quot_0) -> (quotIterReg << 2 | "b00".U), 248 qPrevReg(quot_neg_1) -> (quotM1IterReg << 2 | "b11".U), 249 qPrevReg(quot_neg_2) -> (quotM1IterReg << 2 | "b10".U) 250 )) 251 quotIterM1Next := Mux1H(Seq( 252 qPrevReg(quot_pos_2) -> (quotIterReg << 2 | "b01".U), 253 qPrevReg(quot_pos_1) -> (quotIterReg << 2 | "b00".U), 254 qPrevReg(quot_0) -> (quotM1IterReg << 2 | "b11".U), 255 qPrevReg(quot_neg_1) -> (quotM1IterReg << 2 | "b10".U), 256 qPrevReg(quot_neg_2) -> (quotM1IterReg << 2 | "b01".U) 257 )) 258 259 260 quotIter := Mux(state(s_pre_1), 261 Mux(dIsZero, VecInit(Seq.fill(len)(true.B)).asUInt, 262 Mux(noIterReg, aNormAbsReg(len - 1, 0), 0.U(len.W))), 263 Mux(state(s_iter), quotIterNext, 264 Mux(quotSignReg, aInverter, quotIterReg))) 265 quotM1Iter := Mux(state(s_pre_1), 266 0.U(len.W), Mux(state(s_iter), quotIterM1Next, 267 Mux(quotSignReg, dInverter, quotM1IterReg))) 268 269 270 // iter num 271 val iterNum = Wire(UInt((lzc_width - 1).W)) 272 val iterNumReg = RegEnable(iterNum, state(s_pre_1) | state(s_iter)) 273 274 iterNum := Mux(state(s_pre_1), lzcDiff(lzc_width - 1, 1) +% lzcDiff(0), iterNumReg -% 1.U) 275 finalIter := iterNumReg === 0.U 276 277 // Post Process 278 279 when(rSignReg) { 280 rNext := ~rSumReg + ~rCarryReg + 2.U 281 rNextPd := ~rSumReg + ~rCarryReg + ~Cat(0.U(1.W), dNormAbsReg(len - 1, 0), 0.U(3.W)) + 3.U 282 } .otherwise { 283 rNext := rSumReg + rCarryReg 284 rNextPd := rSumReg + rCarryReg + Cat(0.U(1.W), dNormAbsReg(len - 1, 0), 0.U(3.W)) 285 } 286 287 val r = aNormAbsReg 288 val rPd = dNormAbsReg 289 val rIsZero = ~(r.orR) 290 val needCorr = (~dIsZero & ~noIterReg) & Mux(rSignReg, ~r(len) & ~rIsZero, r(len)) // when we get pos rem for d<0 or neg rem for d>0 291 rPreShifted := Mux(needCorr, rPd, r) 292 val rFinal = RegEnable(rightShifted, state(s_post_1))// right shifted remainder. shift by the number of bits divisor is shifted 293 val qFinal = Mux(needCorr, quotM1IterReg, quotIterReg) 294 val res = Mux(isHi, rFinal, qFinal) 295 io.out_data := Mux(isW, 296 SignExt(res(31, 0), len), 297 res 298 ) 299 io.in_ready := state(s_idle) 300 io.out_valid := state(s_finish) // state === s_finish 301} 302 303class RightShifter(len: Int, lzc_width: Int) extends Module { 304 val io = IO(new Bundle() { 305 val shiftNum = Input(UInt(lzc_width.W)) 306 val in = Input(UInt(len.W)) 307 val msb = Input(Bool()) 308 val out = Output(UInt(len.W)) 309 }) 310 require(len == 64 || len == 32) 311 val shift = io.shiftNum 312 val msb = io.msb 313 val s0 = Mux(shift(0), Cat(VecInit(Seq.fill(1)(msb)).asUInt, io.in(len - 1, 1)), io.in) 314 val s1 = Mux(shift(1), Cat(VecInit(Seq.fill(2)(msb)).asUInt, s0(len - 1, 2)), s0) 315 val s2 = Mux(shift(2), Cat(VecInit(Seq.fill(4)(msb)).asUInt, s1(len - 1, 4)), s1) 316 val s3 = Mux(shift(3), Cat(VecInit(Seq.fill(8)(msb)).asUInt, s2(len - 1, 8)), s2) 317 val s4 = Mux(shift(4), Cat(VecInit(Seq.fill(16)(msb)).asUInt, s3(len - 1, 16)), s3) 318 val s5 = Wire(UInt(len.W)) 319 if (len == 64) { 320 s5 := Mux(shift(5), Cat(VecInit(Seq.fill(32)(msb)).asUInt, s4(len - 1, 32)), s4) 321 } else if (len == 32) { 322 s5 := s4 323 } 324 io.out := s5 325} 326 327object mLookUpTable { 328 // Usage : 329 // result := decoder(QMCMinimizer, index, mLookupTable.xxx) 330 val minus_m = Seq( 331 Seq( // -m[-1] 332 0.U -> "b00_11010".U, 333 1.U -> "b00_11110".U, 334 2.U -> "b01_00000".U, 335 3.U -> "b01_00100".U, 336 4.U -> "b01_00110".U, 337 5.U -> "b01_01010".U, 338 6.U -> "b01_01100".U, 339 7.U -> "b01_10000".U 340 ), 341 Seq( // -m[0] 342 0.U -> "b000_0101".U, 343 1.U -> "b000_0110".U, 344 2.U -> "b000_0110".U, 345 3.U -> "b000_0110".U, 346 4.U -> "b000_1001".U, 347 5.U -> "b000_1000".U, 348 6.U -> "b000_1000".U, 349 7.U -> "b000_1000".U 350 ), 351 Seq( //-m[1] 352 0.U -> "b111_1101".U, 353 1.U -> "b111_1100".U, 354 2.U -> "b111_1100".U, 355 3.U -> "b111_1100".U, 356 4.U -> "b111_1011".U, 357 5.U -> "b111_1010".U, 358 6.U -> "b111_1010".U, 359 7.U -> "b111_1010".U 360 ), 361 Seq( //-m[2] 362 0.U -> "b11_01000".U, 363 1.U -> "b11_00100".U, 364 2.U -> "b11_00010".U, 365 3.U -> "b10_11110".U, 366 4.U -> "b10_11100".U, 367 5.U -> "b10_11000".U, 368 6.U -> "b10_10110".U, 369 7.U -> "b10_10010".U 370 )) 371} 372 373class SRT4QDS(len: Int, itn_len: Int) extends Module { 374 // srt4 quotientr digit selection 375 val io = IO(new Bundle() { 376 val remSum = Input(UInt(itn_len.W)) // 68, 67 377 val remCarry = Input(UInt(itn_len.W)) 378 val d = Input(UInt(len.W)) // 64, 64 379 val specialDivisor = Input(Bool()) 380 val qPrev = Input(UInt(5.W)) 381 val qIterEnd = Output(UInt(5.W)) 382 }) 383 val remSumX16 = io.remSum << 4 // 72, 67 Top 2 bits unused 384 val remCarryX16 = io.remCarry << 4 385 def trunc25(rem: UInt): UInt = {rem(itn_len, itn_len - 7 + 1)} 386 def trunc34(rem: UInt): UInt = {rem(itn_len + 1, itn_len + 1 - 7 + 1)} 387 388 val quot_neg_2 :: quot_neg_1 :: quot_0 :: quot_pos_1 :: quot_pos_2 :: Nil = Enum(5) 389 390 val d = Cat(0.U(1.W), io.d, 0.U(3.W)) // 68, 67 391 val (dX4, dX8, dXNeg4, dXNeg8) = (d << 2, d(itn_len - 2, 0) << 3, ~(d << 2), ~(d(itn_len - 2, 0) << 3)) // 70, 67 392 val dForLookup = io.d(len - 2, len - 2 - 3 + 1) 393 394 val dXq = Mux1H(Seq( 395 io.qPrev(quot_neg_2) -> dX8, 396 io.qPrev(quot_neg_1) -> dX4, 397 io.qPrev(quot_0) -> 0.U((itn_len + 2).W), 398 io.qPrev(quot_pos_1) -> dXNeg4, 399 io.qPrev(quot_pos_2) -> dXNeg8 400 )) 401 val signs = VecInit(Seq.tabulate(4){ // -1 0 1 2 402 i => { 403 val csa1 = Module(new CSA3_2(7)) 404 val csa2 = Module(new CSA3_2(7)) 405 if (i == 1 || i == 2) { 406 csa1.io.in(0) := trunc34(remSumX16) 407 csa1.io.in(1) := trunc34(remCarryX16) 408 csa2.io.in(2) := trunc34(dXq) 409 } else { 410 csa1.io.in(0) := trunc25(remSumX16) 411 csa1.io.in(1) := trunc25(remCarryX16) 412 csa2.io.in(2) := trunc25(dXq) 413 } 414 csa1.io.in(2) := MuxLookup(dForLookup, "b0000000".U)(mLookUpTable.minus_m(i)) 415 csa2.io.in(0) := csa1.io.out(0) 416 csa2.io.in(1) := csa1.io.out(1)(5, 0) << 1 417 (csa2.io.out(0) + (csa2.io.out(1)(5, 0) << 1))(6) 418 } 419 }) 420 val qVec = Wire(Vec(5, Bool())) 421 qVec(quot_neg_2) := signs(0) && signs(1) && signs(2) 422 qVec(quot_neg_1) := ~signs(0) && signs(1) && signs(2) 423 qVec(quot_0) := signs(2) && ~signs(1) 424 qVec(quot_pos_1) := signs(3) && ~signs(2) && ~signs(1) 425 qVec(quot_pos_2) := ~signs(3) && ~signs(2) && ~signs(1) 426 io.qIterEnd := qVec.asUInt 427 // assert(PopCount(qVec) === 1.U) 428} 429 430 431class SRT4Divider(len: Int)(implicit p: Parameters) extends AbstractDivider(len) { 432 433 val newReq = io.in.fire 434 435 val uop = io.in.bits.uop 436 val uopReg = RegEnable(uop, newReq) 437 val ctrlReg = RegEnable(ctrl, newReq) 438 439 val divDataModule = Module(new SRT4DividerDataModule(len)) 440 441 val kill_w = uop.robIdx.needFlush(io.redirectIn) 442 val kill_r = !divDataModule.io.in_ready && uopReg.robIdx.needFlush(io.redirectIn) 443 444 divDataModule.io.src(0) := io.in.bits.src(0) 445 divDataModule.io.src(1) := io.in.bits.src(1) 446 divDataModule.io.valid := io.in.valid 447 divDataModule.io.sign := sign 448 divDataModule.io.kill_w := kill_w 449 divDataModule.io.kill_r := kill_r 450 divDataModule.io.isHi := ctrlReg.isHi 451 divDataModule.io.isW := ctrlReg.isW 452 divDataModule.io.out_ready := io.out.ready 453 454 io.in.ready := divDataModule.io.in_ready 455 io.out.valid := divDataModule.io.out_valid 456 io.out.bits.data := divDataModule.io.out_data 457 io.out.bits.uop := uopReg 458} 459