Automatically build CSR access functions
[litex.git] / top.py
1 from fractions import Fraction
2 from math import ceil
3 from operator import itemgetter
4
5 from migen.fhdl.structure import *
6 from migen.fhdl.module import Module
7 from migen.bus import wishbone, wishbone2asmi, csr, wishbone2csr, dfi
8 from migen.bank import csrgen
9
10 from milkymist import m1crg, lm32, norflash, uart, s6ddrphy, dfii, asmicon, \
11 identifier, timer, minimac3, framebuffer, asmiprobe, dvisampler
12 from cif import get_macros
13
14 MHz = 1000000
15 clk_freq = (83 + Fraction(1, 3))*MHz
16 sram_size = 4096 # in bytes
17 l2_size = 8192 # in bytes
18
19 clk_period_ns = 1000000000/clk_freq
20 def ns(t, margin=True):
21 if margin:
22 t += clk_period_ns/2
23 return ceil(t/clk_period_ns)
24
25 sdram_phy = asmicon.PhySettings(
26 dfi_d=64,
27 nphases=2,
28 rdphase=0,
29 wrphase=1
30 )
31 sdram_geom = asmicon.GeomSettings(
32 bank_a=2,
33 row_a=13,
34 col_a=10
35 )
36 sdram_timing = asmicon.TimingSettings(
37 tRP=ns(15),
38 tRCD=ns(15),
39 tWR=ns(15),
40 tREFI=ns(7800, False),
41 tRFC=ns(70),
42
43 CL=3,
44 rd_delay=4,
45
46 read_time=32,
47 write_time=16
48 )
49
50 version = get_macros("common/version.h")["VERSION"][1:-1]
51
52 class SoC(Module):
53 csr_base = 0xe0000000
54 csr_map = {
55 "uart": 0,
56 "dfii": 1,
57 "identifier": 2,
58 "timer0": 3,
59 "minimac": 4,
60 "fb": 5,
61 "asmiprobe": 6,
62 "dvisampler0": 7,
63 "dvisampler0_edid_mem": 8,
64 "dvisampler1": 9,
65 "dvisampler1_edid_mem": 10,
66 }
67
68 interrupt_map = {
69 "uart": 0,
70 "timer0": 1,
71 "minimac": 2,
72 }
73
74 def __init__(self):
75 #
76 # ASMI
77 #
78 self.submodules.asmicon = asmicon.ASMIcon(sdram_phy, sdram_geom, sdram_timing)
79 asmiport_wb = self.asmicon.hub.get_port()
80 asmiport_fb = self.asmicon.hub.get_port(2)
81 self.asmicon.finalize()
82
83 #
84 # DFI
85 #
86 self.submodules.ddrphy = s6ddrphy.S6DDRPHY(sdram_geom.mux_a, sdram_geom.bank_a, sdram_phy.dfi_d)
87 self.submodules.dfii = dfii.DFIInjector(sdram_geom.mux_a, sdram_geom.bank_a, sdram_phy.dfi_d,
88 sdram_phy.nphases)
89 self.submodules.dficon0 = dfi.Interconnect(self.dfii.master, self.ddrphy.dfi)
90 self.submodules.dficon1 = dfi.Interconnect(self.asmicon.dfi, self.dfii.slave)
91
92 #
93 # WISHBONE
94 #
95 self.submodules.cpu = lm32.LM32()
96 self.submodules.norflash = norflash.NorFlash(25, 12)
97 self.submodules.sram = wishbone.SRAM(sram_size)
98 self.submodules.minimac = minimac3.MiniMAC()
99 self.submodules.wishbone2asmi = wishbone2asmi.WB2ASMI(l2_size//4, asmiport_wb)
100 self.submodules.wishbone2csr = wishbone2csr.WB2CSR()
101
102 # norflash 0x00000000 (shadow @0x80000000)
103 # SRAM/debug 0x10000000 (shadow @0x90000000)
104 # USB 0x20000000 (shadow @0xa0000000)
105 # Ethernet 0x30000000 (shadow @0xb0000000)
106 # SDRAM 0x40000000 (shadow @0xc0000000)
107 # CSR bridge 0x60000000 (shadow @0xe0000000)
108 self.submodules.wishbonecon = wishbone.InterconnectShared(
109 [
110 self.cpu.ibus,
111 self.cpu.dbus
112 ], [
113 (lambda a: a[26:29] == 0, self.norflash.bus),
114 (lambda a: a[26:29] == 1, self.sram.bus),
115 (lambda a: a[26:29] == 3, self.minimac.membus),
116 (lambda a: a[27:29] == 2, self.wishbone2asmi.wishbone),
117 (lambda a: a[27:29] == 3, self.wishbone2csr.wishbone)
118 ],
119 register=True)
120
121 #
122 # CSR
123 #
124 self.submodules.uart = uart.UART(clk_freq, baud=115200)
125 self.submodules.identifier = identifier.Identifier(0x4D31, version, int(clk_freq))
126 self.submodules.timer0 = timer.Timer()
127 self.submodules.fb = framebuffer.Framebuffer(asmiport_fb)
128 self.submodules.asmiprobe = asmiprobe.ASMIprobe(self.asmicon.hub)
129 self.submodules.dvisampler0 = dvisampler.DVISampler("02")
130 self.submodules.dvisampler1 = dvisampler.DVISampler("02")
131
132 self.submodules.csrbankarray = csrgen.BankArray(self,
133 lambda name, memory: self.csr_map[name if memory is None else name + "_" + memory.name_override])
134 self.submodules.csrcon = csr.Interconnect(self.wishbone2csr.csr, self.csrbankarray.get_buses())
135
136 #
137 # Interrupts
138 #
139 for k, v in sorted(self.interrupt_map.items(), key=itemgetter(1)):
140 self.comb += self.cpu.interrupt[v].eq(getattr(self, k).ev.irq)
141
142 #
143 # Clocking
144 #
145 self.submodules.crg = m1crg.M1CRG(50*MHz, clk_freq)
146 self.comb += [
147 self.ddrphy.clk4x_wr_strb.eq(self.crg.clk4x_wr_strb),
148 self.ddrphy.clk4x_rd_strb.eq(self.crg.clk4x_rd_strb)
149 ]