LOG_LENGTH = 0
class ICacheConfig:
- def __init__(self, LINE_SIZE = 64,
+ def __init__(self, XLEN = 64,
+ LINE_SIZE = 64,
NUM_LINES = 64, # Number of lines in a set
NUM_WAYS = 2, # Number of ways
TLB_SIZE = 64, # L1 ITLB number of entries
TLB_LG_PGSZ = 12): # L1 ITLB log_2(page_size)
+ self.XLEN = XLEN
self.LINE_SIZE = LINE_SIZE
self.NUM_LINES = NUM_LINES
self.NUM_WAYS = NUM_WAYS
# (based on WB, so 64-bits)
self.ROW_SIZE = WB_DATA_BITS // 8
# Number of real address bits that we store
- self.REAL_ADDR_BITS = 56
+ self.REAL_ADDR_BITS = XLEN-8 # 56 for XLEN=64
self.ROW_SIZE_BITS = self.ROW_SIZE * 8
# ROW_PER_LINE is the number of row (wishbone) transactions in a line
# L1 ITLB
self.TL_BITS = log2_int(self.TLB_SIZE)
- self.TLB_EA_TAG_BITS = 64 - (self.TLB_LG_PGSZ + self.TL_BITS)
- self.TLB_PTE_BITS = 64
+ self.TLB_EA_TAG_BITS = XLEN - (self.TLB_LG_PGSZ + self.TL_BITS)
+ self.TLB_PTE_BITS = XLEN
+ print("self.XLEN =", self.XLEN)
print("self.BRAM_ROWS =", self.BRAM_ROWS)
print("self.INDEX_BITS =", self.INDEX_BITS)
print("self.INSN_BITS =", self.INSN_BITS)
print("self.TLB_PTE_BITS =", self.TLB_PTE_BITS)
print("self.TLB_SIZE =", self.TLB_SIZE)
print("self.WAY_BITS =", self.WAY_BITS)
+ print()
assert self.LINE_SIZE % self.ROW_SIZE == 0
assert ispow2(self.LINE_SIZE), "self.LINE_SIZE not power of 2"
self.microwatt_compat = (hasattr(pspec, "microwatt_compat") and
(pspec.microwatt_compat == True))
+ XLEN = pspec.XLEN
+
if self.microwatt_compat:
# reduce way sizes and num lines
- ICacheConfig.__init__(self, NUM_LINES = 4,
+ ICacheConfig.__init__(self, LINE_SIZE=XLEN,
+ XLEN=XLEN,
+ NUM_LINES = 4,
NUM_WAYS = 1,
- TLB_SIZE=16 # needs device-tree update
+ TLB_SIZE=4 # needs device-tree update
)
else:
- ICacheConfig.__init__(self)
+ ICacheConfig.__init__(self, LINE_SIZE=XLEN, XLEN=XLEN)
def use_fetch_interface(self):
self.use_fetch_iface = True
sync += r.state.eq(State.WAIT_ACK)
def icache_miss_wait_ack(self, m, r, replace_way, inval_in,
- cache_valids, stbs_done):
+ cache_valids):
comb = m.d.comb
sync = m.d.sync
bus = self.bus
- # Requests are all sent if stb is 0
- stbs_zero = Signal()
- comb += stbs_zero.eq(r.wb.stb == 0)
- comb += stbs_done.eq(stbs_zero)
-
# If we are still sending requests, was one accepted?
- with m.If(~bus.stall & ~stbs_zero):
- # That was the last word? We are done sending.
- # Clear stb and set stbs_done so we can handle
- # an eventual last ack on the same cycle.
+ with m.If(~bus.stall & r.wb.stb):
+ # That was the last word? We are done sending. Clear stb
with m.If(self.is_last_row_addr(r.req_adr, r.end_row_ix)):
sync += Display("IS_LAST_ROW_ADDR r.wb.addr:%x "
- "r.end_row_ix:%x r.wb.stb:%x stbs_zero:%x "
- "stbs_done:%x", r.wb.adr, r.end_row_ix,
- r.wb.stb, stbs_zero, stbs_done)
+ "r.end_row_ix:%x r.wb.stb:%x",
+ r.wb.adr, r.end_row_ix, r.wb.stb)
sync += r.wb.stb.eq(0)
- comb += stbs_done.eq(1)
# Calculate the next row address
rarange = Signal(self.LINE_OFF_BITS - self.ROW_OFF_BITS)
self.LINE_OFF_BITS] + 1)
sync += r.req_adr[self.ROW_OFF_BITS:self.LINE_OFF_BITS].eq(rarange)
sync += Display("RARANGE r.req_adr:%x rarange:%x "
- "stbs_zero:%x stbs_done:%x",
- r.req_adr, rarange, stbs_zero, stbs_done)
+ "r.wb.stb:%x",
+ r.req_adr, rarange, r.wb.stb)
# Incoming acks processing
with m.If(bus.ack):
- sync += Display("WB_IN_ACK data:%x stbs_zero:%x "
- "stbs_done:%x",
- bus.dat_r, stbs_zero, stbs_done)
+ sync += Display("WB_IN_ACK data:%x", bus.dat_r)
sync += r.rows_valid[r.store_row % self.ROW_PER_LINE].eq(1)
# Check for completion
- with m.If(stbs_done & self.is_last_row(r.store_row, r.end_row_ix)):
+ with m.If(self.is_last_row(r.store_row, r.end_row_ix)):
# Complete wishbone cycle
sync += r.wb.cyc.eq(0)
# be nice, clear addr
stall_in, flush_in = self.stall_in, self.flush_in
inval_in = self.inval_in
- stbs_done = Signal()
-
comb += r.wb.sel.eq(-1)
comb += r.wb.adr.eq(r.req_adr[3:])
cache_valids)
self.icache_miss_wait_ack(m, r, replace_way, inval_in,
- cache_valids, stbs_done)
+ cache_valids)
# TLB miss and protection fault processing
with m.If(flush_in | m_in.tlbld):
pspec = TestMemPspec(addr_wid=32,
mask_wid=8,
reg_wid=64,
+ XLEN=32,
)
dut = ICache(pspec)
from soc.config.test.test_loadstore import TestMemPspec
pspec = TestMemPspec(addr_wid=64,
mask_wid=8,
+ XLEN=32,
reg_wid=64,
)
dut = ICache(pspec)