2014-08-06 07:26:00 -04:00
|
|
|
import os
|
|
|
|
from distutils.version import StrictVersion
|
|
|
|
|
2014-06-07 06:24:19 -04:00
|
|
|
from migen.fhdl.std import *
|
2014-08-06 07:26:00 -04:00
|
|
|
from migen.fhdl.specials import SynthesisDirective
|
|
|
|
from migen.genlib.cdc import *
|
2015-03-14 05:45:11 -04:00
|
|
|
from migen.genlib.resetsync import AsyncResetSynchronizer
|
|
|
|
from migen.genlib.io import *
|
2014-08-06 07:26:00 -04:00
|
|
|
from mibuild import tools
|
|
|
|
|
|
|
|
def settings(path, ver=None, sub=None):
|
|
|
|
vers = list(tools.versions(path))
|
|
|
|
if ver is None:
|
|
|
|
ver = max(vers)
|
|
|
|
else:
|
|
|
|
ver = StrictVersion(ver)
|
|
|
|
assert ver in vers
|
|
|
|
|
|
|
|
full = os.path.join(path, str(ver))
|
|
|
|
if sub:
|
|
|
|
full = os.path.join(full, sub)
|
|
|
|
|
|
|
|
search = [64, 32]
|
|
|
|
if tools.arch_bits() == 32:
|
|
|
|
search.reverse()
|
|
|
|
|
|
|
|
for b in search:
|
|
|
|
settings = os.path.join(full, "settings{0}.sh".format(b))
|
|
|
|
if os.path.exists(settings):
|
|
|
|
return settings
|
|
|
|
|
2015-03-13 18:17:45 -04:00
|
|
|
raise OSError("no settings file found")
|
2014-06-07 06:24:19 -04:00
|
|
|
|
2014-08-06 07:26:00 -04:00
|
|
|
class XilinxNoRetimingImpl(Module):
|
|
|
|
def __init__(self, reg):
|
|
|
|
self.specials += SynthesisDirective("attribute register_balancing of {r} is no", r=reg)
|
|
|
|
|
|
|
|
class XilinxNoRetiming:
|
|
|
|
@staticmethod
|
|
|
|
def lower(dr):
|
|
|
|
return XilinxNoRetimingImpl(dr.reg)
|
|
|
|
|
|
|
|
class XilinxMultiRegImpl(MultiRegImpl):
|
|
|
|
def __init__(self, *args, **kwargs):
|
|
|
|
MultiRegImpl.__init__(self, *args, **kwargs)
|
|
|
|
self.specials += [SynthesisDirective("attribute shreg_extract of {r} is no", r=r)
|
|
|
|
for r in self.regs]
|
|
|
|
|
|
|
|
class XilinxMultiReg:
|
|
|
|
@staticmethod
|
|
|
|
def lower(dr):
|
|
|
|
return XilinxMultiRegImpl(dr.i, dr.o, dr.odomain, dr.n)
|
|
|
|
|
2014-08-06 07:38:37 -04:00
|
|
|
class XilinxAsyncResetSynchronizerImpl(Module):
|
|
|
|
def __init__(self, cd, async_reset):
|
|
|
|
rst1 = Signal()
|
|
|
|
self.specials += [
|
|
|
|
Instance("FDPE", p_INIT=1, i_D=0, i_PRE=async_reset,
|
2014-08-06 11:51:50 -04:00
|
|
|
i_CE=1, i_C=cd.clk, o_Q=rst1),
|
2014-08-06 07:38:37 -04:00
|
|
|
Instance("FDPE", p_INIT=1, i_D=rst1, i_PRE=async_reset,
|
2014-08-06 11:51:50 -04:00
|
|
|
i_CE=1, i_C=cd.clk, o_Q=cd.rst)
|
2014-08-06 07:38:37 -04:00
|
|
|
]
|
|
|
|
|
|
|
|
class XilinxAsyncResetSynchronizer:
|
2014-08-06 11:58:09 -04:00
|
|
|
@staticmethod
|
2014-08-06 07:38:37 -04:00
|
|
|
def lower(dr):
|
|
|
|
return XilinxAsyncResetSynchronizerImpl(dr.cd, dr.async_reset)
|
|
|
|
|
2015-03-12 13:32:49 -04:00
|
|
|
class XilinxDifferentialInputImpl(Module):
|
|
|
|
def __init__(self, i_p, i_n, o):
|
|
|
|
self.specials += Instance("IBUFDS", i_I=i_p, i_IB=i_n, o_O=o)
|
|
|
|
|
|
|
|
class XilinxDifferentialInput:
|
|
|
|
@staticmethod
|
|
|
|
def lower(dr):
|
|
|
|
return XilinxDifferentialInputImpl(dr.i_p, dr.i_n, dr.o)
|
|
|
|
|
2015-03-12 14:30:57 -04:00
|
|
|
class XilinxDifferentialOutputImpl(Module):
|
|
|
|
def __init__(self, i, o_p, o_n):
|
|
|
|
self.specials += Instance("OBUFDS", i_I=i, o_O=o_p, o_OB=o_n)
|
|
|
|
|
|
|
|
class XilinxDifferentialOutput:
|
|
|
|
@staticmethod
|
|
|
|
def lower(dr):
|
|
|
|
return XilinxDifferentialOutputImpl(dr.i, dr.o_p, dr.o_n)
|
2015-03-14 05:45:11 -04:00
|
|
|
|
|
|
|
xilinx_special_overrides = {
|
|
|
|
NoRetiming: XilinxNoRetiming,
|
|
|
|
MultiReg: XilinxMultiReg,
|
|
|
|
AsyncResetSynchronizer: XilinxAsyncResetSynchronizer,
|
|
|
|
DifferentialInput: XilinxDifferentialInput,
|
|
|
|
DifferentialOutput: XilinxDifferentialOutput,
|
|
|
|
}
|