未验证 提交 cba0c52f 编写于 作者: Y Yinan Xu 提交者: GitHub

Merge pull request #162 from RISCVERS/brq-opt

Optimize brq
......@@ -17,4 +17,27 @@ object PriorityEncoderDefault {
def apply(in: Seq[Bool], default: UInt): UInt = {
PriorityMuxDefault(in.zipWithIndex.map(x => x._1 -> x._2.U), default)
}
}
object PriorityMuxWithFlag {
def apply[T <: Data](in: Seq[(Bool, T)]): (T, Bool) = {
in.size match {
case 1 =>
(in.head._2, in.head._1)
case _ =>
val (d_tail, f_tail) = PriorityMuxWithFlag(in.tail)
val d_head = in.head._2
val f_head = in.head._1
(Mux(f_head, d_head, d_tail), f_head || f_tail)
}
}
}
object PriorityEncoderWithFlag {
def apply(in: Seq[Bool]): (UInt, Bool) = {
PriorityMuxWithFlag(in.zipWithIndex.map(x => x._1 -> x._2.U))
}
def apply(in: Bits): (UInt, Bool) = {
PriorityEncoderWithFlag(in.asBools())
}
}
\ No newline at end of file
......@@ -72,9 +72,6 @@ class BrqIO extends XSBundle{
class Brq extends XSModule {
val io = IO(new BrqIO)
def redirctWindowSize: Int = BrqSize/2
require(redirctWindowSize <= BrqSize && redirctWindowSize > 0)
class BrqEntry extends Bundle {
val ptrFlag = Bool()
val npc = UInt(VAddrBits.W)
......@@ -103,23 +100,42 @@ class Brq extends XSModule {
// dequeue
val headIdx = headPtr.value
var commitIdx = WireInit(headIdx)
def needCheckNext(idx: UInt): Bool = {
(stateQueue(idx).isWb && !brQueue(idx).misPred) || stateQueue(idx).isCommit
val skipMask = Cat(stateQueue.zipWithIndex.map({
case (s, i) => (s.isWb && !brQueue(i).misPred) || s.isCommit
}).reverse)
/*
example: headIdx = 2
headIdxOH = 00000100
headIdxMaskHI = 11111100
headIdxMaskLo = 00000011
skipMask = 00111101
commitIdxHi = 6
commitIdxLo = 0
commitIdx = 6
*/
val headIdxOH = UIntToOH(headIdx)
val headIdxMaskHiVec = Wire(Vec(BrqSize, Bool()))
for(i <- headIdxMaskHiVec.indices){
headIdxMaskHiVec(i) := { if(i==0) headIdxOH(i) else headIdxMaskHiVec(i-1) || headIdxOH(i) }
}
val headIdxMaskHi = headIdxMaskHiVec.asUInt()
val headIdxMaskLo = (~headIdxMaskHi).asUInt()
val commitIdxHi = PriorityEncoder((~skipMask).asUInt() & headIdxMaskHi)
val (commitIdxLo, findLo) = PriorityEncoderWithFlag((~skipMask).asUInt() & headIdxMaskLo)
var checkNext = WireInit(needCheckNext(headIdx))
val skipHi = (skipMask | headIdxMaskLo) === Fill(BrqSize, 1.U(1.W))
val useLo = skipHi && findLo
for(i <- 1 until redirctWindowSize){
val idx = commitIdx + i.U
val commitThis = checkNext && stateQueue(idx).isWb && brQueue(idx).misPred
commitIdx = Mux(commitThis,
idx,
commitIdx
val commitIdx = Mux(stateQueue(commitIdxHi).isWb && brQueue(commitIdxHi).misPred,
commitIdxHi,
Mux(useLo && stateQueue(commitIdxLo).isWb && brQueue(commitIdxLo).misPred,
commitIdxLo,
headIdx
)
checkNext = checkNext && needCheckNext(idx)
}
)
val commitIsHead = commitIdx===headIdx
val deqValid = !stateQueue(headIdx).isIdle && commitIsHead && brCommitCnt=/=0.U
......@@ -134,10 +150,16 @@ class Brq extends XSModule {
io.inOrderBrInfo.misPred := commitEntry.misPred
io.inOrderBrInfo.redirect := commitEntry.exuOut.redirect
// XSDebug(
// p"commitIdxHi:$commitIdxHi ${Binary(headIdxMaskHi)} ${Binary(skipMask)}\n"
// )
// XSDebug(
// p"commitIdxLo:$commitIdxLo ${Binary(headIdxMaskLo)} ${Binary(skipMask)}\n"
// )
XSDebug(p"headIdx:$headIdx commitIdx:$commitIdx\n")
XSDebug(p"headPtr:$headPtr tailPtr:$tailPtr\n")
XSDebug("")
stateQueue.map(s =>{
stateQueue.reverse.map(s =>{
XSDebug(false, s.isIdle, "-")
XSDebug(false, s.isWb, "w")
XSDebug(false, s.isCommit, "c")
......
......@@ -20,11 +20,11 @@ class BrqTest extends FlatSpec
with ParallelTestExecution
with HasPartialDecoupledDriver {
it should "redirect out-of-order, dequeue in-order" in {
XSLog.generateLog = false
XSLog.generateLog = true
test(new Brq {
AddSinks()
}).withAnnotations(Seq(VerilatorBackendAnnotation)) { c =>
}).withAnnotations(Seq()) { c =>
def genEnqReq(x: => DecoupledIO[CfCtrl], pc: Long) = {
chiselTypeOf(x.bits).Lit(
......@@ -51,7 +51,7 @@ class BrqTest extends FlatSpec
}
var enqTags = List.tabulate(10)(i => i)
val misPred = Random.nextInt(10)
val misPred = 6
println(s"enqTags:$enqTags misPredTag:$misPred")
enqTags = enqTags.take(misPred + 1)
var commitTags, deqTags = List[Int]()
......@@ -91,6 +91,8 @@ class BrqTest extends FlatSpec
}
}
c.io.bcommit.poke((misPred+1).U)
c.clock.step(1)
c.io.bcommit.poke(0.U)
while (deqTags.size != misPred+1) {
checkCommit
checkDeq
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册