From 26a692b997670736a30f1291c60cb40cfa858836 Mon Sep 17 00:00:00 2001 From: Yinan Xu Date: Fri, 15 Jan 2021 22:24:39 +0800 Subject: [PATCH] CtrlBlock,MemBlock: only writeback necessary exceptionVec from execution units --- .../xiangshan/backend/IntegerBlock.scala | 2 +- .../xiangshan/backend/decode/DecodeUnit.scala | 4 +- src/main/scala/xiangshan/backend/fu/CSR.scala | 32 ++++++---- .../scala/xiangshan/backend/roq/Roq.scala | 63 +++++++++---------- src/main/scala/xiangshan/mem/Memend.scala | 1 - .../xiangshan/mem/lsqueue/LoadQueue.scala | 19 ++---- .../xiangshan/mem/lsqueue/LoadQueueData.scala | 10 --- .../xiangshan/mem/lsqueue/StoreQueue.scala | 25 ++------ .../xiangshan/mem/pipeline/LoadUnit.scala | 13 ++-- 9 files changed, 71 insertions(+), 98 deletions(-) diff --git a/src/main/scala/xiangshan/backend/IntegerBlock.scala b/src/main/scala/xiangshan/backend/IntegerBlock.scala index f9b0eacc1..f860340be 100644 --- a/src/main/scala/xiangshan/backend/IntegerBlock.scala +++ b/src/main/scala/xiangshan/backend/IntegerBlock.scala @@ -236,4 +236,4 @@ class IntegerBlock rf.addr := wb.bits.uop.pdest rf.data := wb.bits.data } -} \ No newline at end of file +} diff --git a/src/main/scala/xiangshan/backend/decode/DecodeUnit.scala b/src/main/scala/xiangshan/backend/decode/DecodeUnit.scala index ada95ebed..f33751872 100644 --- a/src/main/scala/xiangshan/backend/decode/DecodeUnit.scala +++ b/src/main/scala/xiangshan/backend/decode/DecodeUnit.scala @@ -386,10 +386,8 @@ class DecodeUnit extends XSModule with DecodeUnitConstants { cs.ldest := Mux(cs.fpWen || cs.rfWen, ctrl_flow.instr(RD_MSB,RD_LSB), 0.U) // fill in exception vector - cf_ctrl.cf.exceptionVec := DontCare + cf_ctrl.cf.exceptionVec := io.enq.ctrl_flow.exceptionVec cf_ctrl.cf.exceptionVec(illegalInstr) := cs.selImm === SelImm.INVALID_INSTR - cf_ctrl.cf.exceptionVec(instrPageFault) := io.enq.ctrl_flow.exceptionVec(instrPageFault) - cf_ctrl.cf.exceptionVec(instrAccessFault) := io.enq.ctrl_flow.exceptionVec(instrAccessFault) // fix frflags // fflags zero csrrs rd csr diff --git a/src/main/scala/xiangshan/backend/fu/CSR.scala b/src/main/scala/xiangshan/backend/fu/CSR.scala index c44d89dfd..b841c6a15 100644 --- a/src/main/scala/xiangshan/backend/fu/CSR.scala +++ b/src/main/scala/xiangshan/backend/fu/CSR.scala @@ -72,31 +72,37 @@ trait HasExceptionNO { ) val atomicsUnitSet = (loadUnitSet ++ storeUnitSet).distinct val allPossibleSet = (frontendSet ++ csrSet ++ loadUnitSet ++ storeUnitSet).distinct - def partialSelect(vec: Vec[Bool], select: Seq[Int], dontCareBits: Boolean = true): Vec[Bool] = { + def partialSelect(vec: Vec[Bool], select: Seq[Int], dontCareBits: Boolean = true, falseBits: Boolean = false): Vec[Bool] = { if (dontCareBits) { val new_vec = Wire(ExceptionVec()) new_vec := DontCare select.map(i => new_vec(i) := vec(i)) return new_vec } + else if (falseBits) { + val new_vec = Wire(ExceptionVec()) + new_vec.map(_ := false.B) + select.map(i => new_vec(i) := vec(i)) + return new_vec + } else { val new_vec = Wire(Vec(select.length, Bool())) select.zipWithIndex.map{ case(s, i) => new_vec(i) := vec(s) } return new_vec } } - def selectFrontend(vec: Vec[Bool], dontCareBits: Boolean = true): Vec[Bool] = - partialSelect(vec, frontendSet, dontCareBits) - def selectCSR(vec: Vec[Bool], dontCareBits: Boolean = true): Vec[Bool] = - partialSelect(vec, csrSet, dontCareBits) - def selectLoad(vec: Vec[Bool], dontCareBits: Boolean = true): Vec[Bool] = - partialSelect(vec, loadUnitSet, dontCareBits) - def selectStore(vec: Vec[Bool], dontCareBits: Boolean = true): Vec[Bool] = - partialSelect(vec, storeUnitSet, dontCareBits) - def selectAtomics(vec: Vec[Bool], dontCareBits: Boolean = true): Vec[Bool] = - partialSelect(vec, atomicsUnitSet, dontCareBits) - def selectAll(vec: Vec[Bool], dontCareBits: Boolean = true): Vec[Bool] = - partialSelect(vec, allPossibleSet, dontCareBits) + def selectFrontend(vec: Vec[Bool], dontCareBits: Boolean = true, falseBits: Boolean = false): Vec[Bool] = + partialSelect(vec, frontendSet, dontCareBits, falseBits) + def selectCSR(vec: Vec[Bool], dontCareBits: Boolean = true, falseBits: Boolean = false): Vec[Bool] = + partialSelect(vec, csrSet, dontCareBits, falseBits) + def selectLoad(vec: Vec[Bool], dontCareBits: Boolean = true, falseBits: Boolean = false): Vec[Bool] = + partialSelect(vec, loadUnitSet, dontCareBits, falseBits) + def selectStore(vec: Vec[Bool], dontCareBits: Boolean = true, falseBits: Boolean = false): Vec[Bool] = + partialSelect(vec, storeUnitSet, dontCareBits, falseBits) + def selectAtomics(vec: Vec[Bool], dontCareBits: Boolean = true, falseBits: Boolean = false): Vec[Bool] = + partialSelect(vec, atomicsUnitSet, dontCareBits, falseBits) + def selectAll(vec: Vec[Bool], dontCareBits: Boolean = true, falseBits: Boolean = false): Vec[Bool] = + partialSelect(vec, allPossibleSet, dontCareBits, falseBits) } class FpuCsrIO extends XSBundle { diff --git a/src/main/scala/xiangshan/backend/roq/Roq.scala b/src/main/scala/xiangshan/backend/roq/Roq.scala index 7e7948325..cabdf6f4c 100644 --- a/src/main/scala/xiangshan/backend/roq/Roq.scala +++ b/src/main/scala/xiangshan/backend/roq/Roq.scala @@ -54,12 +54,9 @@ class RoqEnqIO extends XSBundle { class RoqDispatchData extends RoqCommitInfo { val crossPageIPFFix = Bool() - val exceptionVec = ExceptionVec() } class RoqWbData extends XSBundle { - // mostly for exceptions - val exceptionVec = ExceptionVec() val fflags = UInt(5.W) val flushPipe = Bool() } @@ -265,30 +262,8 @@ class Roq(numWbPorts: Int) extends XSModule with HasCircularQueuePtrHelper { val writebackData = Module(new SyncDataModuleTemplate(new RoqWbData, RoqSize, CommitWidth, numWbPorts)) val writebackDataRead = writebackData.io.rdata - // val exceptionVecWritePortNum = RenameWidth + 1 + 2 + 2 // CSR, 2*load, 2*store - // val exceptionData = Module(new SyncDataModuleTemplate(ExceptionVec(), RoqSize, CommitWidth, exceptionVecWritePortNum)) - def mergeExceptionVec(dpData: RoqDispatchData, wbData: RoqWbData) = { - // these exceptions can be determined before dispatch. - // by default, let all exceptions be determined by dispatch. - // mergeVec(instrAddrMisaligned) := dpData(instrAddrMisaligned) - // mergeVec(instrAccessFault) := dpData(instrAccessFault) - // mergeVec(instrPageFault) := dpData(instrPageFault) - val mergeVec = WireInit(dpData.exceptionVec) - // these exceptions are determined in execution units - mergeVec(illegalInstr) := wbData.exceptionVec(illegalInstr) - mergeVec(breakPoint) := wbData.exceptionVec(breakPoint) - mergeVec(loadAddrMisaligned) := wbData.exceptionVec(loadAddrMisaligned) - mergeVec(loadAccessFault) := wbData.exceptionVec(loadAccessFault) - mergeVec(storeAddrMisaligned) := wbData.exceptionVec(storeAddrMisaligned) - mergeVec(storeAccessFault) := wbData.exceptionVec(storeAccessFault) - mergeVec(ecallU) := wbData.exceptionVec(ecallU) - mergeVec(ecallS) := wbData.exceptionVec(ecallS) - mergeVec(ecallM) := wbData.exceptionVec(ecallM) - mergeVec(loadPageFault) := wbData.exceptionVec(loadPageFault) - mergeVec(storePageFault) := wbData.exceptionVec(storePageFault) - // returns the merged exception vector - mergeVec - } + val exceptionVecWritePortNum = RenameWidth + 1 + 2 + 2 // CSR, 2*load, 2*store + val exceptionData = Module(new SyncDataModuleTemplate(ExceptionVec(), RoqSize, CommitWidth, exceptionVecWritePortNum)) io.roqDeqPtr := deqPtr @@ -360,7 +335,7 @@ class Roq(numWbPorts: Int) extends XSModule with HasCircularQueuePtrHelper { val deqWritebackData = writebackDataRead(0) val debug_deqUop = debug_microOp(deqPtr.value) - val deqExceptionVec = mergeExceptionVec(deqDispatchData, deqWritebackData) + val deqExceptionVec = exceptionData.io.rdata(0) // For MMIO instructions, they should not trigger interrupts since they may be sent to lower level before it writes back. // However, we cannot determine whether a load/store instruction is MMIO. // Thus, we don't allow load/store instructions to trigger an interrupt. @@ -422,7 +397,7 @@ class Roq(numWbPorts: Int) extends XSModule with HasCircularQueuePtrHelper { io.commits.isWalk := state =/= s_idle val commit_v = Mux(state === s_idle, VecInit(deqPtrVec.map(ptr => valid(ptr.value))), VecInit(walkPtrVec.map(ptr => valid(ptr.value)))) val commit_w = VecInit(deqPtrVec.map(ptr => writebacked(ptr.value))) - val commit_exception = dispatchDataRead.zip(writebackDataRead).map{ case (d, w) => mergeExceptionVec(d, w).asUInt.orR } + val commit_exception = exceptionData.io.rdata.map(_.asUInt.orR) val commit_block = VecInit((0 until CommitWidth).map(i => !commit_w(i) || commit_exception(i) || writebackDataRead(i).flushPipe)) for (i <- 0 until CommitWidth) { // defaults: state === s_idle and instructions commit @@ -496,7 +471,7 @@ class Roq(numWbPorts: Int) extends XSModule with HasCircularQueuePtrHelper { deqPtrGenModule.io.state := state deqPtrGenModule.io.deq_v := commit_v deqPtrGenModule.io.deq_w := commit_w - deqPtrGenModule.io.deq_exceptionVec := VecInit(dispatchDataRead.zip(writebackDataRead).map{ case (d, w) => mergeExceptionVec(d, w) }) + deqPtrGenModule.io.deq_exceptionVec := exceptionData.io.rdata deqPtrGenModule.io.deq_flushPipe := writebackDataRead.map(_.flushPipe) deqPtrGenModule.io.intrBitSetReg := intrBitSetReg deqPtrGenModule.io.hasNoSpecExec := hasNoSpecExec @@ -601,7 +576,7 @@ class Roq(numWbPorts: Int) extends XSModule with HasCircularQueuePtrHelper { // enqueue logic set 6 writebacked to false for (i <- 0 until RenameWidth) { when (canEnqueue(i)) { - writebacked(enqPtrVec(i).value) := false.B + writebacked(enqPtrVec(i).value) := selectFrontend(io.enq.req(i).bits.cf.exceptionVec, false).asUInt.orR } } // writeback logic set numWbPorts writebacked to true @@ -642,19 +617,41 @@ class Roq(numWbPorts: Int) extends XSModule with HasCircularQueuePtrHelper { wdata.sqIdx := req.sqIdx wdata.pc := req.cf.pc wdata.crossPageIPFFix := req.cf.crossPageIPFFix - wdata.exceptionVec := req.cf.exceptionVec + // wdata.exceptionVec := req.cf.exceptionVec } dispatchData.io.raddr := commitReadAddr_next writebackData.io.wen := io.exeWbResults.map(_.valid) writebackData.io.waddr := io.exeWbResults.map(_.bits.uop.roqIdx.value) writebackData.io.wdata.zip(io.exeWbResults.map(_.bits)).map{ case (wdata, wb) => - wdata.exceptionVec := wb.uop.cf.exceptionVec wdata.fflags := wb.fflags wdata.flushPipe := wb.uop.ctrl.flushPipe } writebackData.io.raddr := commitReadAddr_next + for (i <- 0 until RenameWidth) { + exceptionData.io.wen(i) := canEnqueue(i) + exceptionData.io.waddr(i) := enqPtrVec(i).value + exceptionData.io.wdata(i) := selectAll(io.enq.req(i).bits.cf.exceptionVec, false, true) + } + def connectWbExc(index: Int, i: Int) = { + exceptionData.io.wen(index) := io.exeWbResults(i).valid + exceptionData.io.waddr(index) := io.exeWbResults(i).bits.uop.roqIdx.value + } + // csr + connectWbExc(RenameWidth, 6) + exceptionData.io.wdata(RenameWidth) := selectCSR(io.exeWbResults(6).bits.uop.cf.exceptionVec) + // load + connectWbExc(RenameWidth+1, 4) + exceptionData.io.wdata(RenameWidth+1) := selectAtomics(io.exeWbResults(4).bits.uop.cf.exceptionVec) + connectWbExc(RenameWidth+2, 5) + exceptionData.io.wdata(RenameWidth+2) := selectAtomics(io.exeWbResults(5).bits.uop.cf.exceptionVec) + // store + connectWbExc(RenameWidth+3, 16) + exceptionData.io.wdata(RenameWidth+3) := selectStore(io.exeWbResults(16).bits.uop.cf.exceptionVec) + connectWbExc(RenameWidth+4, 17) + exceptionData.io.wdata(RenameWidth+4) := selectStore(io.exeWbResults(17).bits.uop.cf.exceptionVec) + exceptionData.io.raddr := VecInit(deqPtrVec_next.map(_.value)) /** * debug info diff --git a/src/main/scala/xiangshan/mem/Memend.scala b/src/main/scala/xiangshan/mem/Memend.scala index fa30d9f89..b750cc30a 100644 --- a/src/main/scala/xiangshan/mem/Memend.scala +++ b/src/main/scala/xiangshan/mem/Memend.scala @@ -41,7 +41,6 @@ class LsPipelineBundle extends XSBundle { val miss = Bool() val tlbMiss = Bool() val mmio = Bool() - val rollback = Bool() val forwardMask = Vec(8, Bool()) val forwardData = Vec(8, UInt(8.W)) diff --git a/src/main/scala/xiangshan/mem/lsqueue/LoadQueue.scala b/src/main/scala/xiangshan/mem/lsqueue/LoadQueue.scala index 4806955c5..5fc766b99 100644 --- a/src/main/scala/xiangshan/mem/lsqueue/LoadQueue.scala +++ b/src/main/scala/xiangshan/mem/lsqueue/LoadQueue.scala @@ -152,7 +152,7 @@ class LoadQueue extends XSModule vaddrModule.io.wen(i) := false.B when(io.loadIn(i).fire()) { when(io.loadIn(i).bits.miss) { - XSInfo(io.loadIn(i).valid, "load miss write to lq idx %d pc 0x%x vaddr %x paddr %x data %x mask %x forwardData %x forwardMask: %x mmio %x roll %x exc %x\n", + XSInfo(io.loadIn(i).valid, "load miss write to lq idx %d pc 0x%x vaddr %x paddr %x data %x mask %x forwardData %x forwardMask: %x mmio %x\n", io.loadIn(i).bits.uop.lqIdx.asUInt, io.loadIn(i).bits.uop.cf.pc, io.loadIn(i).bits.vaddr, @@ -161,12 +161,10 @@ class LoadQueue extends XSModule io.loadIn(i).bits.mask, io.loadIn(i).bits.forwardData.asUInt, io.loadIn(i).bits.forwardMask.asUInt, - io.loadIn(i).bits.mmio, - io.loadIn(i).bits.rollback, - io.loadIn(i).bits.uop.cf.exceptionVec.asUInt + io.loadIn(i).bits.mmio ) }.otherwise { - XSInfo(io.loadIn(i).valid, "load hit write to cbd lqidx %d pc 0x%x vaddr %x paddr %x data %x mask %x forwardData %x forwardMask: %x mmio %x roll %x exc %x\n", + XSInfo(io.loadIn(i).valid, "load hit write to cbd lqidx %d pc 0x%x vaddr %x paddr %x data %x mask %x forwardData %x forwardMask: %x mmio %x\n", io.loadIn(i).bits.uop.lqIdx.asUInt, io.loadIn(i).bits.uop.cf.pc, io.loadIn(i).bits.vaddr, @@ -175,9 +173,7 @@ class LoadQueue extends XSModule io.loadIn(i).bits.mask, io.loadIn(i).bits.forwardData.asUInt, io.loadIn(i).bits.forwardMask.asUInt, - io.loadIn(i).bits.mmio, - io.loadIn(i).bits.rollback, - io.loadIn(i).bits.uop.cf.exceptionVec.asUInt + io.loadIn(i).bits.mmio ) } val loadWbIndex = io.loadIn(i).bits.uop.lqIdx.value @@ -189,7 +185,6 @@ class LoadQueue extends XSModule loadWbData.mask := io.loadIn(i).bits.mask loadWbData.data := io.loadIn(i).bits.data // fwd data loadWbData.fwdMask := io.loadIn(i).bits.forwardMask - loadWbData.exception := selectLoad(io.loadIn(i).bits.uop.cf.exceptionVec) dataModule.io.wbWrite(i, loadWbIndex, loadWbData) dataModule.io.wb.wen(i) := true.B @@ -200,9 +195,8 @@ class LoadQueue extends XSModule debug_mmio(loadWbIndex) := io.loadIn(i).bits.mmio val dcacheMissed = io.loadIn(i).bits.miss && !io.loadIn(i).bits.mmio - val hasException = selectLoad(io.loadIn(i).bits.uop.cf.exceptionVec, false).asUInt.orR - miss(loadWbIndex) := dcacheMissed && !hasException - pending(loadWbIndex) := io.loadIn(i).bits.mmio && !hasException + miss(loadWbIndex) := dcacheMissed + pending(loadWbIndex) := io.loadIn(i).bits.mmio } } @@ -357,7 +351,6 @@ class LoadQueue extends XSModule // // Int load writeback will finish (if not blocked) in one cycle io.ldout(i).bits.uop := seluop - io.ldout(i).bits.uop.cf.exceptionVec := selectLoad(dataModule.io.wb.rdata(i).exception) io.ldout(i).bits.uop.lqIdx := loadWbSel(i).asTypeOf(new LqPtr) io.ldout(i).bits.data := rdataPartialLoad io.ldout(i).bits.redirectValid := false.B diff --git a/src/main/scala/xiangshan/mem/lsqueue/LoadQueueData.scala b/src/main/scala/xiangshan/mem/lsqueue/LoadQueueData.scala index ae2581c85..6f8593c0b 100644 --- a/src/main/scala/xiangshan/mem/lsqueue/LoadQueueData.scala +++ b/src/main/scala/xiangshan/mem/lsqueue/LoadQueueData.scala @@ -15,7 +15,6 @@ class LQDataEntry extends XSBundle { val paddr = UInt(PAddrBits.W) val mask = UInt(8.W) val data = UInt(XLEN.W) - val exception = ExceptionVec() val fwdMask = Vec(8, Bool()) } @@ -236,7 +235,6 @@ class LoadQueueData(size: Int, wbNumRead: Int, wbNumWrite: Int) extends XSModule // data module val paddrModule = Module(new PaddrModule(size, numRead = 3, numWrite = 2)) val maskModule = Module(new MaskModule(size, numRead = 3, numWrite = 2)) - val exceptionModule = Module(new AsyncDataModuleTemplate(ExceptionVec(), size, numRead = 3, numWrite = 2)) val coredataModule = Module(new CoredataModule(size, numRead = 3, numWrite = 3)) // read data @@ -244,26 +242,22 @@ class LoadQueueData(size: Int, wbNumRead: Int, wbNumWrite: Int) extends XSModule (0 until wbNumRead).map(i => { paddrModule.io.raddr(i) := io.wb.raddr(i) maskModule.io.raddr(i) := io.wb.raddr(i) - exceptionModule.io.raddr(i) := io.wb.raddr(i) coredataModule.io.raddr(i) := io.wb.raddr(i) io.wb.rdata(i).paddr := paddrModule.io.rdata(i) io.wb.rdata(i).mask := maskModule.io.rdata(i) io.wb.rdata(i).data := coredataModule.io.rdata(i) - io.wb.rdata(i).exception := exceptionModule.io.rdata(i) io.wb.rdata(i).fwdMask := DontCare }) // read port wbNumRead paddrModule.io.raddr(wbNumRead) := io.uncache.raddr maskModule.io.raddr(wbNumRead) := io.uncache.raddr - exceptionModule.io.raddr(wbNumRead) := io.uncache.raddr coredataModule.io.raddr(wbNumRead) := io.uncache.raddr io.uncache.rdata.paddr := paddrModule.io.rdata(wbNumRead) io.uncache.rdata.mask := maskModule.io.rdata(wbNumRead) io.uncache.rdata.data := coredataModule.io.rdata(wbNumRead) - io.uncache.rdata.exception := exceptionModule.io.rdata(wbNumRead) io.uncache.rdata.fwdMask := DontCare // write data @@ -271,19 +265,16 @@ class LoadQueueData(size: Int, wbNumRead: Int, wbNumWrite: Int) extends XSModule (0 until wbNumWrite).map(i => { paddrModule.io.wen(i) := false.B maskModule.io.wen(i) := false.B - exceptionModule.io.wen(i) := false.B coredataModule.io.wen(i) := false.B coredataModule.io.fwdMaskWen(i) := false.B coredataModule.io.paddrWen(i) := false.B paddrModule.io.waddr(i) := io.wb.waddr(i) maskModule.io.waddr(i) := io.wb.waddr(i) - exceptionModule.io.waddr(i) := io.wb.waddr(i) coredataModule.io.waddr(i) := io.wb.waddr(i) paddrModule.io.wdata(i) := io.wb.wdata(i).paddr maskModule.io.wdata(i) := io.wb.wdata(i).mask - exceptionModule.io.wdata(i) := io.wb.wdata(i).exception coredataModule.io.wdata(i) := io.wb.wdata(i).data coredataModule.io.fwdMaskWdata(i) := io.wb.wdata(i).fwdMask.asUInt coredataModule.io.paddrWdata(i) := io.wb.wdata(i).paddr @@ -291,7 +282,6 @@ class LoadQueueData(size: Int, wbNumRead: Int, wbNumWrite: Int) extends XSModule when(io.wb.wen(i)){ paddrModule.io.wen(i) := true.B maskModule.io.wen(i) := true.B - exceptionModule.io.wen(i) := true.B coredataModule.io.wen(i) := true.B coredataModule.io.fwdMaskWen(i) := true.B coredataModule.io.paddrWen(i) := true.B diff --git a/src/main/scala/xiangshan/mem/lsqueue/StoreQueue.scala b/src/main/scala/xiangshan/mem/lsqueue/StoreQueue.scala index f8cc98a17..ac154b836 100644 --- a/src/main/scala/xiangshan/mem/lsqueue/StoreQueue.scala +++ b/src/main/scala/xiangshan/mem/lsqueue/StoreQueue.scala @@ -52,8 +52,6 @@ class StoreQueue extends XSModule with HasDCacheParameters with HasCircularQueue dataModule.io := DontCare val vaddrModule = Module(new AsyncDataModuleTemplate(UInt(VAddrBits.W), StoreQueueSize, numRead = 1, numWrite = StorePipelineWidth)) vaddrModule.io := DontCare - val exceptionModule = Module(new AsyncDataModuleTemplate(ExceptionVec(), StoreQueueSize, numRead = StorePipelineWidth, numWrite = StorePipelineWidth)) - exceptionModule.io := DontCare // state & misc val allocated = RegInit(VecInit(List.fill(StoreQueueSize)(false.B))) // sq entry has been allocated @@ -83,7 +81,6 @@ class StoreQueue extends XSModule with HasDCacheParameters with HasCircularQueue dataModule.io.raddr(i) := deqPtrExt(i).value } vaddrModule.io.raddr(0) := io.exceptionAddr.lsIdx.sqIdx.value - exceptionModule.io.raddr(0) := deqPtr // read exception /** * Enqueue at dispatch @@ -123,14 +120,11 @@ class StoreQueue extends XSModule with HasDCacheParameters with HasCircularQueue for (i <- 0 until StorePipelineWidth) { dataModule.io.wen(i) := false.B vaddrModule.io.wen(i) := false.B - exceptionModule.io.wen(i) := false.B - when(io.storeIn(i).fire()) { + when (io.storeIn(i).fire()) { val stWbIndex = io.storeIn(i).bits.uop.sqIdx.value - val hasException = selectStore(io.storeIn(i).bits.uop.cf.exceptionVec, false).asUInt.orR - val hasWritebacked = !io.storeIn(i).bits.mmio || hasException - datavalid(stWbIndex) := hasWritebacked - writebacked(stWbIndex) := hasWritebacked - pending(stWbIndex) := !hasWritebacked // valid mmio require + datavalid(stWbIndex) := !io.storeIn(i).bits.mmio + writebacked(stWbIndex) := !io.storeIn(i).bits.mmio + pending(stWbIndex) := io.storeIn(i).bits.mmio val storeWbData = Wire(new SQDataEntry) storeWbData := DontCare @@ -145,21 +139,15 @@ class StoreQueue extends XSModule with HasDCacheParameters with HasCircularQueue vaddrModule.io.wdata(i) := io.storeIn(i).bits.vaddr vaddrModule.io.wen(i) := true.B - exceptionModule.io.waddr(i) := stWbIndex - exceptionModule.io.wdata(i) := selectStore(io.storeIn(i).bits.uop.cf.exceptionVec) - exceptionModule.io.wen(i) := true.B - mmio(stWbIndex) := io.storeIn(i).bits.mmio - XSInfo("store write to sq idx %d pc 0x%x vaddr %x paddr %x data %x mmio %x roll %x exc %x\n", + XSInfo("store write to sq idx %d pc 0x%x vaddr %x paddr %x data %x mmio %x\n", io.storeIn(i).bits.uop.sqIdx.value, io.storeIn(i).bits.uop.cf.pc, io.storeIn(i).bits.vaddr, io.storeIn(i).bits.paddr, io.storeIn(i).bits.data, - io.storeIn(i).bits.mmio, - io.storeIn(i).bits.rollback, - io.storeIn(i).bits.uop.cf.exceptionVec.asUInt + io.storeIn(i).bits.mmio ) } } @@ -258,7 +246,6 @@ class StoreQueue extends XSModule with HasDCacheParameters with HasCircularQueue io.mmioStout.valid := allocated(deqPtr) && datavalid(deqPtr) && !writebacked(deqPtr) io.mmioStout.bits.uop := uop(deqPtr) io.mmioStout.bits.uop.sqIdx := deqPtrExt(0) - io.mmioStout.bits.uop.cf.exceptionVec := selectStore(exceptionModule.io.rdata(0)) io.mmioStout.bits.data := dataModuleRead(0).data // dataModuleRead.read(deqPtr) io.mmioStout.bits.redirectValid := false.B io.mmioStout.bits.redirect := DontCare diff --git a/src/main/scala/xiangshan/mem/pipeline/LoadUnit.scala b/src/main/scala/xiangshan/mem/pipeline/LoadUnit.scala index f1720dc4f..b07294326 100644 --- a/src/main/scala/xiangshan/mem/pipeline/LoadUnit.scala +++ b/src/main/scala/xiangshan/mem/pipeline/LoadUnit.scala @@ -191,7 +191,9 @@ class LoadUnit_S2 extends XSModule with HasLoadHelper { // so we do not need to care about flush in load / store unit's out.valid io.out.bits := io.in.bits io.out.bits.data := rdataPartialLoad - io.out.bits.miss := s2_cache_miss && !fullForward + // when exception occurs, set it to not miss and let it write back to roq (via int port) + io.out.bits.miss := s2_cache_miss && !fullForward && !s2_exception + io.out.bits.uop.ctrl.fpWen := io.in.bits.uop.ctrl.fpWen && !s2_exception io.out.bits.mmio := s2_mmio io.in.ready := io.out.ready || !io.in.valid @@ -268,13 +270,14 @@ class LoadUnit extends XSModule with HasLoadHelper { // Load queue will be updated at s2 for both hit/miss int/fp load io.lsq.loadIn.valid := load_s2.io.out.valid io.lsq.loadIn.bits := load_s2.io.out.bits - val s2_exception = selectLoad(load_s2.io.out.bits.uop.cf.exceptionVec, false).asUInt.orR - val s2Valid = load_s2.io.out.valid && (!load_s2.io.out.bits.miss || s2_exception) + + // write to rob and writeback bus + val s2_wb_valid = load_s2.io.out.valid && !load_s2.io.out.bits.miss val refillFpLoad = io.lsq.ldout.bits.uop.ctrl.fpWen // Int load, if hit, will be writebacked at s2 val intHitLoadOut = Wire(Valid(new ExuOutput)) - intHitLoadOut.valid := s2Valid && !load_s2.io.out.bits.uop.ctrl.fpWen + intHitLoadOut.valid := s2_wb_valid && !load_s2.io.out.bits.uop.ctrl.fpWen intHitLoadOut.bits.uop := load_s2.io.out.bits.uop intHitLoadOut.bits.data := load_s2.io.out.bits.data intHitLoadOut.bits.redirectValid := false.B @@ -291,7 +294,7 @@ class LoadUnit extends XSModule with HasLoadHelper { // Fp load, if hit, will be send to recoder at s2, then it will be recoded & writebacked at s3 val fpHitLoadOut = Wire(Valid(new ExuOutput)) - fpHitLoadOut.valid := s2Valid && load_s2.io.out.bits.uop.ctrl.fpWen + fpHitLoadOut.valid := s2_wb_valid && load_s2.io.out.bits.uop.ctrl.fpWen fpHitLoadOut.bits := intHitLoadOut.bits val fpLoadOut = Wire(Valid(new ExuOutput)) -- GitLab