phy/gensdrphy: fix problems with half-rate phy, tested on minispartan6
This commit is contained in:
parent
7f55e2e2c5
commit
2c5fc6621a
|
@ -45,7 +45,8 @@ class ControllerSettings(Settings):
|
|||
class LiteDRAMController(Module):
|
||||
def __init__(self, phy_settings, geom_settings, timing_settings, clk_freq,
|
||||
controller_settings=ControllerSettings()):
|
||||
address_align = log2_int(burst_lengths[phy_settings.memtype])
|
||||
burst_length = phy_settings.nphases * (1 if phy_settings.memtype == "SDR" else 2)
|
||||
address_align = log2_int(burst_length)
|
||||
|
||||
# Settings ---------------------------------------------------------------------------------
|
||||
self.settings = controller_settings
|
||||
|
|
|
@ -20,7 +20,7 @@ cmds = {
|
|||
|
||||
def get_sdr_phy_init_sequence(phy_settings, timing_settings):
|
||||
cl = phy_settings.cl
|
||||
bl = 1
|
||||
bl = phy_settings.nphases
|
||||
mr = log2_int(bl) + (cl << 4)
|
||||
reset_dll = 1 << 8
|
||||
|
||||
|
|
|
@ -50,17 +50,15 @@ class GENSDRPHY(Module):
|
|||
pads.sel_group(pads_group)
|
||||
|
||||
# Addresses and Commands ---------------------------------------------------------------
|
||||
for i in range(len(pads.a)):
|
||||
self.specials += SDROutput(i=dfi.p0.address[i], o=pads.a[i], clk=ClockSignal("sys"))
|
||||
for i in range(len(pads.ba)):
|
||||
self.specials += SDROutput(i=dfi.p0.bank[i], o=pads.ba[i], clk=ClockSignal("sys"))
|
||||
self.specials += SDROutput(i=dfi.p0.cas_n, o=pads.cas_n, clk=ClockSignal("sys"))
|
||||
self.specials += SDROutput(i=dfi.p0.ras_n, o=pads.ras_n, clk=ClockSignal("sys"))
|
||||
self.specials += SDROutput(i=dfi.p0.we_n, o=pads.we_n, clk=ClockSignal("sys"))
|
||||
self.specials += [SDROutput(i=dfi.p0.address[i], o=pads.a[i]) for i in range(len(pads.a))]
|
||||
self.specials += [SDROutput(i=dfi.p0.bank[i], o=pads.ba[i]) for i in range(len(pads.ba))]
|
||||
self.specials += SDROutput(i=dfi.p0.cas_n, o=pads.cas_n)
|
||||
self.specials += SDROutput(i=dfi.p0.ras_n, o=pads.ras_n)
|
||||
self.specials += SDROutput(i=dfi.p0.we_n, o=pads.we_n)
|
||||
if hasattr(pads, "cke"):
|
||||
self.specials += SDROutput(i=dfi.p0.cke, o=pads.cke, clk=ClockSignal("sys"))
|
||||
self.specials += SDROutput(i=dfi.p0.cke, o=pads.cke)
|
||||
if hasattr(pads, "cs_n"):
|
||||
self.specials += SDROutput(i=dfi.p0.cs_n, o=pads.cs_n, clk=ClockSignal("sys"))
|
||||
self.specials += SDROutput(i=dfi.p0.cs_n, o=pads.cs_n)
|
||||
|
||||
# DQ/DM Data Path --------------------------------------------------------------------------
|
||||
for i in range(len(pads.dq)):
|
||||
|
@ -69,7 +67,6 @@ class GENSDRPHY(Module):
|
|||
o = dfi.p0.wrdata[i],
|
||||
oe = dfi.p0.wrdata_en,
|
||||
i = dfi.p0.rddata[i],
|
||||
clk = ClockSignal("sys")
|
||||
)
|
||||
if hasattr(pads, "dm"):
|
||||
for i in range(len(pads.dm)):
|
||||
|
@ -104,23 +101,36 @@ class HalfRateGENSDRPHY(Module):
|
|||
nranks = nranks,
|
||||
nphases = nphases,
|
||||
rdphase = 0,
|
||||
wrphase = 1,
|
||||
wrphase = 0,
|
||||
rdcmdphase = 1,
|
||||
wrcmdphase = 0,
|
||||
wrcmdphase = 1,
|
||||
cl = cl,
|
||||
read_latency = (cl + cmd_latency)//2 + 1,
|
||||
read_latency = (cl + cmd_latency)//2 + 2, # FIXME: should be possible to have 1 cycle less latency
|
||||
write_latency = 0
|
||||
)
|
||||
|
||||
# DFI adaptation ---------------------------------------------------------------------------
|
||||
self.dfi = dfi = Interface(addressbits, bankbits, nranks, databits, nphases)
|
||||
|
||||
# Select active sys2x phase
|
||||
# sys ----____----____
|
||||
# Clock ------------------------------------------------------------------------------------
|
||||
|
||||
# select active sys2x phase
|
||||
# sys_clk ----____----____
|
||||
# phase_sel 0 1 0 1
|
||||
# sys2x --__--__--__--__
|
||||
phase_sel = Signal(reset=1)
|
||||
self.sync.sys2x += phase_sel.eq(~phase_sel)
|
||||
self.phase_sel = phase_sel = Signal()
|
||||
phase_sys2x = Signal.like(phase_sel)
|
||||
phase_sys = Signal.like(phase_sys2x)
|
||||
|
||||
self.sync += phase_sys.eq(phase_sys2x)
|
||||
|
||||
self.sync.sys2x += [
|
||||
If(phase_sys2x == phase_sys,
|
||||
phase_sel.eq(0),
|
||||
).Else(
|
||||
phase_sel.eq(~phase_sel)
|
||||
),
|
||||
phase_sys2x.eq(~phase_sel)
|
||||
]
|
||||
|
||||
# Commands and address
|
||||
dfi_omit = set(["rddata", "rddata_valid", "wrdata_en"])
|
||||
|
@ -137,7 +147,7 @@ class HalfRateGENSDRPHY(Module):
|
|||
self.comb += full_rate_phy.dfi.phases[0].wrdata_en.eq(wr_data_en | wr_data_en_d)
|
||||
|
||||
# Reads
|
||||
rddata = Signal(2*databits)
|
||||
rddata = Signal(databits)
|
||||
rddata_valid = Signal()
|
||||
|
||||
self.sync.sys2x += [
|
||||
|
@ -149,5 +159,5 @@ class HalfRateGENSDRPHY(Module):
|
|||
dfi.phases[0].rddata.eq(rddata),
|
||||
dfi.phases[0].rddata_valid.eq(rddata_valid),
|
||||
dfi.phases[1].rddata.eq(full_rate_phy.dfi.phases[0].rddata),
|
||||
dfi.phases[1].rddata_valid.eq(full_rate_phy.dfi.phases[0].rddata_valid),
|
||||
dfi.phases[1].rddata_valid.eq(rddata_valid),
|
||||
]
|
||||
|
|
Loading…
Reference in New Issue