Merge branch 'pdr32-wip' into HEAD

This commit is contained in:
Peter Rugg
2020-04-22 18:11:37 +01:00
12 changed files with 449 additions and 299 deletions

View File

@@ -140,10 +140,10 @@ module mkScrFile (ScrFile);
Reg#(CapReg) ddc_reg <- mkCsrReg(defaultValue);
// User level SCRs with accessSysRegs
Reg#(CapReg) utcc_reg <- mkCsrReg(defaultValue);
Reg#(CapReg) utdc_reg <- mkCsrReg(nullCap);
Reg#(CapReg) uScratchC_reg <- mkCsrReg(nullCap);
Reg#(CapReg) uepcc_reg <- mkCsrReg(defaultValue);
// Reg#(CapReg) utcc_reg <- mkCsrReg(defaultValue);
// Reg#(CapReg) utdc_reg <- mkCsrReg(nullCap);
// Reg#(CapReg) uScratchC_reg <- mkCsrReg(nullCap);
// Reg#(CapReg) uepcc_reg <- mkCsrReg(defaultValue);
// System level SCRs with accessSysRegs
Reg#(CapReg) stcc_reg <- mkCsrReg(defaultValue);
@@ -164,10 +164,10 @@ module mkScrFile (ScrFile);
SCR_PCC: pcc_reg[0];
SCR_DDC: ddc_reg;
// User CSRs with accessSysRegs
SCR_UTCC: utcc_reg;
SCR_UTDC: utdc_reg;
SCR_UScratchC: uScratchC_reg;
SCR_UEPCC: uepcc_reg;
// SCR_UTCC: utcc_reg;
// SCR_UTDC: utdc_reg;
// SCR_UScratchC: uScratchC_reg;
// SCR_UEPCC: uepcc_reg;
// System CSRs with accessSysRegs
SCR_STCC: stcc_reg;
SCR_STDC: stdc_reg;

View File

@@ -67,6 +67,9 @@ typedef struct {
CHERIException cheri_exc_code;
} CSR_XCapCause deriving(Bits, FShow);
CSR_XCapCause noCapCause = CSR_XCapCause {cheri_exc_code: None,
cheri_exc_reg: unpack(0)};
function Bit#(64) xccsr_to_word(CSR_XCapCause xccsr);
return zeroExtend({xccsr.cheri_exc_reg, pack(xccsr.cheri_exc_code), 3'b0, 1'b1, 1'b1});
endfunction
@@ -85,10 +88,10 @@ typedef enum {
SCR_PCC = 5'd00,
SCR_DDC = 5'd01,
SCR_UTCC = 5'd04,
SCR_UTDC = 5'd05,
SCR_UScratchC = 5'd06,
SCR_UEPCC = 5'd07,
// SCR_UTCC = 5'd04,
// SCR_UTDC = 5'd05,
// SCR_UScratchC = 5'd06,
// SCR_UEPCC = 5'd07,
SCR_STCC = 5'd12,
SCR_STDC = 5'd13,
@@ -98,8 +101,32 @@ typedef enum {
SCR_MTCC = 5'd28,
SCR_MTDC = 5'd29,
SCR_MScratchC = 5'd30,
SCR_MEPCC = 5'd31
} SCR deriving(Bits, Eq, FShow);
SCR_MEPCC = 5'd31,
// As with CSRs, SCR that catches all unimplemented SCRs
SCR_None = 5'd10
} SCR deriving(Bits, Eq, FShow, Bounded);
function SCR unpackSCR(Bit#(5) x);
return (case(x)
pack(SCR'(SCR_PCC )): (SCR_PCC );
pack(SCR'(SCR_DDC )): (SCR_DDC );
// pack(SCR'(SCR_UTCC )): (SCR_UTCC );
// pack(SCR'(SCR_UTDC )): (SCR_UTDC );
// pack(SCR'(SCR_UScratchC)): (SCR_UScratchC);
// pack(SCR'(SCR_UEPCC )): (SCR_UEPCC );
pack(SCR'(SCR_STCC )): (SCR_STCC );
pack(SCR'(SCR_STDC )): (SCR_STDC );
pack(SCR'(SCR_SScratchC)): (SCR_SScratchC);
pack(SCR'(SCR_SEPCC )): (SCR_SEPCC );
pack(SCR'(SCR_MTCC )): (SCR_MTCC );
pack(SCR'(SCR_MTDC )): (SCR_MTDC );
pack(SCR'(SCR_MScratchC)): (SCR_MScratchC);
pack(SCR'(SCR_MEPCC )): (SCR_MEPCC );
default : (SCR_None );
endcase);
endfunction
function CapPipe update_scr_via_csr (CapPipe old_scr, WordXL new_csr);
let new_scr = setOffset(old_scr, new_csr);

View File

@@ -89,7 +89,8 @@ typedef struct {
Maybe#(Data) csrData; // data to write CSR file
Maybe#(CapPipe) scrData; // datat to write to special capability register file.
ControlFlow controlFlow;
Maybe#(CHERIException) capException;
Maybe#(CSR_XCapCause) capException;
Maybe#(BoundsCheck) check;
// speculation
Maybe#(SpecTag) spec_tag;
`ifdef RVFI
@@ -157,7 +158,7 @@ interface AluExeInput;
Maybe#(Data) csrData,
Maybe#(CapPipe) scrData,
ControlFlow cf,
Maybe#(CHERIException) capCause,
Maybe#(CSR_XCapCause) capCause,
CapPipe pcc
`ifdef RVFI
, ExtraTraceBundle tb
@@ -256,6 +257,9 @@ module mkAluExePipeline#(AluExeInput inIfc)(AluExePipeline);
// get rVal2 (check bypass)
CapPipe rVal2 = nullCap;
if(x.dInst.scr matches tagged Valid .scr) begin
rVal2 = cast(inIfc.scaprf_rd(scr));
end
if(x.regs.src2 matches tagged Valid .src2 &&& src2 != 0) begin
rVal2 <- readRFBypass(src2, regsReady.src2, inIfc.rf_rd2(src2), bypassWire);
end
@@ -323,7 +327,8 @@ module mkAluExePipeline#(AluExeInput inIfc)(AluExePipeline);
// This means that we will have instructions that both write SCR registers and also get mispredictions, unlike
// the CSR file. Given the assertions above, this seems dangerous...
scrData: isValid(x.dInst.scr) ? Valid (exec_result.scrData) : tagged Invalid,
capException: isValid(exec_result.capException) ? (Valid (exec_result.capException.Valid.cheri_exc_code)) : Invalid,
capException: exec_result.capException,
check: exec_result.boundsCheck,
`ifdef RVFI
traceBundle: ExtraTraceBundle{
regWriteData: getAddr(exec_result.data),
@@ -349,6 +354,13 @@ module mkAluExePipeline#(AluExeInput inIfc)(AluExePipeline);
inIfc.writeRegFile(dst.indx, x.data);
end
if (x.check matches tagged Valid .check &&& x.capException matches tagged Invalid) begin
if (!( (check.check_low >= check.authority_base) &&
(check.check_inclusive ? (check.check_high <= check.authority_top )
: (check.check_high < check.authority_top ))))
x.capException = Valid(CSR_XCapCause{cheri_exc_reg: check.authority_idx, cheri_exc_code: LengthViolation});
end
// update the instruction in the reorder buffer.
inIfc.rob_setExecuted(
x.tag,

View File

@@ -358,7 +358,7 @@ module mkRenameStage#(RenameInput inIfc)(RenameStage);
// This avoids doing incorrect work
incrEpochStallFetch;
Maybe#(TrapWithCap) trapWithCap = Invalid;
if (firstTrap matches tagged Valid .trap) trapWithCap = tagged Valid TrapWithCap{trap: trap, capExp: None};
if (firstTrap matches tagged Valid .trap) trapWithCap = tagged Valid TrapWithCap{trap: trap, capExp: noCapCause};
// just place it in the reorder buffer
let y = ToReorderBuffer{pc: setAddr(almightyCap, pc).value,
orig_inst: orig_inst,

View File

@@ -0,0 +1,72 @@
// user standard CSRs
`CSR(CSRfflags , 12'h001)
`CSR(CSRfrm , 12'h002)
`CSR(CSRfcsr , 12'h003)
`CSR(CSRcycle , 12'hc00)
`CSR(CSRtime , 12'hc01)
`CSR(CSRinstret , 12'hc02)
// user non-standard CSRs (TODO)
`CSR(CSRterminate , 12'h800) // terminate (used to exit Linux)
`CSR(CSRstats , 12'h801) // turn on/off perf counters
// `CSR(CSRuccsr , 12'h8c0)
// supervisor standard `CSR(CSRs
`CSR(CSRsstatus , 12'h100)
// no user trap handler, so no se/ideleg
`CSR(CSRsie , 12'h104)
`CSR(CSRstvec , 12'h105)
`CSR(CSRscounteren , 12'h106)
`CSR(CSRsscratch , 12'h140)
`CSR(CSRsepc , 12'h141)
`CSR(CSRscause , 12'h142)
`CSR(CSRstval , 12'h143) // it's still called sbadaddr in spike
`CSR(CSRsip , 12'h144)
`CSR(CSRsatp , 12'h180) // it's still called sptbr in spike
`CSR(CSRsccsr , 12'h9c0)
// machine standard CSRs
`CSR(CSRmstatus , 12'h300)
`CSR(CSRmisa , 12'h301)
`CSR(CSRmedeleg , 12'h302)
`CSR(CSRmideleg , 12'h303)
`CSR(CSRmie , 12'h304)
`CSR(CSRmtvec , 12'h305)
`CSR(CSRmcounteren , 12'h306)
`CSR(CSRmscratch , 12'h340)
`CSR(CSRmepc , 12'h341)
`CSR(CSRmcause , 12'h342)
`CSR(CSRmtval , 12'h343) // it's still called mbadaddr in spike
`CSR(CSRmip , 12'h344)
`CSR(CSRmcycle , 12'hb00)
`CSR(CSRminstret , 12'hb02)
`CSR(CSRmvendorid , 12'hf11)
`CSR(CSRmarchid , 12'hf12)
`CSR(CSRmimpid , 12'hf13)
`CSR(CSRmhartid , 12'hf14)
`CSR(CSRmccsr , 12'hbc0)
`ifdef SECURITY
// sanctum machine CSR
`CSR(CSRmevbase , 12'h7c0)
`CSR(CSRmevmask , 12'h7c1)
`CSR(CSRmeatp , 12'h7c2)
`CSR(CSRmmrbm , 12'h7c3)
`CSR(CSRmemrbm , 12'h7c4)
`CSR(CSRmparbase , 12'h7c5)
`CSR(CSRmparmask , 12'h7c6)
`CSR(CSRmeparbase , 12'h7c7)
`CSR(CSRmeparmask , 12'h7c8)
`CSR(CSRmflush , 12'h7c9) // flush pipeline + cache
`CSR(CSRmspec , 12'h7ca) // control speculation
// sanctum user CSR
`CSR(CSRtrng , 12'hcc0) // random number for secure boot
`endif
`CSR(CSRtselect , 12'h7A0) // Debug/trace tselect
`CSR(CSRtdata1 , 12'h7A1) // Debug/trace tdata1
`CSR(CSRtdata2 , 12'h7A2) // Debug/trace tdata2
`CSR(CSRtdata3 , 12'h7A3) // Debug/trace tdata3
`ifdef INCLUDE_GDB_CONTROL
`CSR(CSRdcsr , 12'h7B0) // Debug control and status
`CSR(CSRdpc , 12'h7B1) // Debug PC
`CSR(CSRdscratch0 , 12'h7B2) // Debug scratch0
`CSR(CSRdscratch1 , 12'h7B3) // Debug scratch1
`endif

View File

@@ -0,0 +1,18 @@
`CAP_CHECK_FIELD(src1_tag,"src1_tag")
`CAP_CHECK_FIELD(src2_tag,"src2_tag")
`CAP_CHECK_FIELD(src1_sealed_with_type,"src1_sealed_with_type")
`CAP_CHECK_FIELD(src1_unsealed,"src1_unsealed")
`CAP_CHECK_FIELD(src2_unsealed,"src2_unsealed")
`CAP_CHECK_FIELD(src1_sealed,"src1_sealed")
`CAP_CHECK_FIELD(src2_sealed,"src2_sealed")
`CAP_CHECK_FIELD(src1_src2_types_match,"src1_src2_types_match")
`CAP_CHECK_FIELD(src1_permit_ccall,"src1_permit_ccall")
`CAP_CHECK_FIELD(src2_permit_ccall,"src2_permit_ccall")
`CAP_CHECK_FIELD(src1_permit_x,"src1_permit_x")
`CAP_CHECK_FIELD(src2_no_permit_x,"src2_no_permit_x")
`CAP_CHECK_FIELD(src2_permit_unseal,"src2_permit_unseal")
`CAP_CHECK_FIELD(src2_permit_seal,"src2_permit_seal")
`CAP_CHECK_FIELD(src2_points_to_src1_type,"src2_points_to_src1_type")
`CAP_CHECK_FIELD(src2_addr_valid_type,"src2_addr_valid_type")
`CAP_CHECK_FIELD(src1_perm_subset_src2,"src1_perm_subset_src2")
`CAP_CHECK_FIELD(src1_derivable,"src1_derivable")

View File

@@ -185,6 +185,7 @@ function DecodeResult decode(Instruction inst);
ImmData immB = signExtend({ inst[31], inst[7], inst[30:25], inst[11:8], 1'b0});
ImmData immU = signExtend({ inst[31:12], 12'b0 });
ImmData immJ = signExtend({ inst[31], inst[19:12], inst[20], inst[30:21], 1'b0});
ImmData immIunsigned = zeroExtend(inst[31:20]);
// Results of mini-decoders
Maybe#(MemInst) mem_inst = decodeMemInst(inst);
@@ -738,42 +739,76 @@ function DecodeResult decode(Instruction inst);
dInst.execFunc = CapModify (ModifyOffset (IncOffset));
end
f3_cap_CSetBoundsImmediate: begin
illegalInst = True;
// TODO
// dInst.capChecks.src1_tag = True;
// dInst.capChecks.src1_unsealed = True;
dInst.capChecks.src1_tag = True;
dInst.capChecks.src1_unsealed = True;
// regs.dst = Valid(tagged Gpr rd);
// regs.src1 = Valid(tagged Gpr rs1);
// regs.src1 = Invalid;
// dInst.imm = Valid (immI);
dInst.capChecks.check_enable = True;
dInst.capChecks.check_authority_src = Src1;
dInst.capChecks.check_low_src = Src1Addr;
dInst.capChecks.check_high_src = ResultTop;
dInst.capChecks.check_inclusive = True;
dInst.iType = Alu;
regs.dst = Valid(tagged Gpr rd);
regs.src1 = Valid(tagged Gpr rs1);
regs.src2 = Invalid;
dInst.imm = Valid (immIunsigned);
dInst.execFunc = CapModify (SetBounds (SetBounds));
end
f3_cap_ThreeOp: begin
case (funct7)
f7_cap_CSpecialRW: begin
// TODO
// TODO capChecks
dInst.iType = Alu;
regs.dst = Valid(tagged Gpr rd);
regs.src1 = Valid(tagged Gpr rs1);
regs.src2 = Invalid;
dInst.scr = Valid (unpackSCR(rs2));
let scrType = case (rs2[1:0])
0: TCC;
3: EPCC;
default: Normal;
endcase;
dInst.execFunc = CapModify (SpecialRW (scrType));
end
f7_cap_CSetBounds: begin
illegalInst = True;
// TODO
// dInst.capChecks.src1_tag = True;
// dInst.capChecks.src1_unsealed = True;
dInst.capChecks.src1_tag = True;
dInst.capChecks.src1_unsealed = True;
// regs.dst = Valid(tagged Gpr rd);
// regs.src1 = Valid(tagged Gpr rs1);
// regs.src2 = Valid(tagged Gpr rs2);
// dInst.imm = Invalid;
dInst.capChecks.check_enable = True;
dInst.capChecks.check_authority_src = Src1;
dInst.capChecks.check_low_src = Src1Addr;
dInst.capChecks.check_high_src = ResultTop;
dInst.capChecks.check_inclusive = True;
dInst.iType = Alu;
regs.dst = Valid(tagged Gpr rd);
regs.src1 = Valid(tagged Gpr rs1);
regs.src2 = Valid(tagged Gpr rs2);
dInst.imm = Invalid;
dInst.execFunc = CapModify (SetBounds (SetBounds));
end
f7_cap_CSetBoundsExact: begin
illegalInst = True;
// TODO
// dInst.capChecks.src1_tag = True;
// dInst.capChecks.src1_unsealed = True;
dInst.capChecks.src1_tag = True;
dInst.capChecks.src1_unsealed = True;
// TODO assert exact
// regs.dst = Valid(tagged Gpr rd);
// regs.src1 = Valid(tagged Gpr rs1);
// regs.src2 = Valid(tagged Gpr rs2);
// dInst.imm = Invalid;
dInst.capChecks.check_enable = True;
dInst.capChecks.check_authority_src = Src1;
dInst.capChecks.check_low_src = Src1Addr;
dInst.capChecks.check_high_src = ResultTop;
dInst.capChecks.check_inclusive = True;
dInst.iType = Alu;
regs.dst = Valid(tagged Gpr rd);
regs.src1 = Valid(tagged Gpr rs1);
regs.src2 = Valid(tagged Gpr rs2);
dInst.imm = Invalid;
dInst.execFunc = CapModify (SetBounds (SetBounds));
end
f7_cap_CSetOffset: begin
dInst.capChecks.src1_unsealed = True;
@@ -813,6 +848,12 @@ function DecodeResult decode(Instruction inst);
dInst.capChecks.src2_permit_seal = True;
dInst.capChecks.src2_addr_valid_type = True;
dInst.capChecks.check_enable = True;
dInst.capChecks.check_authority_src = Src2;
dInst.capChecks.check_low_src = Src2Addr;
dInst.capChecks.check_high_src = Src2Addr;
dInst.capChecks.check_inclusive = False;
dInst.iType = Alu;
regs.dst = Valid(tagged Gpr rd);
regs.src1 = Valid(tagged Gpr rs1);
@@ -857,6 +898,12 @@ function DecodeResult decode(Instruction inst);
dInst.capChecks.src2_points_to_src1_type = True;
dInst.capChecks.src2_permit_unseal = True;
dInst.capChecks.check_enable = True;
dInst.capChecks.check_authority_src = Src2;
dInst.capChecks.check_low_src = Src2Addr;
dInst.capChecks.check_high_src = Src2Addr;
dInst.capChecks.check_inclusive = False;
dInst.iType = Alu;
regs.dst = Valid(tagged Gpr rd);
regs.src1 = Valid(tagged Gpr rs1);
@@ -878,6 +925,12 @@ function DecodeResult decode(Instruction inst);
dInst.capChecks.src1_tag = True;
dInst.capChecks.src1_unsealed = True;
dInst.capChecks.check_enable = True;
dInst.capChecks.check_authority_src = Src1;
dInst.capChecks.check_low_src = Src2Type;
dInst.capChecks.check_high_src = Src2Type;
dInst.capChecks.check_inclusive = False;
dInst.iType = Alu;
regs.dst = Valid(tagged Gpr rd);
regs.src1 = Valid(tagged Gpr rs1);
@@ -913,7 +966,13 @@ function DecodeResult decode(Instruction inst);
dInst.iType = Alu;
regs.dst = Valid(tagged Gpr rd);
regs.src1 = Valid(tagged Gpr rs1);
regs.src2 = Valid(tagged Gpr rs2);
if (rs2 == 0) begin
regs.src2 = Invalid;
dInst.scr = Valid (SCR_DDC);
end else begin
regs.src2 = Valid (tagged Gpr rs2);
dInst.scr = Invalid;
end
dInst.imm = Invalid;
dInst.execFunc = CapInspect (ToPtr);
end
@@ -941,17 +1000,26 @@ function DecodeResult decode(Instruction inst);
dInst.execFunc = Alu (Sub);
end
f7_cap_CBuildCap: begin
illegalInst = True;
// TODO
dInst.capChecks.src1_tag = True;
dInst.capChecks.src1_unsealed = True;
dInst.capChecks.src2_perm_subset_src1 = True;
dInst.capChecks.src2_derivable = True;
dInst.capChecks.src2_tag = True;
dInst.capChecks.src2_unsealed = True;
dInst.capChecks.src1_perm_subset_src2 = True;
dInst.capChecks.src1_derivable = True;
dInst.capChecks.check_enable = True;
dInst.capChecks.check_authority_src = Src2;
dInst.capChecks.check_low_src = Src1Base;
dInst.capChecks.check_high_src = Src1Top;
dInst.capChecks.check_inclusive = True;
// Swap arguments so SCR possibly goes in RS2
dInst.iType = Alu;
regs.dst = Valid(tagged Gpr rd);
regs.src1 = Valid(tagged Gpr rs1);
regs.src2 = Valid(tagged Gpr rs2);
regs.src1 = Valid(tagged Gpr rs2);
if (rs1 == 0) begin
dInst.scr = Valid(SCR_DDC);
end else begin
regs.src2 = Valid(tagged Gpr rs1);
end
dInst.imm = Invalid;
dInst.execFunc = CapModify (BuildCap);
end
@@ -994,18 +1062,20 @@ function DecodeResult decode(Instruction inst);
dInst.execFunc = CapInspect (GetSealed);
end
f5rs2_cap_CRRL: begin
illegalInst = True;
// TODO
// regs.dst = Valid(tagged Gpr rd);
// regs.src1 = Valid(tagged Gpr rs1);
// dInst.imm = Invalid;
dInst.iType = Alu;
regs.dst = Valid(tagged Gpr rd);
regs.src1 = Valid(tagged Gpr 0); // Operate on nullcap
regs.src2 = Valid(tagged Gpr rs1);
dInst.imm = Invalid;
dInst.execFunc = CapModify (SetBounds (CRRL));
end
f5rs2_cap_CRAM: begin
illegalInst = True;
// TODO
// regs.dst = Valid(tagged Gpr rd);
// regs.src1 = Valid(tagged Gpr rs1);
// dInst.imm = Invalid;
dInst.iType = Alu;
regs.dst = Valid(tagged Gpr rd);
regs.src1 = Valid(tagged Gpr 0); // Operate on nullcap
regs.src2 = Valid(tagged Gpr rs1);
dInst.imm = Invalid;
dInst.execFunc = CapModify (SetBounds (CRAM));
end
f5rs2_cap_CMove: begin
dInst.iType = Alu;

View File

@@ -66,11 +66,49 @@ function Maybe#(CapException) capChecks(CapPipe a, CapPipe b, CapChecks toCheck)
result = e2(TypeViolation);
else if (toCheck.src2_addr_valid_type && !validAsType(b, truncate(getAddr(b))))
result = e2(LengthViolation);
else if (toCheck.src2_perm_subset_src1 && (getPerms(a) & getPerms(b)) != getPerms(b))
else if (toCheck.src1_perm_subset_src2 && (getPerms(a) & getPerms(b)) != getPerms(a))
result = e2(SoftwarePermViolation);
else if (toCheck.src1_derivable && !isDerivable(a))
result = e1(LengthViolation);
return result;
endfunction
(* noinline *)
function Maybe#(BoundsCheck) prepareBoundsCheck(CapPipe a, CapPipe b, CapChecks toCheck);
BoundsCheck ret = ?;
CapPipe authority = ?;
case(toCheck.check_authority_src)
Src1: begin
authority = a;
ret.authority_idx = toCheck.rn1;
end
Src2: begin
authority = b;
ret.authority_idx = toCheck.rn2;
end
endcase
ret.authority_base = getBase(authority);
ret.authority_top = getTop(authority);
case(toCheck.check_low_src)
Src1Addr: ret.check_low = getAddr(a);
Src1Base: ret.check_low = getBase(a);
Src2Addr: ret.check_low = getAddr(b);
Src2Type: ret.check_low = zeroExtend(getType(b));
endcase
case(toCheck.check_high_src)
Src1Top: ret.check_high = getTop(a);
Src2Addr: ret.check_high = {1'b0,getAddr(b)};
Src2Type: ret.check_high = zeroExtend(getType(b));
ResultTop: ret.check_high = {1'b0,getAddr(a)} + {1'b0,getAddr(b)};
endcase
ret.check_inclusive = toCheck.check_inclusive;
if (toCheck.check_enable) return Valid(ret);
else return Invalid;
endfunction
(* noinline *)
function Data alu(Data a, Data b, AluFunc func);
Data res = (case(func)
@@ -97,15 +135,27 @@ function Data alu(Data a, Data b, AluFunc func);
return res;
endfunction
(* noinline *)
function CapPipe setBoundsALU(CapPipe cap, Data len, SetBoundsFunc boundsOp);
let combinedResult = setBoundsCombined(cap, len);
CapPipe res = (case (boundsOp) matches
SetBounds: combinedResult.cap;
CRRL: nullWithAddr(combinedResult.length);
CRAM: nullWithAddr(combinedResult.mask);
endcase);
// TODO exfiltrate exact somehow...
return res;
endfunction
(* noinline *)
function CapPipe capModify(CapPipe a, CapPipe b, CapModifyFunc func);
CapPipe res = (case(func) matches
tagged ModifyOffset .offsetOp :
modifyOffset(a, getAddr(b), offsetOp == IncOffset).value;
tagged SetBounds .exact :
setBounds(a, getAddr(b)).value;
//tagged SpecialRW :
// error("SpecialRW not yet implemented");
tagged SetBounds .boundsOp :
setBoundsALU(a, getAddr(b), boundsOp);
tagged SpecialRW .scrType :
a; //TODO masking of various bits
tagged SetAddr .addrSource :
if (addrSource == Src2Type && !isSealed(b)) return nullWithAddr(-1);
else return setAddr(a, (addrSource == Src2Type) ? zeroExtend(getType(b)) : getAddr(b) ).value;
@@ -120,7 +170,7 @@ function CapPipe capModify(CapPipe a, CapPipe b, CapModifyFunc func);
//tagged FromPtr :
// error("FromPtr not yet implemented");
tagged BuildCap :
setValidCap(a, True);
setType(setValidCap(a, True),-1);
tagged Move :
a;
tagged ClearTag :
@@ -156,7 +206,7 @@ function Data capInspect(CapPipe a, CapPipe b, CapInspectFunc func);
tagged GetType :
signExtend(getType(a));
tagged ToPtr :
(getAddr(a) - getBase(b));
(isValidCap(a) ? (getAddr(a) - getBase(b)) : 0);
default: ?;
endcase);
return res;
@@ -233,7 +283,8 @@ function ExecResult basicExec(DecodedInst dInst, CapPipe rVal1, CapPipe rVal2, C
Data inspect_result = capInspect(rVal1, aluVal2, dInst.execFunc.CapInspect);
CapModifyFunc modFunc = ccall ? (Unseal (Src2)):dInst.execFunc.CapModify;
CapPipe modify_result = capModify(rVal1, aluVal2, modFunc);
Maybe#(CapException) capException = capChecks(rVal1, aluVal2, dInst.capChecks); // TODO use this to throw exceptions
Maybe#(CapException) capException = capChecks(rVal1, aluVal2, dInst.capChecks);
Maybe#(BoundsCheck) boundsCheck = prepareBoundsCheck(rVal1, aluVal2, dInst.capChecks);
CapPipe cap_alu_result = case (dInst.execFunc) matches tagged CapInspect .x: nullWithAddr(inspect_result);
tagged CapModify .x: modify_result;
@@ -258,7 +309,7 @@ function ExecResult basicExec(DecodedInst dInst, CapPipe rVal1, CapPipe rVal2, C
Jr &&& (ccall): cap_alu_result; // Depending on defaults falling through!
Jr &&& (cjalr): link_pcc;
Jr : nullWithAddr(getOffset(link_pcc));
Auipc : nullWithAddr(pc + fromMaybe(?, getDInstImm(dInst))); // could be computed with alu
Auipc : (getFlags(pcc)[0] == 1'b0 ? nullWithAddr(pc + fromMaybe(?, getDInstImm(dInst))) : modifyOffset(pcc, fromMaybe(?, getDInstImm(dInst)), True).value); // could be computed with alu
Csr : rVal1;
default : cap_alu_result;
endcase);
@@ -267,9 +318,9 @@ function ExecResult basicExec(DecodedInst dInst, CapPipe rVal1, CapPipe rVal2, C
Ld, St, Lr, Sc, Amo : nullWithAddr(alu_result);
default : nullWithAddr(cf.nextPc);
endcase);
CapPipe scr_data = rVal1;
CapPipe scr_data = modify_result;
return ExecResult{data: data, csrData: csr_data, scrData: scr_data, addr: addr, controlFlow: cf, capException: capException};
return ExecResult{data: data, csrData: csr_data, scrData: scr_data, addr: addr, controlFlow: cf, capException: capException, boundsCheck: boundsCheck};
endfunction
(* noinline *)

View File

@@ -0,0 +1,22 @@
`OPCODE(Load , 7'b0000011)
`OPCODE(LoadFp , 7'b0000111)
`OPCODE(MiscMem, 7'b0001111)
`OPCODE(OpImm , 7'b0010011)
`OPCODE(Auipc , 7'b0010111)
`OPCODE(OpImm32, 7'b0011011)
`OPCODE(Store , 7'b0100011)
`OPCODE(StoreFp, 7'b0100111)
`OPCODE(Amo , 7'b0101111)
`OPCODE(Op , 7'b0110011)
`OPCODE(Lui , 7'b0110111)
`OPCODE(Op32 , 7'b0111011)
`OPCODE(Fmadd , 7'b1000011)
`OPCODE(Fmsub , 7'b1000111)
`OPCODE(Fnmsub , 7'b1001011)
`OPCODE(Fnmadd , 7'b1001111)
`OPCODE(OpFp , 7'b1010011)
`OPCODE(OpCHERI, 7'b1011011)
`OPCODE(Branch , 7'b1100011)
`OPCODE(Jalr , 7'b1100111)
`OPCODE(Jal , 7'b1101111)
`OPCODE(System , 7'b1110011)

View File

@@ -171,212 +171,37 @@ function Bool allRegsReady(RegsReady x);
endfunction
typedef enum {
Invalid = 7'b0,
Load = 7'b0000011,
LoadFp = 7'b0000111,
MiscMem = 7'b0001111,
OpImm = 7'b0010011,
Auipc = 7'b0010111,
OpImm32 = 7'b0011011,
Store = 7'b0100011,
StoreFp = 7'b0100111,
Amo = 7'b0101111,
Op = 7'b0110011,
Lui = 7'b0110111,
Op32 = 7'b0111011,
Fmadd = 7'b1000011,
Fmsub = 7'b1000111,
Fnmsub = 7'b1001011,
Fnmadd = 7'b1001111,
OpFp = 7'b1010011,
OpCHERI = 7'b1011011,
Branch = 7'b1100011,
Jalr = 7'b1100111,
Jal = 7'b1101111,
System = 7'b1110011
`define OPCODE(o,v) o = v,
`include "Opcodes.bsvi"
`undef OPCODE
Invalid = 7'b0
} Opcode deriving(Bits, Eq, FShow);
function Opcode unpackOpcode(Bit#(7) x);
return (case(x)
pack(Opcode'(Load )): (Load );
pack(Opcode'(LoadFp )): (LoadFp );
pack(Opcode'(MiscMem)): (MiscMem);
pack(Opcode'(OpImm )): (OpImm );
pack(Opcode'(Auipc )): (Auipc );
pack(Opcode'(OpImm32)): (OpImm32);
pack(Opcode'(Store )): (Store );
pack(Opcode'(StoreFp)): (StoreFp);
pack(Opcode'(Amo )): (Amo );
pack(Opcode'(Op )): (Op );
pack(Opcode'(Lui )): (Lui );
pack(Opcode'(Op32 )): (Op32 );
pack(Opcode'(Fmadd )): (Fmadd );
pack(Opcode'(Fmsub )): (Fmsub );
pack(Opcode'(Fnmsub )): (Fnmsub );
pack(Opcode'(Fnmadd )): (Fnmadd );
pack(Opcode'(OpFp )): (OpFp );
pack(Opcode'(OpCHERI)): (OpCHERI);
pack(Opcode'(Branch )): (Branch );
pack(Opcode'(Jalr )): (Jalr );
pack(Opcode'(Jal )): (Jal );
pack(Opcode'(System )): (System );
default : (Invalid);
`define OPCODE(o,v) pack(Opcode'(o)): (o);
`include "Opcodes.bsvi"
`undef OPCODE
default : Invalid;
endcase);
endfunction
/* If Bluespec never allows illegal values of sparse enumerated types, this function should replace the one above:
function Opcode unpackOpcode(Bit#(7) x);
Opcode test = unpack(x);
if (pack(test) != x) return Invalid;
else return test;
endfunction
*/
typedef enum {
// user standard CSRs
CSRfflags = 12'h001,
CSRfrm = 12'h002,
CSRfcsr = 12'h003,
CSRcycle = 12'hc00,
CSRtime = 12'hc01,
CSRinstret = 12'hc02,
// user non-standard CSRs (TODO)
CSRterminate = 12'h800, // terminate (used to exit Linux)
CSRstats = 12'h801, // turn on/off perf counters
CSRuccsr = 12'h8c0,
// supervisor standard CSRs
CSRsstatus = 12'h100,
// no user trap handler, so no se/ideleg
CSRsie = 12'h104,
CSRstvec = 12'h105,
CSRscounteren = 12'h106,
CSRsscratch = 12'h140,
CSRsepc = 12'h141,
CSRscause = 12'h142,
CSRstval = 12'h143, // it's still called sbadaddr in spike
CSRsip = 12'h144,
CSRsatp = 12'h180, // it's still called sptbr in spike
CSRsccsr = 12'h9c0,
// machine standard CSRs
CSRmstatus = 12'h300,
CSRmisa = 12'h301,
CSRmedeleg = 12'h302,
CSRmideleg = 12'h303,
CSRmie = 12'h304,
CSRmtvec = 12'h305,
CSRmcounteren = 12'h306,
CSRmscratch = 12'h340,
CSRmepc = 12'h341,
CSRmcause = 12'h342,
CSRmtval = 12'h343, // it's still called mbadaddr in spike
CSRmip = 12'h344,
CSRmcycle = 12'hb00,
CSRminstret = 12'hb02,
CSRmvendorid = 12'hf11,
CSRmarchid = 12'hf12,
CSRmimpid = 12'hf13,
CSRmhartid = 12'hf14,
CSRmccsr = 12'hbc0,
`ifdef SECURITY
// sanctum machine CSR
CSRmevbase = 12'h7c0,
CSRmevmask = 12'h7c1,
CSRmeatp = 12'h7c2,
CSRmmrbm = 12'h7c3,
CSRmemrbm = 12'h7c4,
CSRmparbase = 12'h7c5,
CSRmparmask = 12'h7c6,
CSRmeparbase = 12'h7c7,
CSRmeparmask = 12'h7c8,
CSRmflush = 12'h7c9, // flush pipeline + cache
CSRmspec = 12'h7ca, // control speculation
// sanctum user CSR
CSRtrng = 12'hcc0, // random number for secure boot
`endif
CSRtselect = 12'h7A0, // Debug/trace tselect
CSRtdata1 = 12'h7A1, // Debug/trace tdata1
CSRtdata2 = 12'h7A2, // Debug/trace tdata2
CSRtdata3 = 12'h7A3, // Debug/trace tdata3
`ifdef INCLUDE_GDB_CONTROL
CSRdcsr = 12'h7B0, // Debug control and status
CSRdpc = 12'h7B1, // Debug PC
CSRdscratch0 = 12'h7B2, // Debug scratch0
CSRdscratch1 = 12'h7B3, // Debug scratch1
`endif
`define CSR(c,v) c = v,
`include "CSRs.bsvi"
`undef CSR
// CSR that catches all the unimplemented CSRs. To avoid exception on this,
// make it a user non-standard read/write CSR.
// Bluespec: in RenameStage.getTrap(), we force this to be a csr_access_trap
CSRnone = 12'h8ff
CSRnone = 12'h8ff
} CSR deriving(Bits, Eq, FShow);
function CSR unpackCSR(Bit#(12) x);
return (case(x)
pack(CSR'(CSRfflags )): (CSRfflags );
pack(CSR'(CSRfrm )): (CSRfrm );
pack(CSR'(CSRfcsr )): (CSRfcsr );
pack(CSR'(CSRcycle )): (CSRcycle );
pack(CSR'(CSRtime )): (CSRtime );
pack(CSR'(CSRinstret )): (CSRinstret );
pack(CSR'(CSRterminate )): (CSRterminate );
pack(CSR'(CSRstats )): (CSRstats );
pack(CSR'(CSRsstatus )): (CSRsstatus );
pack(CSR'(CSRsie )): (CSRsie );
pack(CSR'(CSRstvec )): (CSRstvec );
pack(CSR'(CSRscounteren)): (CSRscounteren);
pack(CSR'(CSRsscratch )): (CSRsscratch );
pack(CSR'(CSRsepc )): (CSRsepc );
pack(CSR'(CSRscause )): (CSRscause );
pack(CSR'(CSRstval )): (CSRstval );
pack(CSR'(CSRsip )): (CSRsip );
pack(CSR'(CSRsatp )): (CSRsatp );
pack(CSR'(CSRmstatus )): (CSRmstatus );
pack(CSR'(CSRmisa )): (CSRmisa );
pack(CSR'(CSRmedeleg )): (CSRmedeleg );
pack(CSR'(CSRmideleg )): (CSRmideleg );
pack(CSR'(CSRmie )): (CSRmie );
pack(CSR'(CSRmtvec )): (CSRmtvec );
pack(CSR'(CSRmcounteren)): (CSRmcounteren);
pack(CSR'(CSRmscratch )): (CSRmscratch );
pack(CSR'(CSRmepc )): (CSRmepc );
pack(CSR'(CSRmcause )): (CSRmcause );
pack(CSR'(CSRmtval )): (CSRmtval );
pack(CSR'(CSRmip )): (CSRmip );
pack(CSR'(CSRmcycle )): (CSRmcycle );
pack(CSR'(CSRminstret )): (CSRminstret );
pack(CSR'(CSRmvendorid )): (CSRmvendorid );
pack(CSR'(CSRmarchid )): (CSRmarchid );
pack(CSR'(CSRmimpid )): (CSRmimpid );
pack(CSR'(CSRmhartid )): (CSRmhartid );
`ifdef SECURITY
pack(CSR'(CSRmevbase )): (CSRmevbase );
pack(CSR'(CSRmevmask )): (CSRmevmask );
pack(CSR'(CSRmeatp )): (CSRmeatp );
pack(CSR'(CSRmmrbm )): (CSRmmrbm );
pack(CSR'(CSRmemrbm )): (CSRmemrbm );
pack(CSR'(CSRmparbase )): (CSRmparbase );
pack(CSR'(CSRmparmask )): (CSRmparmask );
pack(CSR'(CSRmeparbase )): (CSRmeparbase );
pack(CSR'(CSRmeparmask )): (CSRmeparmask );
pack(CSR'(CSRmflush )): (CSRmflush );
pack(CSR'(CSRmspec )): (CSRmspec );
pack(CSR'(CSRtrng )): (CSRtrng );
`endif
pack(CSR'(CSRtselect )): (CSRtselect );
pack(CSR'(CSRtdata1 )): (CSRtdata1 );
pack(CSR'(CSRtdata2 )): (CSRtdata2 );
pack(CSR'(CSRtdata3 )): (CSRtdata3 );
`ifdef INCLUDE_GDB_CONTROL
pack(CSR'(CSRdcsr )): (CSRdcsr );
pack(CSR'(CSRdpc )): (CSRdpc );
pack(CSR'(CSRdscratch0 )): (CSRdscratch0 );
pack(CSR'(CSRdscratch1 )): (CSRdscratch1 );
`endif
default : (CSRnone );
`define CSR(c,v) pack(CSR'(c)): (c);
`include "CSRs.bsvi"
`undef CSR
default : (CSRnone );
endcase);
endfunction
@@ -420,9 +245,13 @@ typedef enum {
} ModifyOffsetFunc deriving(Bits, Eq, FShow);
typedef enum {
SetBounds, SetBoundsExact, CRRL, CRAM
SetBounds, CRRL, CRAM
} SetBoundsFunc deriving(Bits, Eq, FShow);
typedef enum {
TCC, EPCC, Normal
} SpecialRWFunc deriving(Bits, Eq, FShow);
typedef enum {
Src2Type, Src2Addr
} AddrSource deriving(Bits, Eq, FShow);
@@ -433,8 +262,8 @@ typedef enum {
typedef union tagged {
ModifyOffsetFunc ModifyOffset;
Bool SetBounds;
void SpecialRW;
SetBoundsFunc SetBounds;
SpecialRWFunc SpecialRW;
AddrSource SetAddr;
void Seal;
SrcSelector Unseal;
@@ -568,8 +397,8 @@ typedef union tagged {
typedef struct {
Trap trap;
CHERIException capExp;
} TrapWithCap deriving(Bits, Eq, FShow);
CSR_XCapCause capExp;
} TrapWithCap deriving(Bits, FShow);
// privilege modes
Bit#(2) prvU = 0;
@@ -672,30 +501,72 @@ typedef struct {
Bool illegalInst;
} DecodeResult deriving(Bits, Eq, FShow);
typedef enum {
Src1,
Src2
} CheckAuthoritySrc deriving(Bits, Eq, FShow);
typedef enum {
Src1Addr,
Src2Addr,
Src2Type,
Src1Base
} CheckLowSrc deriving(Bits, Eq, FShow);
typedef enum {
Src1Top,
Src2Addr,
Src2Type,
ResultTop
} CheckHighSrc deriving(Bits, Eq, FShow);
typedef struct {
Data authority_base;
CapTop authority_top;
Bit#(6) authority_idx;
Data check_low;
CapTop check_high;
Bool check_inclusive;
} BoundsCheck deriving(Bits, Eq, FShow);
typedef Bit#(65) CapTop;
typedef Bit#(32) ImmData; // 32-bit decoded immediate data
typedef struct {
Bool src1_tag;
Bool src2_tag;
Bool src1_sealed_with_type;
Bool src1_unsealed;
Bool src2_unsealed;
Bool src1_sealed;
Bool src2_sealed;
Bool src1_src2_types_match;
Bool src1_permit_ccall;
Bool src2_permit_ccall;
Bool src1_permit_x;
Bool src2_no_permit_x;
Bool src2_permit_unseal;
Bool src2_permit_seal;
Bool src2_points_to_src1_type;
Bool src2_addr_valid_type;
Bool src2_perm_subset_src1;
Bool src2_derivable;
`define CAP_CHECK_FIELD(x,s) Bool x;
`include "CapChecks.bsvi"
`undef CAP_CHECK_FIELD
Bool check_enable;
CheckAuthoritySrc check_authority_src;
CheckLowSrc check_low_src;
CheckHighSrc check_high_src;
Bool check_inclusive;
Bit#(6) rn1;
Bit#(6) rn2;
} CapChecks deriving(Bits, Eq, FShow);
} CapChecks deriving(Bits, Eq);
instance FShow#(CapChecks);
function Fmt fshow(CapChecks x);
let ret = $format("CapChecks {",
"rn1 ", fshow(x.rn1), ", rn2 ", fshow(x.rn2));
`define CAP_CHECK_FIELD(f,s) if (x.f) ret = ret + $format(", ", s);
`include "CapChecks.bsvi"
`undef CAP_CHECK_FIELD
if (x.check_enable)
ret = $format(ret, ", bounds check: ",
"auth ", fshow(x.check_authority_src), ", ",
"low ", fshow(x.check_low_src), ", ",
"high ", fshow(x.check_high_src), ", ",
"inclusive ", fshow(x.check_inclusive));
return $format(ret, "}");
endfunction
endinstance
typedef CSR_XCapCause CapException;
@@ -719,6 +590,7 @@ typedef struct {
CapPipe addr;
ControlFlow controlFlow;
Maybe#(CapException) capException;
Maybe#(BoundsCheck) boundsCheck;
} ExecResult deriving(Bits, FShow);
// MMIO

View File

@@ -117,7 +117,7 @@ interface Row_setExecuted_doFinishAlu;
Maybe#(Data) csrData,
Maybe#(CapPipe) scrData,
ControlFlow cf,
Maybe#(CHERIException) cause,
Maybe#(CSR_XCapCause) cause,
CapPipe pcc
`ifdef RVFI
, ExtraTraceBundle tb
@@ -289,7 +289,7 @@ module mkReorderBufferRowEhr(ReorderBufferRowEhr#(aluExeNum, fpuMulDivExeNum)) p
Maybe#(Data) csrData,
Maybe#(CapPipe) scrData,
ControlFlow cf,
Maybe#(CHERIException) cause,
Maybe#(CSR_XCapCause) cause,
CapPipe pcc
`ifdef RVFI
, ExtraTraceBundle tb
@@ -313,10 +313,12 @@ module mkReorderBufferRowEhr(ReorderBufferRowEhr#(aluExeNum, fpuMulDivExeNum)) p
CapPipe new_pcc = setAddrUnsafe(pcc, getAddr(pc[pc_finishAlu_port(i)]));
pc[pc_finishAlu_port(i)] <= new_pcc;
if (!isInBounds(new_pcc, False)) begin
trap[trap_finishAlu_port(i)] <= Valid (TrapWithCap{trap: tagged Exception CHERIFault, capExp: LengthViolation});
trap[trap_finishAlu_port(i)] <= Valid (TrapWithCap{trap: tagged Exception CHERIFault,
capExp: CSR_XCapCause {cheri_exc_code: LengthViolation,
cheri_exc_reg: {1,pack(SCR_PCC)}}});
tval[trap_finishAlu_port(i)] <= tval[trap_finishAlu_port(i)];
end else if (cause matches tagged Valid .exp) begin
trap[trap_finishAlu_port(i)] <= Valid (TrapWithCap{trap: tagged Exception CHERIFault, capExp: fromMaybe(None, cause)});
trap[trap_finishAlu_port(i)] <= Valid (TrapWithCap{trap: tagged Exception CHERIFault, capExp: exp});
tval[trap_finishAlu_port(i)] <= tval[trap_finishAlu_port(i)];
end
`ifdef RVFI
@@ -346,10 +348,12 @@ module mkReorderBufferRowEhr(ReorderBufferRowEhr#(aluExeNum, fpuMulDivExeNum)) p
fflags[fflags_finishFpuMulDiv_port(i)] <= new_fflags;
CapPipe new_pcc = setAddrUnsafe(pcc, getAddr(pc[pc_finishAlu_port(i)]));
if (!isInBounds(new_pcc, False)) begin
trap[trap_finishFpuMulDiv_port(i)] <= Valid (TrapWithCap{trap: tagged Exception CHERIFault, capExp: LengthViolation});
trap[trap_finishFpuMulDiv_port(i)] <= Valid (TrapWithCap{trap: tagged Exception CHERIFault,
capExp: CSR_XCapCause {cheri_exc_code: LengthViolation,
cheri_exc_reg: {1,pack(SCR_PCC)}}});
tval[trap_finishFpuMulDiv_port(i)] <= tval[trap_finishAlu_port(i)];
end else if (cause matches tagged Valid .exp) begin
trap[trap_finishFpuMulDiv_port(i)] <= Valid (TrapWithCap{trap: tagged Exception exp, capExp: None});
trap[trap_finishFpuMulDiv_port(i)] <= Valid (TrapWithCap{trap: tagged Exception exp, capExp: noCapCause});
tval[trap_finishFpuMulDiv_port(i)] <= tval[trap_finishAlu_port(i)];
end
//pc[pc_finishFpuMulDiv_port(i)] <= newPcc; //XXX add pcc checks on FPU instructions
@@ -403,10 +407,12 @@ module mkReorderBufferRowEhr(ReorderBufferRowEhr#(aluExeNum, fpuMulDivExeNum)) p
CapPipe new_pcc = setAddrUnsafe(pcc, getAddr(pc[pc_finishMem_port]));
pc[pc_finishMem_port] <= new_pcc;
if (!isInBounds(new_pcc, False)) begin
mem_early_trap[0] <= Valid (TrapWithCap{trap: tagged Exception CHERIFault, capExp: LengthViolation});
mem_early_trap[0] <= Valid (TrapWithCap{trap: tagged Exception CHERIFault,
capExp: CSR_XCapCause {cheri_exc_code: LengthViolation,
cheri_exc_reg: {1,pack(SCR_PCC)}}});
tval[trap_finishMem_port] <= tval[trap_finishMem_port];
end else if (cause matches tagged Valid .exp) begin
mem_early_trap[0] <= Valid (TrapWithCap{trap: tagged Exception exp, capExp: None});
mem_early_trap[0] <= Valid (TrapWithCap{trap: tagged Exception exp, capExp: noCapCause});
tval[trap_finishMem_port] <= tval[trap_finishMem_port];
end
endmethod
@@ -533,7 +539,7 @@ module mkReorderBufferRowEhr(ReorderBufferRowEhr#(aluExeNum, fpuMulDivExeNum)) p
// record trap
//doAssert(!isValid(trap[trap_deqLSQ_port]), "cannot have trap");
if (isValid(mem_early_trap[0])) trap[trap_deqLSQ_port] <= mem_early_trap[0];
else if(cause matches tagged Valid .e) trap[trap_deqLSQ_port] <= Valid (TrapWithCap{trap: tagged Exception e, capExp: None});
else if(cause matches tagged Valid .e) trap[trap_deqLSQ_port] <= Valid (TrapWithCap{trap: tagged Exception e, capExp: noCapCause});
// TODO: shouldn't we record tval here as well?
// record ld misspeculation
ldKilled[ldKill_deqLSQ_port] <= ld_killed;
@@ -595,7 +601,7 @@ interface ROB_setExecuted_doFinishAlu;
Maybe#(Data) csrData,
Maybe#(CapPipe) scrData,
ControlFlow cf,
Maybe#(CHERIException) cause,
Maybe#(CSR_XCapCause) cause,
CapPipe pcc
`ifdef RVFI
, ExtraTraceBundle tb
@@ -1144,7 +1150,7 @@ module mkSupReorderBuffer#(
Maybe#(Data) csrData,
Maybe#(CapPipe) scrData,
ControlFlow cf,
Maybe#(CHERIException) cause,
Maybe#(CSR_XCapCause) cause,
CapPipe pcc
`ifdef RVFI
, ExtraTraceBundle tb