2 use ieee.std_logic_1164.all;
3 use ieee.std_logic_arith.all;
4 use ieee.std_logic_unsigned.all;
5 use ieee.numeric_std.all;
8 use unisim.vcomponents.all;
11 use work.lx_rocon_pkg.all;
13 -- lx_rocon_top - wires the modules with the outside world
15 -- ======================================================
16 -- MASTER CPU EXTERNAL MEMORY BUS
17 -- ======================================================
19 -- Master cpu memory bus has the following wires:
21 -- - address[15..0] The address, used to mark chip enable
22 -- - data_in[31..0] The data coming to bus
23 -- - data_out[31..0] The data coming from bus, multiplexed
24 -- - bls[3..0] Write enable for respective bytes
26 entity lx_rocon_top is
30 --clk_cpu : in std_logic;
31 clk_50m : in std_logic;
33 cs0_xc : in std_logic;
36 bls : in std_logic_vector(3 downto 0);
37 address : in std_logic_vector(15 downto 0);
38 data : inout std_logic_vector(31 downto 0);
40 irc0_a : in std_logic;
41 irc0_b : in std_logic;
42 irc0_index : in std_logic;
43 irc0_mark : in std_logic;
45 irc1_a : in std_logic;
46 irc1_b : in std_logic;
47 irc1_index : in std_logic;
48 irc1_mark : in std_logic;
50 irc2_a : in std_logic;
51 irc2_b : in std_logic;
52 irc2_index : in std_logic;
53 irc2_mark : in std_logic;
55 irc3_a : in std_logic;
56 irc3_b : in std_logic;
57 irc3_index : in std_logic;
58 irc3_mark : in std_logic;
60 irc4_a : in std_logic;
61 irc4_b : in std_logic;
62 irc4_index : in std_logic;
63 irc4_mark : in std_logic;
65 irc5_a : in std_logic;
66 irc5_b : in std_logic;
67 irc5_index : in std_logic;
68 irc5_mark : in std_logic;
70 irc6_a : in std_logic;
71 irc6_b : in std_logic;
72 irc6_index : in std_logic;
73 irc6_mark : in std_logic;
75 irc7_a : in std_logic;
76 irc7_b : in std_logic;
77 irc7_index : in std_logic;
78 irc7_mark : in std_logic;
82 s1_clk_in : in std_logic;
83 s1_miso : in std_logic;
84 s1_sync_in : in std_logic;
86 s1_clk_out : out std_logic;
87 s1_mosi : out std_logic;
88 s1_sync_out : out std_logic
92 architecture Behavioral of lx_rocon_top is
95 signal reset_s : std_logic;
96 signal init_s : std_logic;
97 -- Peripherals on the memory buses
98 -- Master to Tumbl DMEM / IMEM (Master)
99 signal tumbl_out_s : std_logic_vector(31 downto 0);
100 signal tumbl_ce_s : std_logic;
101 -- Measurement (Master)
102 signal meas_out_s : std_logic_vector(31 downto 0);
103 signal meas_ce_s : std_logic;
104 -- Master to Tumbl XMEM
105 signal master_tumbl_xmem_out_s : std_logic_vector(31 downto 0);
106 signal master_tumbl_xmem_ce_s : std_logic;
107 signal master_tumbl_xmem_lock_s : std_logic;
109 signal irc_proc_out_s : std_logic_vector(31 downto 0);
110 signal irc_proc_ce_s : std_logic;
111 signal irc_proc_next_ce_s : std_logic;
113 signal lxmaster_out_s : std_logic_vector(15 downto 0);
114 signal lxmaster_ce_s : std_logic;
115 signal lxmaster_next_ce_s : std_logic;
116 -- Signals for external bus transmission
117 signal data_i_s : std_logic_vector(31 downto 0);
118 signal data_o_s : std_logic_vector(31 downto 0);
119 -- Signals for internal transaction
120 signal last_address_s : std_logic_vector(15 downto 0);
121 signal last_rd_s : std_logic;
122 signal last_bls_s : std_logic_vector(3 downto 0);
124 -- Reading logic for Master CPU:
125 -- Broadcast rd only till ta (transaction acknowledge)
126 -- is received, then latch the data till the state of
127 -- rd or address changes
129 -- Data latching is synchronous - it's purpose is to
130 -- provide stable data for CPU on the bus
131 signal rd_f_s : std_logic; -- Filtered RD
132 signal rd_d_s : std_logic; -- D over RD
133 signal i_rd_s : std_logic; -- Internal bus RD (active 1)
134 signal last_i_rd_s : std_logic; -- Delayed RD bus, used for latching
136 signal address_f_s : std_logic_vector(15 downto 0); -- Filtered address
137 signal address_d_s : std_logic_vector(15 downto 0); -- D over address
139 signal data_read_s : std_logic_vector(31 downto 0); -- Latched read data
142 signal bls_f_s : std_logic_vector(3 downto 0); -- Filtered BLS
143 signal bls_d_s : std_logic_vector(3 downto 0); -- D over BLS
144 signal i_bls_s : std_logic_vector(3 downto 0); -- Internal BLS (active 1)
146 signal data_write_s : std_logic_vector(31 downto 0); -- Data broadcasted to write
149 signal tumbl_bls_s : std_logic_vector(3 downto 0);
150 signal tumbl_address_s : std_logic_vector(14 downto 0);
151 signal tumbl_data_i_s : std_logic_vector(31 downto 0);
153 signal tumbl_xmemb_o_s : CORE2DMEMB_Type;
154 signal tumbl_xmemb_i_s : DMEMB2CORE_Type;
155 signal tumbl_xmemb_sel_s : std_logic;
160 memory_bus_tumbl: bus_tumbl
167 address_i => address_f_s(11 downto 0),
169 data_o => tumbl_out_s,
171 xmemb_o => tumbl_xmemb_o_s,
172 xmemb_i => tumbl_xmemb_i_s,
173 xmemb_sel_o => tumbl_xmemb_sel_s
177 memory_bus_measurement: bus_measurement
183 address_i => address_f_s(1 downto 0),
190 memory_bus_irc: bus_irc
196 address_i => tumbl_address_s(4 downto 0),
197 next_ce_i => irc_proc_next_ce_s,
198 data_i => tumbl_data_i_s,
199 data_o => irc_proc_out_s,
200 bls_i => tumbl_bls_s,
202 irc_i(0).a => irc0_a,
203 irc_i(0).b => irc0_b,
204 irc_i(0).index => irc0_index,
205 irc_i(0).mark => irc0_mark,
207 irc_i(1).a => irc1_a,
208 irc_i(1).b => irc1_b,
209 irc_i(1).index => irc1_index,
210 irc_i(1).mark => irc1_mark,
212 irc_i(2).a => irc2_a,
213 irc_i(2).b => irc2_b,
214 irc_i(2).index => irc2_index,
215 irc_i(2).mark => irc2_mark,
217 irc_i(3).a => irc3_a,
218 irc_i(3).b => irc3_b,
219 irc_i(3).index => irc3_index,
220 irc_i(3).mark => irc3_mark,
222 irc_i(4).a => irc4_a,
223 irc_i(4).b => irc4_b,
224 irc_i(4).index => irc4_index,
225 irc_i(4).mark => irc4_mark,
227 irc_i(5).a => irc5_a,
228 irc_i(5).b => irc5_b,
229 irc_i(5).index => irc5_index,
230 irc_i(5).mark => irc5_mark,
232 irc_i(6).a => irc6_a,
233 irc_i(6).b => irc6_b,
234 irc_i(6).index => irc6_index,
235 irc_i(6).mark => irc6_mark,
237 irc_i(7).a => irc7_a,
238 irc_i(7).b => irc7_b,
239 irc_i(7).index => irc7_index,
240 irc_i(7).mark => irc7_mark
244 memory_bus_lxmaster: bus_lxmaster
250 address_i => tumbl_address_s(10 downto 0),
251 next_ce_i => lxmaster_next_ce_s,
252 data_i => tumbl_data_i_s(15 downto 0),
253 data_o => lxmaster_out_s,
254 bls_i => tumbl_bls_s(1 downto 0),
256 clock_i => s1_clk_in,
258 sync_i => s1_sync_in,
260 clock_o => s1_clk_out,
262 sync_o => s1_sync_out
279 bls_f_s <= bls when bls = bls_d_s else "1111";
280 rd_f_s <= rd when rd = rd_d_s else '1';
281 address_f_s <= address when address = address_d_s else last_address_s; -- Use last address on mismatch!
284 data_i_s <= data_write_s when i_bls_s /= "0000" else (others => '0');
287 tumbl_bls_s <= i_bls_s when (master_tumbl_xmem_lock_s = '1')
288 else tumbl_xmemb_o_s.bls when (tumbl_xmemb_sel_s = '1')
290 tumbl_address_s <= address_f_s(14 downto 0) when (master_tumbl_xmem_lock_s = '1')
291 else tumbl_xmemb_o_s.addr when (tumbl_xmemb_sel_s = '1')
292 else (others => '0');
293 tumbl_data_i_s <= data_i_s when (master_tumbl_xmem_lock_s = '1')
294 else tumbl_xmemb_o_s.data when (tumbl_xmemb_sel_s = '1')
295 else (others => '0');
297 tumbl_xmemb_i_s.int <= '0'; -- No interrupt
298 -- Enable clken only when available for Tumbl
299 tumbl_xmemb_i_s.clken <= not master_tumbl_xmem_lock_s;
306 wait until clk_50m = '1' and clk_50m'event;
312 -- Check if we have chip select
319 if (last_rd_s = '1' or last_address_s /= address_f_s) then
323 if i_rd_s = '0' and last_i_rd_s = '1' then
324 -- Latch data we just read - they are valid in this cycle
325 data_read_s <= data_o_s;
328 last_address_s <= address_f_s;
330 -- Not reading, anything goes
331 data_read_s <= (others => 'X');
337 if bls_f_s /= "1111" then
340 if (last_bls_s /= bls_f_s or last_address_s /= address_f_s) then
341 i_bls_s <= not bls_f_s;
344 last_address_s <= address_f_s;
347 last_bls_s <= bls_f_s;
351 -- Set last read / bls to '1' if CS0 is not asserted
353 last_bls_s <= (others => '1');
354 last_address_s <= address_d_s;
361 address_d_s <= address;
363 last_i_rd_s <= i_rd_s;
365 -- ======================================================
367 -- ======================================================
369 -- Just copy these to their desired next state
370 irc_proc_ce_s <= irc_proc_next_ce_s;
371 lxmaster_ce_s <= lxmaster_next_ce_s;
375 -- Do the actual wiring here
377 process(cs0_xc, address_f_s, tumbl_out_s, meas_out_s, master_tumbl_xmem_out_s)
380 -- Inactive by default
383 master_tumbl_xmem_ce_s <= '0';
384 data_o_s <= (others => '0');
388 -- Memory Map (16-bit address @ 32-bit each)
390 -- Each address is seen as 32-bit entry now
391 -- 0x0000 - 0x0FFF: Tumbl IMEM / DMEM
392 -- 0x1FFC - 0x1FFF: Measurement
393 -- 0x8000 - 0x8FFF: Tumbl BUS
395 if address_f_s < "0001000000000000" then -- Tumbl
397 data_o_s <= tumbl_out_s;
398 elsif address_f_s(15 downto 2) = "00011111111111" then -- Measurement
400 data_o_s <= meas_out_s;
401 elsif address_f_s(15) = '1' then -- Tumbl External BUS
402 master_tumbl_xmem_ce_s <= '1';
403 data_o_s <= master_tumbl_xmem_out_s;
410 -- If RD and BLS is not high, we must keep DATA at high impedance
411 -- or the FPGA collides with SDRAM (damaging each other)
413 process(cs0_xc, rd, data, data_read_s)
416 -- CS0 / RD / BLS are active LOW
417 if cs0_xc = '0' and rd = '0' then
418 -- Don't risk flipping (between data_o_s and latched data_read_s, it's better to wait)
419 -- Maybe check this later.
420 -- if last_i_rd_s = '1' then
427 data <= (others => 'Z');
430 data_write_s <= data;
434 -- Outputs from Tumbl (enabling and address muxing) and Master CPU
436 process(tumbl_xmemb_sel_s, tumbl_xmemb_o_s, master_tumbl_xmem_ce_s, address_f_s, i_rd_s, i_bls_s)
437 variable addr_v : std_logic_vector(14 downto 0); -- This space is visible by both (32-bit)
438 variable sel_v : std_logic;
442 irc_proc_next_ce_s <= '0';
443 lxmaster_next_ce_s <= '0';
444 master_tumbl_xmem_lock_s <= '0';
446 addr_v := (others => '0');
449 -- Check who is accessing
450 if master_tumbl_xmem_ce_s = '1' and (i_rd_s = '1' or i_bls_s /= "0000") then
451 -- Master blocks Tumbl
452 master_tumbl_xmem_lock_s <= '1';
453 addr_v := address_f_s(14 downto 0);
456 addr_v := tumbl_xmemb_o_s.addr;
461 -- IRC: 0x0800 - 0x081F (32-bit address)
462 -- LX MASTER: 0x1000 - 0x17FF (32-bit address)
463 if addr_v(14 downto 5) = "0001000000" then
464 irc_proc_next_ce_s <= '1';
465 elsif addr_v(14 downto 11) = "0010" then
466 lxmaster_next_ce_s <= '1';
472 -- Inputs to Tumbl (enabling and address muxing)
474 process(irc_proc_ce_s, irc_proc_out_s, lxmaster_ce_s, lxmaster_out_s, tumbl_xmemb_i_s)
477 tumbl_xmemb_i_s.data <= (others => 'X');
479 -- NOTE: This is input to Tumbl EXEQ - with MUL instruction for input > 18-bit,
480 -- (i.e. more DSPs in a sequence), this already has tough timing constraints
481 -- and SmartXplorer has to be used with XiSE or use Synplify.
482 if irc_proc_ce_s = '1' then
483 tumbl_xmemb_i_s.data <= irc_proc_out_s;
484 elsif lxmaster_ce_s = '1' then
485 tumbl_xmemb_i_s.data(15 downto 0) <= lxmaster_out_s;
486 tumbl_xmemb_i_s.data(31 downto 16) <= (others => '0');
489 master_tumbl_xmem_out_s <= tumbl_xmemb_i_s.data;