feat: MU rewrite 2
TLB Support
This commit is contained in:
parent
9ce588757d
commit
4f7fe2adf2
@ -1,9 +1,11 @@
|
|||||||
`verilator_config
|
`verilator_config
|
||||||
lint_off -rule TIMESCALEMOD
|
lint_off -rule TIMESCALEMOD
|
||||||
lint_off -rule DECLFILENAME
|
lint_off -rule DECLFILENAME
|
||||||
|
lint_off -rule INITIALDLY
|
||||||
|
|
||||||
lint_off -file "model/*.v"
|
lint_off -file "model/*.v"
|
||||||
lint_off -file "../resources/func_test/*.v"
|
lint_off -file "../resources/func_test/*.v"
|
||||||
|
|
||||||
lint_off -rule BLKSEQ -file "../src/CP0/CP0.sv"
|
lint_off -rule UNOPTFLAT -file "model/axi_crossbar_addr.v"
|
||||||
lint_off -rule PINCONNECTEMPTY -file "../src/MU/MU.sv"
|
lint_off -rule UNOPTFLAT -file "model/priority_encoder.v"
|
||||||
|
lint_off -rule BLKSEQ -file "../src/CP0/CP0.sv"
|
||||||
|
@ -1232,10 +1232,10 @@ module Datapath (
|
|||||||
assign C0_wdata = M_I0_ForwardT;
|
assign C0_wdata = M_I0_ForwardT;
|
||||||
|
|
||||||
// M.I1.MEM
|
// M.I1.MEM
|
||||||
assign C0.cpu_tlbwi = M.I1.MCtrl.TLBWI;
|
assign C0.cpu_tlbwi = M.I1.MCtrl.TLBWI;
|
||||||
assign C0.cpu_tlbwr = M.I1.MCtrl.TLBWR;
|
assign C0.cpu_tlbwr = M.I1.MCtrl.TLBWR;
|
||||||
assign C0.cpu_tlbr = M.I1.MCtrl.TLBR;
|
assign C0.cpu_tlbr = M.I1.MCtrl.TLBR;
|
||||||
assign C0.cpu_c0_tlbp = M.I1.MCtrl.TLBP & M.en;
|
assign C0.cpu_c0_tlbp = M.I1.MCtrl.TLBP & M.en;
|
||||||
assign mem.wr = M.I1.MCtrl.MWR;
|
assign mem.wr = M.I1.MCtrl.MWR;
|
||||||
memoutput M_I1_memoutput (
|
memoutput M_I1_memoutput (
|
||||||
.addr (M.I1.ALUOut[1:0]),
|
.addr (M.I1.ALUOut[1:0]),
|
||||||
|
114
src/MU/MU.sv
114
src/MU/MU.sv
@ -20,6 +20,7 @@ module MU (
|
|||||||
// == CacheOp ==
|
// == CacheOp ==
|
||||||
// =============
|
// =============
|
||||||
|
|
||||||
|
// NOTE: req and op and addr should be kept until addr_ok
|
||||||
logic cop_i_req = cacheop.req & cacheop.op.icache_op;
|
logic cop_i_req = cacheop.req & cacheop.op.icache_op;
|
||||||
logic cop_d_req = cacheop.req & cacheop.op.dcache_op;
|
logic cop_d_req = cacheop.req & cacheop.op.dcache_op;
|
||||||
logic cop_i_ok, cop_d_ok;
|
logic cop_i_ok, cop_d_ok;
|
||||||
@ -51,10 +52,8 @@ module MU (
|
|||||||
|
|
||||||
// TLB
|
// TLB
|
||||||
word_t instfetch_phy_addr;
|
word_t instfetch_phy_addr;
|
||||||
logic instfetch_hit;
|
|
||||||
logic instfetch_cached;
|
logic instfetch_cached;
|
||||||
logic instfetch_valid;
|
logic instfetch_valid;
|
||||||
logic instfetch_privilege;
|
|
||||||
|
|
||||||
// ===============
|
// ===============
|
||||||
// AXI Read Worker
|
// AXI Read Worker
|
||||||
@ -158,6 +157,9 @@ module MU (
|
|||||||
cacheop.addr_ok = 1;
|
cacheop.addr_ok = 1;
|
||||||
icache.index_for_lookup = cacheop.addr[`IC_TAGL-1:`IC_INDEXL];
|
icache.index_for_lookup = cacheop.addr[`IC_TAGL-1:`IC_INDEXL];
|
||||||
|
|
||||||
|
end else if (~instfetch_valid) begin
|
||||||
|
in_if_ready = 1;
|
||||||
|
|
||||||
end else if (if_req & instfetch_cached & icache.hit) begin
|
end else if (if_req & instfetch_cached & icache.hit) begin
|
||||||
// Cached + Hit -> return
|
// Cached + Hit -> return
|
||||||
ifc_next_state = IFC_LOOKUP;
|
ifc_next_state = IFC_LOOKUP;
|
||||||
@ -230,6 +232,7 @@ module MU (
|
|||||||
icache.ctrl.cache_index_invalidate = ~stored_cacheop_op.index_or_hit;
|
icache.ctrl.cache_index_invalidate = ~stored_cacheop_op.index_or_hit;
|
||||||
icache.ctrl.cache_hit_invalidate = stored_cacheop_op.index_or_hit;
|
icache.ctrl.cache_hit_invalidate = stored_cacheop_op.index_or_hit;
|
||||||
|
|
||||||
|
icache.index = stored_cacheop_addr[`IC_TAGL-1:`IC_INDEXL];
|
||||||
icache.index_for_lookup = stored_cacheop_addr[`IC_TAGL-1:`IC_INDEXL];
|
icache.index_for_lookup = stored_cacheop_addr[`IC_TAGL-1:`IC_INDEXL];
|
||||||
end
|
end
|
||||||
default: begin end
|
default: begin end
|
||||||
@ -419,6 +422,9 @@ module MU (
|
|||||||
// Handle Cache Instruction
|
// Handle Cache Instruction
|
||||||
mem_nxt_state = MEM_CACHE_INVALID;
|
mem_nxt_state = MEM_CACHE_INVALID;
|
||||||
dcache.index_for_lookup = cacheop.addr[`DC_TAGL-1:`DC_INDEXL];
|
dcache.index_for_lookup = cacheop.addr[`DC_TAGL-1:`DC_INDEXL];
|
||||||
|
end else if (~memory_valid) begin
|
||||||
|
in_mem_ready = 1;
|
||||||
|
|
||||||
end else if (mem_req & memory_cached & dcache.hit) begin
|
end else if (mem_req & memory_cached & dcache.hit) begin
|
||||||
// Cached + Hit
|
// Cached + Hit
|
||||||
if (~memory.wr) begin
|
if (~memory.wr) begin
|
||||||
@ -605,6 +611,82 @@ module MU (
|
|||||||
// ======= virt addr -> phy addr =======
|
// ======= virt addr -> phy addr =======
|
||||||
// =====================================
|
// =====================================
|
||||||
|
|
||||||
|
`ifdef ENABLE_TLB
|
||||||
|
|
||||||
|
logic tlbw;
|
||||||
|
logic [2:0] c0_Index_u;
|
||||||
|
|
||||||
|
assign tlbw = cp0.cpu_tlbwi | cp0.cpu_tlbwr;
|
||||||
|
assign c0_Index_u = cp0.cpu_tlbwr ? cp0.cp0_Random[2:0] : cp0.cp0_Index[2:0];
|
||||||
|
|
||||||
|
word_t iVA, iPA1;
|
||||||
|
word_t dVA, dPA1;
|
||||||
|
logic iHit1, iCached1, iMValid1, iUser1;
|
||||||
|
logic dHit1, dCached1, dMValid1, dUser1, dDirty1;
|
||||||
|
|
||||||
|
TLB TLB (
|
||||||
|
.clk (clk),
|
||||||
|
.rst (rst),
|
||||||
|
.K0 (cp0.cp0_K0),
|
||||||
|
.tlbw (tlbw),
|
||||||
|
.tlbp (cp0.cpu_tlb_tlbp),
|
||||||
|
.c0_Index (c0_Index_u),
|
||||||
|
.c0_EntryHi (cp0.cp0_EntryHi),
|
||||||
|
.c0_EntryLo1(cp0.cp0_EntryLo1),
|
||||||
|
.c0_EntryLo0(cp0.cp0_EntryLo0),
|
||||||
|
.EntryHi (cp0.tlb_EntryHi),
|
||||||
|
.EntryLo1 (cp0.tlb_EntryLo1),
|
||||||
|
.EntryLo0 (cp0.tlb_EntryLo0),
|
||||||
|
.Index (cp0.tlb_Index),
|
||||||
|
|
||||||
|
.iVAddr (iVA),
|
||||||
|
.iPAddr (iPA1),
|
||||||
|
.iHit (iHit1),
|
||||||
|
.iCached (iCached1),
|
||||||
|
.iValid (iMValid1),
|
||||||
|
.iUser (iUser1),
|
||||||
|
.dVAddr (dVA),
|
||||||
|
.dPAddr (dPA1),
|
||||||
|
.dHit (dHit1),
|
||||||
|
.dCached (dCached1),
|
||||||
|
.dDirty (dDirty1),
|
||||||
|
.dValid (dMValid1),
|
||||||
|
.dUser (dUser1)
|
||||||
|
);
|
||||||
|
|
||||||
|
logic choose_cop_i = (ifc_cur_state == IFC_LOOKUP) & cop_i_req;
|
||||||
|
logic choose_cop_d = (mem_cur_state == MEM_LOOKUP) & cop_d_req;
|
||||||
|
|
||||||
|
// instfetch
|
||||||
|
assign iVA = choose_cop_i ? cacheop.addr : (instfetch.req ? instfetch.addr : stored_instfetch_addr);
|
||||||
|
assign instfetch_phy_addr = iPA1;
|
||||||
|
assign instfetch_valid = iHit1 & iMValid1 & (cp0.cp0_in_kernel | iUser1);
|
||||||
|
assign instfetch_cached = iCached1;
|
||||||
|
|
||||||
|
assign cp0.tlb_iTLBRefill = if_req & ~iHit1;
|
||||||
|
assign cp0.tlb_iTLBInvalid = if_req & ~iMValid1;
|
||||||
|
assign cp0.tlb_iAddressError = if_req & ~(cp0.cp0_in_kernel | iUser1);
|
||||||
|
|
||||||
|
// memory
|
||||||
|
assign dVA = choose_cop_d ? cacheop.addr : (memory.req ? memory.addr : stored_memory_addr);
|
||||||
|
assign memory_phy_addr = dPA1;
|
||||||
|
// TODO: should memory.wr be stored?
|
||||||
|
assign memory_valid = dHit1 & dMValid1 & (cp0.cp0_in_kernel | dUser1) & (~memory.wr | dDirty1);
|
||||||
|
assign memory_cached = dCached1;
|
||||||
|
|
||||||
|
assign cp0.tlb_dTLBRefill = mem_req & ~dHit1;
|
||||||
|
assign cp0.tlb_dTLBInvalid = mem_req & ~dMValid1;
|
||||||
|
assign cp0.tlb_dTLBModified = mem_req & memory.wr & ~dDirty1;
|
||||||
|
assign cp0.tlb_dAddressError = mem_req & ~(cp0.cp0_in_kernel | dUser1);
|
||||||
|
|
||||||
|
`else
|
||||||
|
|
||||||
|
logic if_vp_hit, if_vp_valid, if_vp_privilege;
|
||||||
|
logic mem_vp_hit, mem_vp_valid, mem_vp_privilege;
|
||||||
|
assign instfetch_valid = if_vp_hit & if_vp_valid;
|
||||||
|
assign memory_valid = mem_vp_hit & mem_vp_valid;
|
||||||
|
|
||||||
|
/* verilator lint_off PINCONNECTEMPTY */
|
||||||
addr_virt_to_phy instfetch_addr_convert(
|
addr_virt_to_phy instfetch_addr_convert(
|
||||||
.K0 (cp0.cp0_K0),
|
.K0 (cp0.cp0_K0),
|
||||||
.virt_addr (stored_instfetch_addr),
|
.virt_addr (stored_instfetch_addr),
|
||||||
@ -614,11 +696,11 @@ module MU (
|
|||||||
.tlb_dirty (1'b1),
|
.tlb_dirty (1'b1),
|
||||||
.tlb_valid (1'b1),
|
.tlb_valid (1'b1),
|
||||||
.phy_addr (instfetch_phy_addr),
|
.phy_addr (instfetch_phy_addr),
|
||||||
.hit (instfetch_hit),
|
.hit (if_vp_hit),
|
||||||
.cached (instfetch_cached),
|
.cached (instfetch_cached),
|
||||||
.dirty (),
|
.dirty (),
|
||||||
.valid (instfetch_valid),
|
.valid (if_vp_valid),
|
||||||
.privilege (instfetch_privilege)
|
.privilege (if_vp_privilege)
|
||||||
);
|
);
|
||||||
addr_virt_to_phy memory_addr_convert(
|
addr_virt_to_phy memory_addr_convert(
|
||||||
.K0 (cp0.cp0_K0),
|
.K0 (cp0.cp0_K0),
|
||||||
@ -629,12 +711,26 @@ module MU (
|
|||||||
.tlb_dirty (1'b1),
|
.tlb_dirty (1'b1),
|
||||||
.tlb_valid (1'b1),
|
.tlb_valid (1'b1),
|
||||||
.phy_addr (memory_phy_addr),
|
.phy_addr (memory_phy_addr),
|
||||||
.hit (memory_hit),
|
.hit (mem_vp_hit),
|
||||||
.cached (memory_cached),
|
.cached (memory_cached),
|
||||||
.dirty (memory_dirty),
|
.dirty (),
|
||||||
.valid (memory_valid),
|
.valid (mem_vp_valid),
|
||||||
.privilege (memory_privilege)
|
.privilege (mem_vp_privilege)
|
||||||
);
|
);
|
||||||
|
/* verilator lint_on PINCONNECTEMPTY */
|
||||||
|
|
||||||
|
assign cp0.tlb_EntryHi = 0;
|
||||||
|
assign cp0.tlb_EntryLo1 = 0;
|
||||||
|
assign cp0.tlb_EntryLo0 = 0;
|
||||||
|
assign cp0.tlb_Index = 0;
|
||||||
|
assign cp0.tlb_iTLBRefill = 0;
|
||||||
|
assign cp0.tlb_iTLBInvalid = 0;
|
||||||
|
assign cp0.tlb_iAddressError = 0;
|
||||||
|
assign cp0.tlb_dTLBRefill = 0;
|
||||||
|
assign cp0.tlb_dTLBInvalid = 0;
|
||||||
|
assign cp0.tlb_dTLBModified = 0;
|
||||||
|
assign cp0.tlb_dAddressError = 0;
|
||||||
|
|
||||||
|
`endif
|
||||||
|
|
||||||
endmodule
|
endmodule
|
||||||
|
@ -12,12 +12,10 @@ module TLB (
|
|||||||
input logic [2:0] c0_Index, // TLBWR + TLBWI + TLBR
|
input logic [2:0] c0_Index, // TLBWR + TLBWI + TLBR
|
||||||
|
|
||||||
input EntryHi_t c0_EntryHi, // TLBWI + F/M(ASID)
|
input EntryHi_t c0_EntryHi, // TLBWI + F/M(ASID)
|
||||||
// input PageMask_t c0_PageMask, // TLBWI
|
|
||||||
input EntryLo_t c0_EntryLo1, // TLBWI
|
input EntryLo_t c0_EntryLo1, // TLBWI
|
||||||
input EntryLo_t c0_EntryLo0, // TLBWI
|
input EntryLo_t c0_EntryLo0, // TLBWI
|
||||||
|
|
||||||
output EntryHi_t EntryHi, // TLBR
|
output EntryHi_t EntryHi, // TLBR
|
||||||
// output PageMask_t PageMask, // TLBR
|
|
||||||
output EntryLo_t EntryLo1, // TLBR
|
output EntryLo_t EntryLo1, // TLBR
|
||||||
output EntryLo_t EntryLo0, // TLBR
|
output EntryLo_t EntryLo0, // TLBR
|
||||||
output Index_t Index, // TLBP
|
output Index_t Index, // TLBP
|
||||||
@ -57,28 +55,25 @@ module TLB (
|
|||||||
TLB_t [7:0] TLB_entries;
|
TLB_t [7:0] TLB_entries;
|
||||||
TLB_t entry;
|
TLB_t entry;
|
||||||
|
|
||||||
// CP0(TLBWI) EntryHi /*PageMask*/ EntryLo0 EntryLo1 -> TLB[Index]
|
// CP0(TLBWI) EntryHi EntryLo0 EntryLo1 -> TLB[Index]
|
||||||
always_ff @(posedge clk) begin
|
always_ff @(posedge clk) begin
|
||||||
if (rst) begin
|
if (rst) begin
|
||||||
TLB_entries <= 624'b0;
|
TLB_entries <= 624'b0;
|
||||||
end else if (tlbw)
|
end else if (tlbw)
|
||||||
TLB_entries[c0_Index] <= {c0_EntryHi.VPN2, c0_EntryHi.ASID,
|
TLB_entries[c0_Index] <= {
|
||||||
// c0_PageMask.Mask,
|
c0_EntryHi.VPN2, c0_EntryHi.ASID,
|
||||||
c0_EntryLo0.G & c0_EntryLo1.G,
|
c0_EntryLo0.G & c0_EntryLo1.G,
|
||||||
c0_EntryLo0.PFN, c0_EntryLo0.C, c0_EntryLo0.D, c0_EntryLo0.V,
|
c0_EntryLo0.PFN, c0_EntryLo0.C, c0_EntryLo0.D, c0_EntryLo0.V,
|
||||||
c0_EntryLo1.PFN, c0_EntryLo1.C, c0_EntryLo1.D, c0_EntryLo1.V};
|
c0_EntryLo1.PFN, c0_EntryLo1.C, c0_EntryLo1.D, c0_EntryLo1.V
|
||||||
|
};
|
||||||
end
|
end
|
||||||
// CP0(TLBR) Index -> EntryHi /*PageMask*/ EntryLo0 EntryLo1
|
// CP0(TLBR) Index -> EntryHi EntryLo0 EntryLo1
|
||||||
assign entry = TLB_entries[c0_Index];
|
assign entry = TLB_entries[c0_Index];
|
||||||
|
|
||||||
assign EntryHi.zero = 5'b0;
|
assign EntryHi.zero = 5'b0;
|
||||||
assign EntryHi.VPN2 = entry.VPN2;
|
assign EntryHi.VPN2 = entry.VPN2;
|
||||||
assign EntryHi.ASID = entry.ASID;
|
assign EntryHi.ASID = entry.ASID;
|
||||||
|
|
||||||
// assign PageMask.zero1 = 7'b0;
|
|
||||||
// assign PageMask.Mask = entry.PageMask;
|
|
||||||
// assign PageMask.zero2 = 13'b0;
|
|
||||||
|
|
||||||
assign EntryLo0.zero = 6'b0;
|
assign EntryLo0.zero = 6'b0;
|
||||||
assign EntryLo0.PFN = entry.PFN0;
|
assign EntryLo0.PFN = entry.PFN0;
|
||||||
assign EntryLo0.C = entry.C0;
|
assign EntryLo0.C = entry.C0;
|
||||||
@ -135,57 +130,37 @@ module TLB (
|
|||||||
|
|
||||||
// Output
|
// Output
|
||||||
ffenr #(55) inst_ff(
|
ffenr #(55) inst_ff(
|
||||||
clk, rst,
|
.*,
|
||||||
{fVAddr, fPAddr, fHit, fCached, fValid},
|
.d ({fVAddr, fPAddr, fHit, fCached, fValid}),
|
||||||
1'b1,
|
.en(1'b1),
|
||||||
{fVAddr1, fPAddr1, fHit1, fCached1, fValid1}
|
.q ({fVAddr1, fPAddr1, fHit1, fCached1, fValid1})
|
||||||
);
|
);
|
||||||
always_comb begin
|
/* verilator lint_off PINCONNECTEMPTY */
|
||||||
if (fVAddr1 > 32'hBFFF_FFFF || fVAddr1 <= 32'h7FFF_FFFF) begin
|
|
||||||
// kseg2 + kseg3 + kuseg -> tlb
|
|
||||||
iPAddr = {fPAddr1, fVAddr1[11:0]};
|
|
||||||
iHit = fHit1;
|
|
||||||
iCached = fCached1;
|
|
||||||
iValid = fValid1;
|
|
||||||
iUser = ~fVAddr1[31];
|
|
||||||
end else if (fVAddr1 > 32'h9FFF_FFFF) begin
|
|
||||||
// kseg1 uncached
|
|
||||||
iPAddr = fVAddr1 & 32'h1FFF_FFFF;
|
|
||||||
iHit = 1'b1;
|
|
||||||
iCached = 1'b0;
|
|
||||||
iValid = 1'b1;
|
|
||||||
iUser = 1'b0;
|
|
||||||
end else begin
|
|
||||||
// kseg0 -> CP0.K0
|
|
||||||
iPAddr = fVAddr1 & 32'h1FFF_FFFF;
|
|
||||||
iHit = 1'b1;
|
|
||||||
iCached = K0[0];
|
|
||||||
iValid = 1'b1;
|
|
||||||
iUser = 1'b0;
|
|
||||||
end
|
|
||||||
end
|
|
||||||
addr_virt_to_phy instfetch_addr_convert(
|
addr_virt_to_phy instfetch_addr_convert(
|
||||||
|
.K0 (K0),
|
||||||
.virt_addr (fVAddr1),
|
.virt_addr (fVAddr1),
|
||||||
.tlb_addr (fPAddr1),
|
.tlb_addr (fPAddr1),
|
||||||
.tlb_hit (fHit1),
|
.tlb_hit (fHit1),
|
||||||
.tlb_cached (fCached1),
|
.tlb_cached (fCached1),
|
||||||
.tlb_dirty (fDirty1),
|
.tlb_dirty (),
|
||||||
.tlb_valid (fValid1),
|
.tlb_valid (fValid1),
|
||||||
.phy_addr (iPAddr),
|
.phy_addr (iPAddr),
|
||||||
.hit (iHit),
|
.hit (iHit),
|
||||||
.cached (iCached),
|
.cached (iCached),
|
||||||
.dirty (iDirty),
|
.dirty (),
|
||||||
.valid (iValid),
|
.valid (iValid),
|
||||||
.privilege (iUser) // not
|
.privilege (iUser) // not
|
||||||
);
|
);
|
||||||
|
/* verilator lint_on PINCONNECTEMPTY */
|
||||||
|
|
||||||
ffenr #(56) data_ff (
|
ffenr #(56) data_ff (
|
||||||
clk, rst,
|
.*,
|
||||||
{mVAddr, mPAddr, mHit, mCached, mValid, mDirty},
|
.d ({mVAddr, mPAddr, mHit, mCached, mValid, mDirty}),
|
||||||
1'b1,
|
.en(1'b1),
|
||||||
{mVAddr1, mPAddr1, mHit1, mCached1, mValid1, mDirty1}
|
.q ({mVAddr1, mPAddr1, mHit1, mCached1, mValid1, mDirty1})
|
||||||
);
|
);
|
||||||
addr_virt_to_phy memory_addr_convert(
|
addr_virt_to_phy memory_addr_convert(
|
||||||
|
.K0 (K0),
|
||||||
.virt_addr (mVAddr1),
|
.virt_addr (mVAddr1),
|
||||||
.tlb_addr (mPAddr1),
|
.tlb_addr (mPAddr1),
|
||||||
.tlb_hit (mHit1),
|
.tlb_hit (mHit1),
|
||||||
|
@ -16,18 +16,14 @@ module TLB_Lookup (
|
|||||||
|
|
||||||
logic [7:0] hitWay;
|
logic [7:0] hitWay;
|
||||||
for (genvar i = 0; i < 8; i++)
|
for (genvar i = 0; i < 8; i++)
|
||||||
// assign hitWay[i] = ((TLB_entries[i].VPN2 & ~{7'b0, TLB_entries[i].PageMask})
|
|
||||||
// == (VPN[19:1] & ~{7'b0, TLB_entries[i].PageMask}))
|
|
||||||
// & (TLB_entries[i].G | TLB_entries[i].ASID == ASID);
|
|
||||||
assign hitWay[i] = (TLB_entries[i].VPN2 == VPN[19:1])
|
assign hitWay[i] = (TLB_entries[i].VPN2 == VPN[19:1])
|
||||||
& (TLB_entries[i].G | TLB_entries[i].ASID == ASID);
|
& (TLB_entries[i].G | TLB_entries[i].ASID == ASID);
|
||||||
|
|
||||||
// assume: hit is unique
|
// NOTE: assume: hit is unique
|
||||||
assign hit = |{hitWay};
|
assign hit = |{hitWay};
|
||||||
assign index.P = ~hit;
|
assign index.P = ~hit;
|
||||||
assign index.zero = 0;
|
assign index.zero = 0;
|
||||||
onehot_bin8 index_decoder(hitWay, index.Index);
|
onehot_bin8 index_decoder(hitWay, index.Index);
|
||||||
// always_comb for (int i = 0; i < 32; i++) index.Index |= hitWay[i] ? i : 0;
|
|
||||||
|
|
||||||
TLB_t found;
|
TLB_t found;
|
||||||
assign found = (hitWay[ 0] ? TLB_entries[ 0] : 78'b0)
|
assign found = (hitWay[ 0] ? TLB_entries[ 0] : 78'b0)
|
||||||
@ -40,21 +36,10 @@ module TLB_Lookup (
|
|||||||
| (hitWay[ 7] ? TLB_entries[ 7] : 78'b0);
|
| (hitWay[ 7] ? TLB_entries[ 7] : 78'b0);
|
||||||
|
|
||||||
logic parity;
|
logic parity;
|
||||||
// assign parity = |{
|
|
||||||
// VPN[12] & found.PageMask[10],
|
|
||||||
// VPN[10] & ~found.PageMask[10] & found.PageMask[ 8],
|
|
||||||
// VPN[ 8] & ~found.PageMask[ 8] & found.PageMask[ 6],
|
|
||||||
// VPN[ 6] & ~found.PageMask[ 6] & found.PageMask[ 4],
|
|
||||||
// VPN[ 4] & ~found.PageMask[ 4] & found.PageMask[ 2],
|
|
||||||
// VPN[ 2] & ~found.PageMask[ 2] & found.PageMask[ 0],
|
|
||||||
// VPN[ 0] & ~found.PageMask[ 0]
|
|
||||||
// };
|
|
||||||
// assign parity = |{VPN & {7'b0, found.PageMask + 1'b1}};
|
|
||||||
assign parity = VPN[0];
|
assign parity = VPN[0];
|
||||||
|
|
||||||
logic [19:0] PFN;
|
logic [19:0] PFN;
|
||||||
assign {PFN, cached, dirty, valid} = parity ? {found.PFN1, found.C1[0], found.D1, found.V1}
|
assign {PFN, cached, dirty, valid} = parity ? {found.PFN1, found.C1[0], found.D1, found.V1}
|
||||||
: {found.PFN0, found.C0[0], found.D0, found.V0};
|
: {found.PFN0, found.C0[0], found.D0, found.V0};
|
||||||
// assign PPN = (VPN & {8'b0, found.PageMask}) | (PFN & ~{8'b0, found.PageMask});
|
|
||||||
assign PPN = PFN;
|
assign PPN = PFN;
|
||||||
endmodule
|
endmodule
|
||||||
|
@ -130,12 +130,10 @@ interface CP0_i;
|
|||||||
logic cpu_tlbr;
|
logic cpu_tlbr;
|
||||||
Random_t cp0_Random; // TLBWR
|
Random_t cp0_Random; // TLBWR
|
||||||
EntryHi_t cp0_EntryHi; // TLBWI + F/M(ASID)
|
EntryHi_t cp0_EntryHi; // TLBWI + F/M(ASID)
|
||||||
// PageMask_t cp0_PageMask; // TLBWI
|
|
||||||
EntryLo_t cp0_EntryLo1; // TLBWI
|
EntryLo_t cp0_EntryLo1; // TLBWI
|
||||||
EntryLo_t cp0_EntryLo0; // TLBWI
|
EntryLo_t cp0_EntryLo0; // TLBWI
|
||||||
Index_t cp0_Index; // TLBWI + TLBR
|
Index_t cp0_Index; // TLBWI + TLBR
|
||||||
EntryHi_t tlb_EntryHi;
|
EntryHi_t tlb_EntryHi;
|
||||||
// PageMask_t tlb_PageMask;
|
|
||||||
EntryLo_t tlb_EntryLo1;
|
EntryLo_t tlb_EntryLo1;
|
||||||
EntryLo_t tlb_EntryLo0;
|
EntryLo_t tlb_EntryLo0;
|
||||||
Index_t tlb_Index; // TLBP
|
Index_t tlb_Index; // TLBP
|
||||||
@ -156,11 +154,9 @@ interface CP0_i;
|
|||||||
input cp0_Random,
|
input cp0_Random,
|
||||||
input cp0_Index,
|
input cp0_Index,
|
||||||
input cp0_EntryHi,
|
input cp0_EntryHi,
|
||||||
// input cp0_PageMask,
|
|
||||||
input cp0_EntryLo1,
|
input cp0_EntryLo1,
|
||||||
input cp0_EntryLo0,
|
input cp0_EntryLo0,
|
||||||
output tlb_EntryHi,
|
output tlb_EntryHi,
|
||||||
// output tlb_PageMask,
|
|
||||||
output tlb_EntryLo1,
|
output tlb_EntryLo1,
|
||||||
output tlb_EntryLo0,
|
output tlb_EntryLo0,
|
||||||
output tlb_Index,
|
output tlb_Index,
|
||||||
|
@ -7,12 +7,6 @@ typedef struct packed {
|
|||||||
logic [ 7:0] ASID;
|
logic [ 7:0] ASID;
|
||||||
} EntryHi_t;
|
} EntryHi_t;
|
||||||
|
|
||||||
// typedef struct packed {
|
|
||||||
// logic [ 6:0] zero1;
|
|
||||||
// logic [11:0] Mask;
|
|
||||||
// logic [12:0] zero2;
|
|
||||||
// } PageMask_t;
|
|
||||||
|
|
||||||
typedef struct packed {
|
typedef struct packed {
|
||||||
logic [ 5:0] zero;
|
logic [ 5:0] zero;
|
||||||
logic [19:0] PFN;
|
logic [19:0] PFN;
|
||||||
@ -41,7 +35,6 @@ typedef struct packed {
|
|||||||
typedef struct packed {
|
typedef struct packed {
|
||||||
logic [18:0] VPN2;
|
logic [18:0] VPN2;
|
||||||
logic [ 7:0] ASID;
|
logic [ 7:0] ASID;
|
||||||
// logic [11:0] PageMask;
|
|
||||||
logic G;
|
logic G;
|
||||||
logic [19:0] PFN0;
|
logic [19:0] PFN0;
|
||||||
logic [ 2:0] C0;
|
logic [ 2:0] C0;
|
||||||
|
@ -2,6 +2,7 @@
|
|||||||
`define DEFINES_SVH
|
`define DEFINES_SVH
|
||||||
|
|
||||||
`define XLEN 32
|
`define XLEN 32
|
||||||
|
`define ENABLE_TLB
|
||||||
|
|
||||||
`define PCRST 32'hBFC00000
|
`define PCRST 32'hBFC00000
|
||||||
`define Off_TRef 9'h000
|
`define Off_TRef 9'h000
|
||||||
|
Loading…
Reference in New Issue
Block a user