bank/description/CSRStorage: support alignment bits

This commit is contained in:
Sebastien Bourdeauducq 2013-04-30 18:53:40 +02:00
parent 51f1ace061
commit dc0304a87b
1 changed files with 17 additions and 9 deletions

View File

@ -47,14 +47,17 @@ class CSRStatus(_CompoundCSR):
self.simple_csrs.append(sc) self.simple_csrs.append(sc)
class CSRStorage(_CompoundCSR): class CSRStorage(_CompoundCSR):
def __init__(self, size=1, reset=0, atomic_write=False, write_from_dev=False, name=None): def __init__(self, size=1, reset=0, atomic_write=False, write_from_dev=False, alignment_bits=0, name=None):
_CompoundCSR.__init__(self, size, name) _CompoundCSR.__init__(self, size, name)
self.storage = Signal(self.size, reset=reset) self.alignment_bits = alignment_bits
self.storage_full = Signal(self.size, reset=reset)
self.storage = Signal(self.size - self.alignment_bits)
self.comb += self.storage.eq(self.storage_full[self.alignment_bits:])
self.atomic_write = atomic_write self.atomic_write = atomic_write
if write_from_dev: if write_from_dev:
self.we = Signal() self.we = Signal()
self.dat_w = Signal(self.size) self.dat_w = Signal(self.size - self.alignment_bits)
self.sync += If(self.we, self.storage.eq(self.dat_w)) self.sync += If(self.we, self.storage_full.eq(self.dat_w << self.alignment_bits))
def do_finalize(self, busword): def do_finalize(self, busword):
nwords = (self.size + busword - 1)//busword nwords = (self.size + busword - 1)//busword
@ -63,20 +66,25 @@ class CSRStorage(_CompoundCSR):
for i in reversed(range(nwords)): for i in reversed(range(nwords)):
nbits = min(self.size - i*busword, busword) nbits = min(self.size - i*busword, busword)
sc = CSR(nbits, self.name + str(i) if nwords else self.name) sc = CSR(nbits, self.name + str(i) if nwords else self.name)
self.simple_csrs.append(sc)
lo = i*busword lo = i*busword
hi = lo+nbits hi = lo+nbits
# read # read
self.comb += sc.w.eq(self.storage[lo:hi]) if lo >= self.alignment_bits:
self.comb += sc.w.eq(self.storage_full[lo:hi])
elif hi > self.alignment_bits:
self.comb += sc.w.eq(Cat(Replicate(0, hi - self.alignment_bits),
self.storage_full[self.alignment_bits:hi]))
else:
self.comb += sc.w.eq(0)
# write # write
if nwords > 1 and self.atomic_write: if nwords > 1 and self.atomic_write:
if i: if i:
self.sync += If(sc.re, backstore[lo-busword:hi-busword].eq(sc.r)) self.sync += If(sc.re, backstore[lo-busword:hi-busword].eq(sc.r))
else: else:
self.sync += If(sc.re, self.storage.eq(Cat(sc.r, backstore))) self.sync += If(sc.re, self.storage_full.eq(Cat(sc.r, backstore)))
else: else:
self.sync += If(sc.re, self.storage[lo:hi].eq(sc.r)) self.sync += If(sc.re, self.storage_full[lo:hi].eq(sc.r))
self.simple_csrs.append(sc)
def csrprefix(prefix, csrs): def csrprefix(prefix, csrs):
for csr in csrs: for csr in csrs: