From 449070e347ca6ef6a6e23ea94bf694afcc0d5e37 Mon Sep 17 00:00:00 2001 From: Franz Fuchs Date: Mon, 8 Apr 2024 10:59:33 +0100 Subject: [PATCH] Copied over preliminary Konata support from https://github.com/bluespec/Toooba/commit/89b0c37a7b28066f2852e1eb46d174bf8e2b130e The referenced commit did not merge well with our code base. Therefore, I copied over the changes manually. These changes do not constitute a working Konata support for Toooba. In this commit, I commented out some things that did not compile, which will be fixed in future --- .../RISCY_OOO/procs/RV64G_OOO/FetchStage.bsv | 117 +++++++++++++++++- .../RISCY_OOO/procs/RV64G_OOO/RenameStage.bsv | 40 +++++- .../RISCY_OOO/procs/lib/ReorderBuffer.bsv | 37 ++++++ 3 files changed, 190 insertions(+), 4 deletions(-) diff --git a/src_Core/RISCY_OOO/procs/RV64G_OOO/FetchStage.bsv b/src_Core/RISCY_OOO/procs/RV64G_OOO/FetchStage.bsv index a99974a..8acba4c 100644 --- a/src_Core/RISCY_OOO/procs/RV64G_OOO/FetchStage.bsv +++ b/src_Core/RISCY_OOO/procs/RV64G_OOO/FetchStage.bsv @@ -195,6 +195,9 @@ typedef struct { Maybe#(PcCompressed) pred_next_pc; Bool decode_epoch; Epoch main_epoch; +`ifdef KONATA + Bit#(64) u_id; +`endif } Fetch1ToFetch2 deriving(Bits, Eq, FShow); typedef struct { @@ -208,6 +211,9 @@ typedef struct { Bool access_mmio; // inst fetch from MMIO Bool decode_epoch; Epoch main_epoch; +`ifdef KONATA + Bit#(64) u_id; +`endif } Fetch2ToFetch3 deriving(Bits, Eq, FShow); typedef struct { @@ -220,6 +226,9 @@ typedef struct { `ifdef RVFI_DII Dii_Parcel_Id dii_pid; `endif +`ifdef KONATA + Bit#(64) u_id; +`endif } Fetch3ToDecode deriving(Bits, Eq, FShow); // Used purely internally in doDecode. @@ -238,6 +247,9 @@ typedef struct { Maybe#(Exception) cause; Bool cause_second_half; Bool mispred_first_half; +`ifdef KONATA + Bit#(64) u_id; +`endif } InstrFromFetch3 deriving(Bits, Eq, FShow); function Bool popInst(DecodeResult dr); @@ -284,6 +296,9 @@ function InstrFromFetch3 fetch3_2_instC(Fetch3ToDecode in, Instruction inst, Bit cause: in.cause, cause_second_half: False, mispred_first_half: False +`ifdef KONATA + , u_id: in.u_id +`endif }; function InstrFromFetch3 fetch3s_2_inst(Fetch3ToDecode inHi, Fetch3ToDecode inLo); @@ -314,6 +329,9 @@ typedef struct { ArchRegs regs; Maybe#(Exception) cause; Addr tval; // in case of exception +`ifdef KONATA + Bit#(64) u_id; +`endif } FromFetchStage deriving (Bits, Eq, FShow); // train next addr pred (BTB) @@ -470,6 +488,22 @@ module mkFetchStage(FetchStage); `ifdef PERFORMANCE_MONITORING Reg#(Bool) redirect_evt_reg <- mkDReg(False); `endif +`ifdef KONATA + Reg#(Bit#(64)) uid <- mkReg(0); + Reg#(Bool) k_reset <- mkReg(True); + + rule header(k_reset); + k_reset <= ! k_reset; + $display("KONATAKanata\t0004"); + $display("KONATAC=\t0"); + $fflush; + endrule + + rule displayCycle; + $display("KONATAC\t1"); + $fflush; + endrule +`endif rule updatePcInBtb; nextAddrPred.put_pc(pc_reg[pc_final_port]); @@ -520,10 +554,24 @@ module mkFetchStage(FetchStage); pred_next_pc: isValid(pred_next_pc) ? Valid(compressPc(ppc_idx, validValue(pred_next_pc))) : Invalid, decode_epoch: decode_epoch[0], - main_epoch: f_main_epoch}; + main_epoch: f_main_epoch +`ifdef KONATA + , u_id: uid +`endif + }; f12f2.enq(out); if (verbose) $display("%d Fetch1: ", cur_cycle, fshow(out), " posLastSupX2: %d", posLastSupX2); +`ifdef KONATA + Bit#(TAdd#(TLog#(SupSizeX2),1)) posLastSupX2ex = zeroExtend(posLastSupX2); + uid <= uid + fromInteger(valueof(SupSizeX2)); + for (Integer i = 0; fromInteger(i) <= posLastSupX2ex; i = i+1) + begin + $display("KONATAI\t%0d\t%0d\t0", uid + fromInteger(i), uid + fromInteger(i)); + $display("KONATAS\t%0d\t0\tF1", uid + fromInteger(i)); + $fflush; + end +`endif endrule rule doFetch2; @@ -574,7 +622,11 @@ module mkFetchStage(FetchStage); cause: cause, access_mmio: access_mmio, decode_epoch: in.decode_epoch, - main_epoch: in.main_epoch }; + main_epoch: in.main_epoch +`ifdef KONATA + , u_id: in.u_id +`endif + }; f22f3.enq(out); if (verbosity >= 2) begin @@ -582,6 +634,16 @@ module mkFetchStage(FetchStage); $display ("Fetch2: TLB response pyhs_pc 0x%0h cause ", phys_pc, fshow (cause)); $display ("Fetch2: f2_tof3.enq: out ", fshow (out)); end +`ifdef KONATA + + Bit#(TAdd#(TLog#(SupSizeX2),1)) posLastSupX2ex = zeroExtend( in.inst_frags_fetched); + for (Integer i = 0; fromInteger(i) <= posLastSupX2ex; i = i+1) + begin + $display("KONATAE\t%0d\t0\tF1", in.u_id + fromInteger(i)); + $display("KONATAS\t%0d\t0\tF2", in.u_id + fromInteger(i)); + $fflush; + end +`endif endrule // Break out of i$ @@ -630,7 +692,15 @@ module mkFetchStage(FetchStage); cause: fetch3In.cause, decode_epoch: fetch3In.decode_epoch, main_epoch: fetch3In.main_epoch +`ifdef KONATA + , u_id: fetch3In.u_id + fromInteger(i) +`endif }); +`ifdef KONATA + $display("KONATAE\t%0d\t0\tF2", fetch3In.u_id + fromInteger(i)); + $display("KONATAS\t%0d\t0\tM", fetch3In.u_id + fromInteger(i)); + $fflush; +`endif end endrule: doFetch3 @@ -643,6 +713,12 @@ module mkFetchStage(FetchStage); if (f32d.deqS[i].canDeq &&& !isCurrent(f32d.deqS[i].first)) begin pcBlocks.rPort[i].remove(f32d.deqS[i].first.pc.idx); f32d.deqS[i].deq; +`ifdef KONATA + $display("KONATAL\t%0d\t0\tWrongPathDecode %x", f32d.deqS[i].first.u_id, f32d.deqS[i].first.pc); + $display("KONATAE\t%0d\t0\tM", f32d.deqS[i].first.u_id); + $display("KONATAR\t%0d\t%0d\t1\t//KILLDECODE", f32d.deqS[i].first.u_id, f32d.deqS[i].first.u_id); + $fflush; +`endif end endrule: doDecodeFlush @@ -661,7 +737,18 @@ module mkFetchStage(FetchStage); if (frags[i] matches tagged Valid .frag) begin Fetch3ToDecode prev_frag = (i != 0) ? validValue(frags[i-1]) : ?; if (prev_frag_available &&& !is_16b_inst(prev_frag.inst_frag)) begin // 2nd half of 32-bit instruction +//`ifdef KONATA +// $display("KONATAL\t%0d\t0\tBrought Fragment %x", prev_frag.u_id, prev_frag.pc); +// $display("KONATAE\t%0d\t0\tM", prev_frag.u_id); +// $display("KONATAR\t%0d\t%0d\t1\t//MERGE FRAGMENT", prev_frag.u_id, prev_frag.u_id ); +// $fflush; +//`endif new_pick = tagged Valid fetch3s_2_inst(frag, prev_frag); +//`ifdef KONATA +// $display("KONATAE\t%0d\t0\tM", fromMaybe(?,frags[i]).u_id); +// $display("KONATAS\t%0d\t0\tD", fromMaybe(?,frags[i]).u_id); +// $fflush; +//`endif /*if (!validValue(new_pick).mispred_first_half) begin doAssert(getAddr(decompressPc(prev_frag.pc))+2 == getAddr(decompressPc(frag.pc)), "Attached fragments with non-contigious PCs"); `ifdef RVFI_DII @@ -669,6 +756,11 @@ module mkFetchStage(FetchStage); `endif end*/ end else if (is_16b_inst(frag.inst_frag) || isValid(frag.cause)) begin // 16-bit instruction +//`ifdef KONATA +// $display("KONATAE\t%0d\t0\tM", fromMaybe(?,frags[i]).u_id); +// $display("KONATAS\t%0d\t0\tD", fromMaybe(?,frags[i]).u_id); +// $fflush; +//`endif new_pick = tagged Valid fetch3_2_instC(frag, fv_decode_C (misa, misa_mxl_64, getFlags(decompressPc(frag.pc))==1, frag.inst_frag), zeroExtend(frag.inst_frag)); @@ -751,6 +843,12 @@ module mkFetchStage(FetchStage); // We predicted a taken branch for PC, but this is an // uncompressed instruction, so we redirect to this PC and // train it to fetch the other half in future. +`ifdef KONATA + $display("KONATAE\t%0d\t0\tD", in.u_id); + $display("KONATAL\t%0d\t0\t%x ", in.u_id, pc); + $display("KONATAR\t%0d\t%0d\t1\t//depoch wrong", in.u_id, in.u_id); + $fflush; +`endif if (verbose) $display("mispredicted first half in decode: pc : %h", pc); decode_epoch_local = !decode_epoch_local; redirectPc = Valid (pc); // record redirect to the first PC in this bundle. @@ -842,6 +940,12 @@ module mkFetchStage(FetchStage); end // if (!isValid(cause)) if (isValid(m_push_addr)) trainInfo.ras = trainInfo.ras + 1; decode_pc_reg[i] <= getAddr(ppc); +`ifdef KONATA + $display("KONATAE\t%0d\t0\tD", in.u_id); + $display("KONATAL\t%0d\t0\t%x ", in.u_id, pc, fshow(dInst)); + $display("KONATAS\t%0d\t0\tRnm", in.u_id); + $fflush; +`endif let out = FromFetchStage{pc: pc, `ifdef RVFI_DII dii_pid: in.dii_pid, @@ -855,6 +959,9 @@ module mkFetchStage(FetchStage); regs: decode_result.regs, cause: cause, tval: getAddr(pc) + ((in.cause_second_half) ? 2:0) +`ifdef KONATA + , u_id : in.u_id +`endif }; out_fifo.enqS[i].enq(out); if (verbosity >= 1) begin @@ -866,6 +973,12 @@ module mkFetchStage(FetchStage); end end // if (in.decode_epoch == decode_epoch_local) else begin +`ifdef KONATA + $display("KONATAE\t%0d\t0\tD", in.u_id); + $display("KONATAL\t%0d\t0\t%x ", in.u_id, pc); + $display("KONATAR\t%0d\t%0d\t1\t//depoch wrong", in.u_id, in.u_id); + $fflush; +`endif if (verbose) $display("Drop decoded within a superscalar"); // just drop wrong path instructions end diff --git a/src_Core/RISCY_OOO/procs/RV64G_OOO/RenameStage.bsv b/src_Core/RISCY_OOO/procs/RV64G_OOO/RenameStage.bsv index 7405ef5..3eb5f11 100644 --- a/src_Core/RISCY_OOO/procs/RV64G_OOO/RenameStage.bsv +++ b/src_Core/RISCY_OOO/procs/RV64G_OOO/RenameStage.bsv @@ -230,6 +230,12 @@ module mkRenameStage#(RenameInput inIfc)(RenameStage); stop = True; end else begin +`ifdef KONATA + $display("KONATAE\t%d\t0\tRnm", x.u_id); + $display("KONATAL\t%0d\t0\tWrongPathRename %x", x.u_id, x.pc); + $display("KONATAR\t%d\t%d\t1\t//KILLRENAME", x.u_id, x.u_id); + $fflush; +`endif // wrong path, kill it & update prev epoch fetchStage.pipelines[i].deq; epochManager.updatePrevEpoch[i].update(x.main_epoch); @@ -388,9 +394,17 @@ module mkRenameStage#(RenameInput inIfc)(RenameStage); `endif `ifdef RVFI , traceBundle: unpack(0) +`endif +`ifdef KONATA + , u_id : x.u_id `endif }; rob.enqPort[0].enq(y); +`ifdef KONATA + $display("KONATAE\t%d\t0\tRnm", x.u_id); + $display("KONATAS\t%d\t0\tE", x.u_id); + $fflush; +`endif // record if we issue an interrupt if(firstTrap matches tagged Valid (tagged Interrupt .i)) begin inIfc.issueCsrInstOrInterrupt; @@ -602,10 +616,17 @@ module mkRenameStage#(RenameInput inIfc)(RenameStage); `endif `ifdef RVFI , traceBundle: unpack(0) +`endif +`ifdef KONATA + , u_id : x.u_id `endif }; rob.enqPort[0].enq(y); - +`ifdef KONATA + $display("KONATAE\t%d\t0\tRnm", x.u_id); + $display("KONATAS\t%d\t0\tE", x.u_id); + $fflush; +`endif `ifdef PERFORMANCE_MONITORING EventsTransExe events = unpack(0); events.evt_RENAMED_INST = 1; @@ -786,10 +807,18 @@ module mkRenameStage#(RenameInput inIfc)(RenameStage); spec_bits: spec_bits `ifdef RVFI_DII , dii_pid: x.dii_pid +`endif +`ifdef KONATA + , u_id : x.u_id `endif }; rob.enqPort[0].enq(y); +`ifdef KONATA + $display("KONATAE\t%d\t0\tRnm", x.u_id); + $display("KONATAS\t%d\t0\tE", x.u_id); + $fflush; +`endif `ifdef CHECK_DEADLOCK renameCorrectPath.send; `endif @@ -1153,10 +1182,17 @@ module mkRenameStage#(RenameInput inIfc)(RenameStage); `endif `ifdef RVFI , traceBundle: unpack(0) +`endif +`ifdef KONATA + , u_id : x.u_id `endif }; rob.enqPort[i].enq(y); - +`ifdef KONATA + $display("KONATAE\t%0d\t0\tRnm", x.u_id); + $display("KONATAS\t%0d\t0\tE", x.u_id); + $fflush; +`endif // record activity doCorrectPath = True; renameCnt = renameCnt + 1; diff --git a/src_Core/RISCY_OOO/procs/lib/ReorderBuffer.bsv b/src_Core/RISCY_OOO/procs/lib/ReorderBuffer.bsv index a96a64c..9f10087 100644 --- a/src_Core/RISCY_OOO/procs/lib/ReorderBuffer.bsv +++ b/src_Core/RISCY_OOO/procs/lib/ReorderBuffer.bsv @@ -117,6 +117,9 @@ typedef struct { `ifdef RVFI ExtraTraceBundle traceBundle; `endif +`ifdef KONATA + Bit#(64) u_id; +`endif } ToReorderBuffer deriving(Bits, FShow); typedef enum { @@ -282,6 +285,9 @@ module mkReorderBufferRowEhr(ReorderBufferRowEhr#(aluExeNum, fpuMulDivExeNum)) p `ifdef RVFI Ehr#(TAdd#(2, TAdd#(fpuMulDivExeNum, aluExeNum)), ExtraTraceBundle) traceBundle <- mkEhr(?); `endif +`ifdef KONATA + Reg#(Bit#(64)) uid <- mkReg(?); +`endif // wires to get stale (EHR port 0) values of PPC Wire#(CapMem) predPcWire <- mkBypassWire; @@ -409,6 +415,9 @@ module mkReorderBufferRowEhr(ReorderBufferRowEhr#(aluExeNum, fpuMulDivExeNum)) p method Action write_enq(ToReorderBuffer x); pc <= x.pc; +`ifdef KONATA + uid <= x.u_id; +`endif orig_inst <= x.orig_inst; iType <= x.iType; rg_dst_reg <= x.dst; @@ -482,6 +491,9 @@ module mkReorderBufferRowEhr(ReorderBufferRowEhr#(aluExeNum, fpuMulDivExeNum)) p traceBundle: traceBundle[traceBundle_deq_port], `endif spec_bits: spec_bits[sb_deq_port] +`ifdef KONATA + , u_id: uid +`endif }; endmethod @@ -692,6 +704,9 @@ module mkSupReorderBuffer#( Vector#(SupSize, Vector#(SingleScalarSize, Ehr#(2, Bool))) valid <- replicateM(replicateM(mkEhr(False))); Vector#(SupSize, Reg#(SingleScalarPtr)) enqP <- replicateM(mkReg(0)); Vector#(SupSize, Ehr#(2, SingleScalarPtr)) deqP_ehr <- replicateM(mkEhr(0)); +`ifdef KONATA + Vector#(SupSize, Vector#(SingleScalarSize, Ehr#(2, Bit#(64)))) uid <- replicateM(replicateM(mkEhr(0))); +`endif let deqP = getVEhrPort(deqP_ehr, 0); let deqP_wrongSpec = getVEhrPort(deqP_ehr, 1); // for overwrite deqP when killing all @@ -756,6 +771,11 @@ module mkSupReorderBuffer#( // move deqP & reset valid deqP[i] <= getNextPtr(deqP[i]); valid[i][deqP[i]][valid_deq_port] <= False; +`ifdef KONATA + let id = uid[i][deqP[i]][valid_deq_port]; + $display("KONATAR\t%0d\t%0d\t0", id, id); + $fflush; +`endif end end // update firstDeqWay: find the first deq port that is not enabled @@ -789,6 +809,13 @@ module mkSupReorderBuffer#( for(Integer w = 0; w < valueof(SupSize); w = w+1) begin for(Integer i = 0; i < valueof(SingleScalarSize); i = i+1) begin valid[w][i][valid_wrongSpec_port] <= False; +`ifdef KONATA + if (valid[w][i][valid_wrongSpec_port]) begin + $display("KONATAE\t%0d\t0\tE", uid[w][i][valid_wrongSpec_port]); + $display("KONATAR\t%0d\t%0d\t1\t//KILLALLROB", uid[w][i][valid_wrongSpec_port], uid[w][i][valid_wrongSpec_port]); + $fflush; + end +`endif end end // reset all ptrs to 0 @@ -810,6 +837,13 @@ module mkSupReorderBuffer#( for(Integer i = 0; i < valueof(SingleScalarSize); i = i+1) begin if(row[w][i].dependsOn_wrongSpec(specTag)) begin valid[w][i][valid_wrongSpec_port] <= False; +`ifdef KONATA + if (valid[w][i][valid_wrongSpec_port]) begin + $display("KONATAE\t%0d\t0\tE", uid[w][i][valid_wrongSpec_port]); + $display("KONATAR\t%0d\t%0d\t1\t//KILLMISPREDICTION", uid[w][i][valid_wrongSpec_port], uid[w][i][valid_wrongSpec_port]); + $fflush; + end +`endif end end end @@ -970,6 +1004,9 @@ module mkSupReorderBuffer#( enqP[i] <= getNextPtr(enqP[i]); row[i][enqP[i]].write_enq(x); valid[i][enqP[i]][valid_enq_port] <= True; +`ifdef KONATA + uid[i][enqP[i]][valid_enq_port] <= x.u_id; +`endif end end // update firstEnqWay: find the first enq port that is not enabled