3 # This file is Copyright (c) 2018-2020 Florent Kermarrec <florent@enjoy-digital.fr>
4 # This file is Copyright (c) 2020 Stefan Schrijvers <ximin@ximinity.net>
8 LiteDRAM standalone core generator
10 LiteDRAM aims to be directly used as a python package when the SoC is created using LiteX. However,
11 for some use cases it could be interesting to generate a standalone verilog file of the core:
12 - integration of the core in a SoC using a more traditional flow.
13 - need to version/package the core.
14 - avoid Migen/LiteX dependencies.
17 The standalone core is generated from a YAML configuration file that allows the user to generate
18 easily a custom configuration of the core.
20 Current version of the generator is limited to DDR2/DDR3 Xilinx 7-Series FPGA and DDR3 on Lattice
32 from migen
.genlib
.resetsync
import AsyncResetSynchronizer
34 from litex
.build
.tools
import replace_in_file
35 from litex
.build
.generic_platform
import *
36 from litex
.build
.xilinx
import XilinxPlatform
37 from litex
.build
.lattice
import LatticePlatform
38 from litex
.boards
.platforms
import versa_ecp5
40 from litex
.soc
.cores
.clock
import *
41 from litex
.soc
.integration
.soc_core
import *
42 from litex
.soc
.integration
.builder
import *
43 from litex
.soc
.interconnect
import wishbone
44 from litex
.soc
.cores
.uart
import *
46 from gram
import modules
as litedram_modules
47 from gram
import phy
as litedram_phys
48 from gram
.phy
.ecp5ddrphy
import ECP5DDRPHY
49 from gram
.phy
.s7ddrphy
import S7DDRPHY
50 from gram
.core
.controller
import ControllerSettings
51 from gram
.frontend
.axi
import *
52 from gram
.frontend
.wishbone
import *
53 from gram
.frontend
.bist
import LiteDRAMBISTGenerator
54 from gram
.frontend
.bist
import LiteDRAMBISTChecker
55 from gram
.frontend
.fifo
import LiteDRAMFIFO
57 # IOs/Interfaces -----------------------------------------------------------------------------------
68 Subsignal("tx", Pins(1)),
69 Subsignal("rx", Pins(1))
73 ("pll_locked", 0, Pins(1)),
76 ("init_done", 0, Pins(1)),
77 ("init_error", 0, Pins(1)),
80 ("clk_iodelay", 0, Pins(1)),
81 ("rst_iodelay", 0, Pins(1)),
84 ("user_clk", 0, Pins(1)),
85 ("user_rst", 0, Pins(1))
89 def get_dram_ios(core_config
):
90 sdram_module
= core_config
["sdram_module"]
94 log2_int(core_config
["sdram_module"].nrows
))),
96 log2_int(core_config
["sdram_module"].nbanks
))),
97 Subsignal("ras_n", Pins(1)),
98 Subsignal("cas_n", Pins(1)),
99 Subsignal("we_n", Pins(1)),
100 Subsignal("cs_n", Pins(core_config
["sdram_rank_nb"])),
101 Subsignal("dm", Pins(core_config
["sdram_module_nb"])),
102 Subsignal("dq", Pins(8*core_config
["sdram_module_nb"])),
103 Subsignal("dqs_p", Pins(core_config
["sdram_module_nb"])),
104 Subsignal("dqs_n", Pins(core_config
["sdram_module_nb"])),
105 Subsignal("clk_p", Pins(core_config
["sdram_rank_nb"])),
106 Subsignal("clk_n", Pins(core_config
["sdram_rank_nb"])),
107 Subsignal("cke", Pins(core_config
["sdram_rank_nb"])),
108 Subsignal("odt", Pins(core_config
["sdram_rank_nb"])),
109 Subsignal("reset_n", Pins(1))
114 def get_native_user_port_ios(_id
, aw
, dw
):
116 ("user_port_{}".format(_id
), 0,
118 Subsignal("cmd_valid", Pins(1)),
119 Subsignal("cmd_ready", Pins(1)),
120 Subsignal("cmd_we", Pins(1)),
121 Subsignal("cmd_addr", Pins(aw
)),
124 Subsignal("wdata_valid", Pins(1)),
125 Subsignal("wdata_ready", Pins(1)),
126 Subsignal("wdata_we", Pins(dw
//8)),
127 Subsignal("wdata_data", Pins(dw
)),
130 Subsignal("rdata_valid", Pins(1)),
131 Subsignal("rdata_ready", Pins(1)),
132 Subsignal("rdata_data", Pins(dw
))
137 def get_wishbone_user_port_ios(_id
, aw
, dw
):
139 ("user_port_{}".format(_id
), 0,
140 Subsignal("adr", Pins(aw
)),
141 Subsignal("dat_w", Pins(dw
)),
142 Subsignal("dat_r", Pins(dw
)),
143 Subsignal("sel", Pins(dw
//8)),
144 Subsignal("cyc", Pins(1)),
145 Subsignal("stb", Pins(1)),
146 Subsignal("ack", Pins(1)),
147 Subsignal("we", Pins(1)),
148 Subsignal("err", Pins(1)),
153 def get_axi_user_port_ios(_id
, aw
, dw
, iw
):
155 ("user_port_{}".format(_id
), 0,
157 Subsignal("awvalid", Pins(1)),
158 Subsignal("awready", Pins(1)),
159 Subsignal("awaddr", Pins(aw
)),
160 Subsignal("awburst", Pins(2)),
161 Subsignal("awlen", Pins(8)),
162 Subsignal("awsize", Pins(4)),
163 Subsignal("awid", Pins(iw
)),
166 Subsignal("wvalid", Pins(1)),
167 Subsignal("wready", Pins(1)),
168 Subsignal("wlast", Pins(1)),
169 Subsignal("wstrb", Pins(dw
//8)),
170 Subsignal("wdata", Pins(dw
)),
173 Subsignal("bvalid", Pins(1)),
174 Subsignal("bready", Pins(1)),
175 Subsignal("bresp", Pins(2)),
176 Subsignal("bid", Pins(iw
)),
179 Subsignal("arvalid", Pins(1)),
180 Subsignal("arready", Pins(1)),
181 Subsignal("araddr", Pins(aw
)),
182 Subsignal("arburst", Pins(2)),
183 Subsignal("arlen", Pins(8)),
184 Subsignal("arsize", Pins(4)),
185 Subsignal("arid", Pins(iw
)),
188 Subsignal("rvalid", Pins(1)),
189 Subsignal("rready", Pins(1)),
190 Subsignal("rlast", Pins(1)),
191 Subsignal("rresp", Pins(2)),
192 Subsignal("rdata", Pins(dw
)),
193 Subsignal("rid", Pins(iw
))
198 def get_fifo_user_port_ios(_id
, dw
):
200 ("user_fifo_{}".format(_id
), 0,
202 Subsignal("in_valid", Pins(1)),
203 Subsignal("in_ready", Pins(1)),
204 Subsignal("in_data", Pins(dw
)),
207 Subsignal("out_valid", Pins(1)),
208 Subsignal("out_ready", Pins(1)),
209 Subsignal("out_data", Pins(dw
)),
214 class Platform(XilinxPlatform
):
216 XilinxPlatform
.__init
__(self
, "", io
=[], toolchain
="vivado")
218 # CRG ----------------------------------------------------------------------------------------------
221 class LiteDRAMECP5DDRPHYCRG(Module
):
222 def __init__(self
, platform
, core_config
):
223 self
.clock_domains
.cd_init
= ClockDomain()
224 self
.clock_domains
.cd_por
= ClockDomain(reset_less
=True)
225 self
.clock_domains
.cd_sys
= ClockDomain()
226 self
.clock_domains
.cd_sys2x
= ClockDomain()
227 self
.clock_domains
.cd_sys2x_i
= ClockDomain(reset_less
=True)
234 clk
= platform
.request("clk")
235 rst
= platform
.request("rst")
238 por_count
= Signal(16, reset
=2**16-1)
240 self
.comb
+= self
.cd_por
.clk
.eq(ClockSignal())
241 self
.comb
+= por_done
.eq(por_count
== 0)
242 self
.sync
.por
+= If(~por_done
, por_count
.eq(por_count
- 1))
245 self
.submodules
.pll
= pll
= ECP5PLL()
246 pll
.register_clkin(clk
, core_config
["input_clk_freq"])
247 pll
.create_clkout(self
.cd_sys2x_i
, 2*core_config
["sys_clk_freq"])
248 pll
.create_clkout(self
.cd_init
, core_config
["init_clk_freq"])
250 Instance("ECLKSYNCB",
251 i_ECLKI
=self
.cd_sys2x_i
.clk
,
253 o_ECLKO
=self
.cd_sys2x
.clk
),
257 i_CLKI
=self
.cd_sys2x
.clk
,
258 i_RST
=self
.cd_sys2x
.rst
,
259 o_CDIVX
=self
.cd_sys
.clk
),
260 AsyncResetSynchronizer(
261 self
.cd_init
, ~por_done | ~pll
.locked | rst
),
262 AsyncResetSynchronizer(
263 self
.cd_sys
, ~por_done | ~pll
.locked | rst
),
267 class LiteDRAMS7DDRPHYCRG(Module
):
268 def __init__(self
, platform
, core_config
):
269 self
.clock_domains
.cd_sys
= ClockDomain()
270 if core_config
["memtype"] == "DDR3":
271 self
.clock_domains
.cd_sys4x
= ClockDomain(reset_less
=True)
272 self
.clock_domains
.cd_sys4x_dqs
= ClockDomain(reset_less
=True)
274 self
.clock_domains
.cd_sys2x
= ClockDomain(reset_less
=True)
275 self
.clock_domains
.cd_sys2x_dqs
= ClockDomain(reset_less
=True)
276 self
.clock_domains
.cd_iodelay
= ClockDomain()
280 clk
= platform
.request("clk")
281 rst
= platform
.request("rst")
283 self
.submodules
.sys_pll
= sys_pll
= S7PLL(
284 speedgrade
=core_config
["speedgrade"])
285 self
.comb
+= sys_pll
.reset
.eq(rst
)
286 sys_pll
.register_clkin(clk
, core_config
["input_clk_freq"])
287 sys_pll
.create_clkout(self
.cd_sys
, core_config
["sys_clk_freq"])
288 if core_config
["memtype"] == "DDR3":
289 sys_pll
.create_clkout(self
.cd_sys4x
, 4*core_config
["sys_clk_freq"])
290 sys_pll
.create_clkout(self
.cd_sys4x_dqs
, 4 *
291 core_config
["sys_clk_freq"], phase
=90)
293 sys_pll
.create_clkout(self
.cd_sys2x
, 2*core_config
["sys_clk_freq"])
294 sys_pll
.create_clkout(self
.cd_sys2x_dqs
, 2 *
295 core_config
["sys_clk_freq"], phase
=90)
296 self
.comb
+= platform
.request("pll_locked").eq(sys_pll
.locked
)
298 self
.submodules
.iodelay_pll
= iodelay_pll
= S7PLL(
299 speedgrade
=core_config
["speedgrade"])
300 self
.comb
+= iodelay_pll
.reset
.eq(rst
)
301 iodelay_pll
.register_clkin(clk
, core_config
["input_clk_freq"])
302 iodelay_pll
.create_clkout(
303 self
.cd_iodelay
, core_config
["iodelay_clk_freq"])
304 self
.submodules
.idelayctrl
= S7IDELAYCTRL(self
.cd_iodelay
)
306 # LiteDRAMCoreControl ------------------------------------------------------------------------------
309 class LiteDRAMCoreControl(Module
, AutoCSR
):
311 self
.init_done
= CSRStorage()
312 self
.init_error
= CSRStorage()
314 # LiteDRAMCore -------------------------------------------------------------------------------------
317 class LiteDRAMCore(SoCCore
):
318 def __init__(self
, platform
, core_config
, **kwargs
):
319 platform
.add_extension(get_common_ios())
321 # Parameters -------------------------------------------------------------------------------
322 sys_clk_freq
= core_config
["sys_clk_freq"]
323 cpu_type
= core_config
["cpu"]
324 cpu_variant
= core_config
.get("cpu_variant", "standard")
325 csr_alignment
= core_config
.get("csr_alignment", 32)
327 kwargs
["integrated_rom_size"] = 0
328 kwargs
["integrated_sram_size"] = 0
329 kwargs
["with_uart"] = False
330 kwargs
["with_timer"] = False
331 kwargs
["with_ctrl"] = False
333 # SoCCore ----------------------------------------------------------------------------------
334 SoCCore
.__init
__(self
, platform
, sys_clk_freq
,
336 cpu_variant
=cpu_variant
,
337 csr_alignment
=csr_alignment
,
340 # CRG --------------------------------------------------------------------------------------
341 if core_config
["sdram_phy"] in [litedram_phys
.ECP5DDRPHY
]:
342 self
.submodules
.crg
= crg
= LiteDRAMECP5DDRPHYCRG(
343 platform
, core_config
)
344 if core_config
["sdram_phy"] in [litedram_phys
.A7DDRPHY
, litedram_phys
.K7DDRPHY
, litedram_phys
.V7DDRPHY
]:
345 self
.submodules
.crg
= LiteDRAMS7DDRPHYCRG(platform
, core_config
)
347 # DRAM -------------------------------------------------------------------------------------
348 platform
.add_extension(get_dram_ios(core_config
))
350 if core_config
["sdram_phy"] in [litedram_phys
.ECP5DDRPHY
]:
351 assert core_config
["memtype"] in ["DDR3"]
352 self
.submodules
.ddrphy
= core_config
["sdram_phy"](
353 pads
=platform
.request("ddram"),
354 sys_clk_freq
=sys_clk_freq
)
355 self
.comb
+= crg
.stop
.eq(self
.ddrphy
.init
.stop
)
356 self
.add_constant("ECP5DDRPHY")
357 sdram_module
= core_config
["sdram_module"](sys_clk_freq
, "1:2")
359 if core_config
["sdram_phy"] in [litedram_phys
.A7DDRPHY
, litedram_phys
.K7DDRPHY
, litedram_phys
.V7DDRPHY
]:
360 assert core_config
["memtype"] in ["DDR2", "DDR3"]
361 self
.submodules
.ddrphy
= core_config
["sdram_phy"](
362 pads
=platform
.request("ddram"),
363 memtype
=core_config
["memtype"],
364 nphases
=4 if core_config
["memtype"] == "DDR3" else 2,
365 sys_clk_freq
=sys_clk_freq
,
366 iodelay_clk_freq
=core_config
["iodelay_clk_freq"],
367 cmd_latency
=core_config
["cmd_latency"])
368 self
.add_constant("CMD_DELAY", core_config
["cmd_delay"])
369 if core_config
["memtype"] == "DDR3":
370 self
.ddrphy
.settings
.add_electrical_settings(
371 rtt_nom
=core_config
["rtt_nom"],
372 rtt_wr
=core_config
["rtt_wr"],
373 ron
=core_config
["ron"])
374 self
.add_csr("ddrphy")
376 sdram_module
= core_config
["sdram_module"](sys_clk_freq
,
377 "1:4" if core_config
["memtype"] == "DDR3" else "1:2")
378 controller_settings
= controller_settings
= ControllerSettings(
379 cmd_buffer_depth
=core_config
["cmd_buffer_depth"])
380 self
.add_sdram("sdram",
383 origin
=self
.mem_map
["main_ram"],
384 # Only expose 16MB to the CPU, enough for Init/Calib.
386 with_soc_interconnect
=cpu_type
is not None,
388 l2_cache_min_data_width
=0,
389 controller_settings
=controller_settings
,
392 # DRAM Control/Status ----------------------------------------------------------------------
393 # Expose calibration status to user.
394 self
.submodules
.ddrctrl
= LiteDRAMCoreControl()
395 self
.add_csr("ddrctrl")
396 self
.comb
+= platform
.request("init_done").eq(
397 self
.ddrctrl
.init_done
.storage
)
398 self
.comb
+= platform
.request("init_error").eq(
399 self
.ddrctrl
.init_error
.storage
)
400 # If no CPU, expose a bus control interface to user.
402 wb_bus
= wishbone
.Interface()
403 self
.bus
.add_master(master
=wb_bus
)
404 platform
.add_extension(wb_bus
.get_ios("wb_ctrl"))
405 wb_pads
= platform
.request("wb_ctrl")
406 self
.comb
+= wb_bus
.connect_to_pads(wb_pads
, mode
="slave")
408 # User ports -------------------------------------------------------------------------------
410 platform
.request("user_clk").eq(ClockSignal()),
411 platform
.request("user_rst").eq(ResetSignal())
413 for name
, port
in core_config
["user_ports"].items():
414 # Native -------------------------------------------------------------------------------
415 if port
["type"] == "native":
416 user_port
= self
.sdram
.crossbar
.get_port()
417 platform
.add_extension(get_native_user_port_ios(name
,
418 user_port
.address_width
,
419 user_port
.data_width
))
420 _user_port_io
= platform
.request("user_port_{}".format(name
))
423 user_port
.cmd
.valid
.eq(_user_port_io
.cmd_valid
),
424 _user_port_io
.cmd_ready
.eq(user_port
.cmd
.ready
),
425 user_port
.cmd
.we
.eq(_user_port_io
.cmd_we
),
426 user_port
.cmd
.addr
.eq(_user_port_io
.cmd_addr
),
429 user_port
.wdata
.valid
.eq(_user_port_io
.wdata_valid
),
430 _user_port_io
.wdata_ready
.eq(user_port
.wdata
.ready
),
431 user_port
.wdata
.we
.eq(_user_port_io
.wdata_we
),
432 user_port
.wdata
.data
.eq(_user_port_io
.wdata_data
),
435 _user_port_io
.rdata_valid
.eq(user_port
.rdata
.valid
),
436 user_port
.rdata
.ready
.eq(_user_port_io
.rdata_ready
),
437 _user_port_io
.rdata_data
.eq(user_port
.rdata
.data
),
439 # Wishbone -----------------------------------------------------------------------------
440 elif port
["type"] == "wishbone":
441 user_port
= self
.sdram
.crossbar
.get_port()
442 wb_port
= wishbone
.Interface(
443 user_port
.data_width
,
444 user_port
.address_width
)
445 wishbone2native
= LiteDRAMWishbone2Native(wb_port
, user_port
)
446 self
.submodules
+= wishbone2native
447 platform
.add_extension(get_wishbone_user_port_ios(name
,
450 _wb_port_io
= platform
.request("user_port_{}".format(name
))
452 wb_port
.adr
.eq(_wb_port_io
.adr
),
453 wb_port
.dat_w
.eq(_wb_port_io
.dat_w
),
454 _wb_port_io
.dat_r
.eq(wb_port
.dat_r
),
455 wb_port
.sel
.eq(_wb_port_io
.sel
),
456 wb_port
.cyc
.eq(_wb_port_io
.cyc
),
457 wb_port
.stb
.eq(_wb_port_io
.stb
),
458 _wb_port_io
.ack
.eq(wb_port
.ack
),
459 wb_port
.we
.eq(_wb_port_io
.we
),
460 _wb_port_io
.err
.eq(wb_port
.err
),
462 # AXI ----------------------------------------------------------------------------------
463 elif port
["type"] == "axi":
464 user_port
= self
.sdram
.crossbar
.get_port()
465 axi_port
= LiteDRAMAXIPort(
466 user_port
.data_width
,
467 user_port
.address_width
+
468 log2_int(user_port
.data_width
//8),
470 axi2native
= LiteDRAMAXI2Native(axi_port
, user_port
)
471 self
.submodules
+= axi2native
472 platform
.add_extension(get_axi_user_port_ios(name
,
473 axi_port
.address_width
,
476 _axi_port_io
= platform
.request("user_port_{}".format(name
))
479 axi_port
.aw
.valid
.eq(_axi_port_io
.awvalid
),
480 _axi_port_io
.awready
.eq(axi_port
.aw
.ready
),
481 axi_port
.aw
.addr
.eq(_axi_port_io
.awaddr
),
482 axi_port
.aw
.burst
.eq(_axi_port_io
.awburst
),
483 axi_port
.aw
.len.eq(_axi_port_io
.awlen
),
484 axi_port
.aw
.size
.eq(_axi_port_io
.awsize
),
485 axi_port
.aw
.id.eq(_axi_port_io
.awid
),
488 axi_port
.w
.valid
.eq(_axi_port_io
.wvalid
),
489 _axi_port_io
.wready
.eq(axi_port
.w
.ready
),
490 axi_port
.w
.last
.eq(_axi_port_io
.wlast
),
491 axi_port
.w
.strb
.eq(_axi_port_io
.wstrb
),
492 axi_port
.w
.data
.eq(_axi_port_io
.wdata
),
495 _axi_port_io
.bvalid
.eq(axi_port
.b
.valid
),
496 axi_port
.b
.ready
.eq(_axi_port_io
.bready
),
497 _axi_port_io
.bresp
.eq(axi_port
.b
.resp
),
498 _axi_port_io
.bid
.eq(axi_port
.b
.id),
501 axi_port
.ar
.valid
.eq(_axi_port_io
.arvalid
),
502 _axi_port_io
.arready
.eq(axi_port
.ar
.ready
),
503 axi_port
.ar
.addr
.eq(_axi_port_io
.araddr
),
504 axi_port
.ar
.burst
.eq(_axi_port_io
.arburst
),
505 axi_port
.ar
.len.eq(_axi_port_io
.arlen
),
506 axi_port
.ar
.size
.eq(_axi_port_io
.arsize
),
507 axi_port
.ar
.id.eq(_axi_port_io
.arid
),
510 _axi_port_io
.rvalid
.eq(axi_port
.r
.valid
),
511 axi_port
.r
.ready
.eq(_axi_port_io
.rready
),
512 _axi_port_io
.rlast
.eq(axi_port
.r
.last
),
513 _axi_port_io
.rresp
.eq(axi_port
.r
.resp
),
514 _axi_port_io
.rdata
.eq(axi_port
.r
.data
),
515 _axi_port_io
.rid
.eq(axi_port
.r
.id),
517 # FIFO ---------------------------------------------------------------------------------
518 elif port
["type"] == "fifo":
519 platform
.add_extension(
520 get_fifo_user_port_ios(name
, user_port
.data_width
))
521 _user_fifo_io
= platform
.request("user_fifo_{}".format(name
))
523 data_width
=user_port
.data_width
,
526 write_port
=self
.sdram
.crossbar
.get_port("write"),
527 write_threshold
=port
["depth"] - 32, # FIXME
528 read_port
=self
.sdram
.crossbar
.get_port("read"),
529 read_threshold
=32 # FIXME
531 self
.submodules
+= fifo
534 fifo
.sink
.valid
.eq(_user_fifo_io
.in_valid
),
535 _user_fifo_io
.in_ready
.eq(fifo
.sink
.ready
),
536 fifo
.sink
.data
.eq(_user_fifo_io
.in_data
),
539 _user_fifo_io
.out_valid
.eq(fifo
.source
.valid
),
540 fifo
.source
.ready
.eq(_user_fifo_io
.out_ready
),
541 _user_fifo_io
.out_data
.eq(fifo
.source
.data
),
545 "Unsupported port type: {}".format(port
["type"]))
547 # Build --------------------------------------------------------------------------------------------
551 parser
= argparse
.ArgumentParser(
552 description
="LiteDRAM standalone core generator")
554 parser
.set_defaults(output_dir
="build")
555 parser
.add_argument("config", help="YAML config file")
556 args
= parser
.parse_args()
557 core_config
= yaml
.load(open(args
.config
).read(), Loader
=yaml
.Loader
)
559 # Convert YAML elements to Python/LiteX --------------------------------------------------------
560 for k
, v
in core_config
.items():
561 replaces
= {"False": False, "True": True, "None": None}
562 for r
in replaces
.keys():
564 core_config
[k
] = replaces
[r
]
566 core_config
[k
] = float(core_config
[k
])
567 if k
== "sdram_module":
568 core_config
[k
] = getattr(litedram_modules
, core_config
[k
])
570 core_config
[k
] = getattr(litedram_phys
, core_config
[k
])
572 # Generate core --------------------------------------------------------------------------------
573 if core_config
["sdram_phy"] in [litedram_phys
.ECP5DDRPHY
]:
574 # FIXME: allow other devices.
575 platform
= LatticePlatform(
576 "LFE5UM5G-45F-8BG381C", io
=[], toolchain
="trellis")
577 elif core_config
["sdram_phy"] in [litedram_phys
.A7DDRPHY
, litedram_phys
.K7DDRPHY
, litedram_phys
.V7DDRPHY
]:
578 platform
= XilinxPlatform("", io
=[], toolchain
="vivado")
580 raise ValueError("Unsupported SDRAM PHY: {}".format(
581 core_config
["sdram_phy"]))
583 builder_arguments
= builder_argdict(args
)
584 builder_arguments
["compile_gateware"] = False
586 soc
= LiteDRAMCore(platform
, core_config
, integrated_rom_size
=0x6000)
587 builder
= Builder(soc
, **builder_arguments
)
588 vns
= builder
.build(build_name
="litedram_core", regular_comb
=False)
590 if soc
.cpu_type
is not None:
591 init_filename
= "mem.init"
592 os
.system("mv {} {}".format(
593 os
.path
.join(builder
.gateware_dir
, init_filename
),
594 os
.path
.join(builder
.gateware_dir
, "litedram_core.init"),
596 replace_in_file(os
.path
.join(builder
.gateware_dir
,
597 "litedram_core.v"), init_filename
, "litedram_core.init")
600 if __name__
== "__main__":