reggae_eda 0.0.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/assets/Nexys4DDR_Master.xdc +255 -0
- data/assets/fifo.vhd +109 -0
- data/assets/flag_buf.vhd +45 -0
- data/assets/mod_m_counter.vhd +36 -0
- data/assets/slow_ticker.vhd +49 -0
- data/assets/uart.vhd +69 -0
- data/assets/uart_bus_master.vhd +256 -0
- data/assets/uart_rx.vhd +90 -0
- data/assets/uart_tx.vhd +102 -0
- data/bin/reggae +6 -0
- data/lib/reggae.rb +3 -0
- data/lib/reggae/ast.rb +72 -0
- data/lib/reggae/code.rb +55 -0
- data/lib/reggae/compiler.rb +110 -0
- data/lib/reggae/parser.rb +281 -0
- data/lib/reggae/pretty_printer.rb +107 -0
- data/lib/reggae/version.rb +3 -0
- data/lib/reggae/vhdl_generator.rb +973 -0
- data/lib/reggae/visitor.rb +107 -0
- data/tests/regmap.sexp +139 -0
- metadata +64 -0
@@ -0,0 +1,49 @@
|
|
1
|
+
library ieee;
|
2
|
+
use ieee.std_logic_1164.all;
|
3
|
+
use ieee.numeric_std.all;
|
4
|
+
|
5
|
+
entity slow_ticker is
|
6
|
+
generic(N : natural := 27);
|
7
|
+
port(
|
8
|
+
reset_n : in std_logic;
|
9
|
+
fast_clk : in std_logic;
|
10
|
+
slow_clk : out std_logic; --50% high/low
|
11
|
+
slow_tick : out std_logic --single pulse on positive edge
|
12
|
+
);
|
13
|
+
end entity;
|
14
|
+
|
15
|
+
architecture rtl of slow_ticker is
|
16
|
+
signal counter : unsigned(N-1 downto 0);
|
17
|
+
signal slow_clk_r,slow_clk_c : std_logic;
|
18
|
+
begin
|
19
|
+
|
20
|
+
counting : process(reset_n,fast_clk)
|
21
|
+
begin
|
22
|
+
if reset_n = '0' then
|
23
|
+
counter <= to_unsigned(0, N);
|
24
|
+
slow_clk_r <= '0';
|
25
|
+
elsif rising_edge(fast_clk) then
|
26
|
+
counter <= counter + 1;
|
27
|
+
slow_clk_r <= slow_clk_c;
|
28
|
+
end if;
|
29
|
+
end process;
|
30
|
+
|
31
|
+
slow_clk_c <= counter(N-1);
|
32
|
+
slow_clk <= slow_clk_r;
|
33
|
+
|
34
|
+
tick : process(reset_n,fast_clk)
|
35
|
+
begin
|
36
|
+
if reset_n = '0' then
|
37
|
+
slow_tick <= '0';
|
38
|
+
elsif rising_edge(fast_clk) then
|
39
|
+
if slow_clk_r='0' then
|
40
|
+
slow_tick <= slow_clk_c xor slow_clk_r;
|
41
|
+
else
|
42
|
+
slow_tick <= '0';
|
43
|
+
end if;
|
44
|
+
end if;
|
45
|
+
end process;
|
46
|
+
|
47
|
+
end rtl;
|
48
|
+
|
49
|
+
|
data/assets/uart.vhd
ADDED
@@ -0,0 +1,69 @@
|
|
1
|
+
-- Listing 7.4
|
2
|
+
library ieee;
|
3
|
+
use ieee.std_logic_1164.all;
|
4
|
+
use ieee.numeric_std.all;
|
5
|
+
entity uart is
|
6
|
+
generic(
|
7
|
+
-- Default setting:
|
8
|
+
-- 19,200 baud, 8 data bis, 1 stop its, 2^2 FIFO
|
9
|
+
DBIT : integer := 8; -- # data bits
|
10
|
+
SB_TICK : integer := 16; -- # ticks for stop bits, 16/24/32
|
11
|
+
-- for 1/1.5/2 stop bits
|
12
|
+
DVSR : integer := 163; -- baud rate divisor
|
13
|
+
-- DVSR = 50M/(16*baud rate)
|
14
|
+
DVSR_BIT : integer := 8; -- # bits of DVSR
|
15
|
+
FIFO_W : integer := 2 -- # addr bits of FIFO
|
16
|
+
-- # words in FIFO=2^FIFO_W
|
17
|
+
);
|
18
|
+
port(
|
19
|
+
clk, reset_n : in std_logic;
|
20
|
+
rd_uart, wr_uart : in std_logic;
|
21
|
+
rx : in std_logic;
|
22
|
+
w_data : in std_logic_vector(7 downto 0);
|
23
|
+
tx_full, rx_empty : out std_logic;
|
24
|
+
r_data : out std_logic_vector(7 downto 0);
|
25
|
+
tx : out std_logic
|
26
|
+
);
|
27
|
+
end uart;
|
28
|
+
|
29
|
+
architecture str_arch of uart is
|
30
|
+
signal tick : std_logic;
|
31
|
+
signal rx_done_tick : std_logic;
|
32
|
+
signal tx_fifo_out : std_logic_vector(7 downto 0);
|
33
|
+
signal rx_data_out : std_logic_vector(7 downto 0);
|
34
|
+
signal tx_empty, tx_fifo_not_empty : std_logic;
|
35
|
+
signal tx_done_tick : std_logic;
|
36
|
+
begin
|
37
|
+
|
38
|
+
baud_gen_unit : entity work.mod_m_counter(arch)
|
39
|
+
generic map(M => DVSR, N => DVSR_BIT)
|
40
|
+
port map(clk => clk, reset_n => reset_n,
|
41
|
+
q =>open, max_tick => tick);
|
42
|
+
|
43
|
+
uart_rx_unit : entity work.uart_rx(arch)
|
44
|
+
generic map(DBIT => DBIT, SB_TICK => SB_TICK)
|
45
|
+
port map(clk => clk, reset_n => reset_n, rx => rx,
|
46
|
+
s_tick => tick, rx_done_tick => rx_done_tick,
|
47
|
+
dout => rx_data_out);
|
48
|
+
|
49
|
+
fifo_rx_unit : entity work.fifo(arch)
|
50
|
+
generic map(B => DBIT, W => FIFO_W)
|
51
|
+
port map(clk => clk, reset_n => reset_n, rd => rd_uart,
|
52
|
+
wr => rx_done_tick, w_data => rx_data_out,
|
53
|
+
empty => rx_empty, full => open, r_data => r_data);
|
54
|
+
|
55
|
+
fifo_tx_unit : entity work.fifo(arch)
|
56
|
+
generic map(B => DBIT, W => FIFO_W)
|
57
|
+
port map(clk => clk, reset_n => reset_n, rd => tx_done_tick,
|
58
|
+
wr => wr_uart, w_data => w_data, empty => tx_empty,
|
59
|
+
full => tx_full, r_data => tx_fifo_out);
|
60
|
+
|
61
|
+
uart_tx_unit : entity work.uart_tx(arch)
|
62
|
+
generic map(DBIT => DBIT, SB_TICK => SB_TICK)
|
63
|
+
port map(clk => clk, reset_n => reset_n,
|
64
|
+
tx_start => tx_fifo_not_empty,
|
65
|
+
s_tick => tick, din => tx_fifo_out,
|
66
|
+
tx_done_tick => tx_done_tick, tx => tx);
|
67
|
+
|
68
|
+
tx_fifo_not_empty <= not tx_empty;
|
69
|
+
end str_arch;
|
@@ -0,0 +1,256 @@
|
|
1
|
+
library ieee;
|
2
|
+
use ieee.std_logic_1164.all;
|
3
|
+
use ieee.numeric_std.all;
|
4
|
+
|
5
|
+
entity uart_bus_master is
|
6
|
+
generic(
|
7
|
+
ADDR_WIDTH : natural :=8;
|
8
|
+
DATA_WIDTH : natural :=32
|
9
|
+
);
|
10
|
+
port(
|
11
|
+
reset_n : in std_logic;
|
12
|
+
clk : in std_logic;
|
13
|
+
-- UART side
|
14
|
+
rx : in std_logic;
|
15
|
+
tx : out std_logic;
|
16
|
+
-- Bus side
|
17
|
+
ce : out std_logic;
|
18
|
+
we : out std_logic;
|
19
|
+
address : out unsigned(7 downto 0);
|
20
|
+
datain : out std_logic_vector(DATA_WIDTH-1 downto 0);
|
21
|
+
dataout : in std_logic_vector(DATA_WIDTH-1 downto 0);
|
22
|
+
debug : out std_logic_vector(15 downto 0)
|
23
|
+
);
|
24
|
+
end entity;
|
25
|
+
|
26
|
+
architecture rtl of uart_bus_master is
|
27
|
+
--
|
28
|
+
constant NB_BYTES_PER_ADDR : natural := ADDR_WIDTH/8;
|
29
|
+
subtype byte_a_type is natural range 0 to NB_BYTES_PER_ADDR;
|
30
|
+
signal byte_a,byte_a_c : byte_a_type;
|
31
|
+
|
32
|
+
constant NB_BYTES_PER_DATA : natural := DATA_WIDTH/8;
|
33
|
+
subtype byte_d_type is natural range 0 to NB_BYTES_PER_DATA;
|
34
|
+
signal byte_d,byte_d_c : byte_d_type;
|
35
|
+
--
|
36
|
+
signal rd_uart, wr_uart, wr_uart_c : std_logic;
|
37
|
+
signal w_data, w_data_c : std_logic_vector(7 downto 0);
|
38
|
+
signal tx_full, rx_empty : std_logic;
|
39
|
+
signal r_data : std_logic_vector(7 downto 0);
|
40
|
+
--
|
41
|
+
signal data_from_pc_r : std_logic_vector(7 downto 0);
|
42
|
+
signal data_from_pc_valid_r : std_logic;
|
43
|
+
--
|
44
|
+
type state_type is (
|
45
|
+
IDLE, WRITING_RCV_ADDR, WRITING_RCV_DATA, WRITING_APPLY_PULSE,
|
46
|
+
READING_RCV_ADDR, READING_APPLY_PULSE_WS, READING_APPLY_PULSE);
|
47
|
+
signal state, state_c : state_type;
|
48
|
+
--
|
49
|
+
signal sreset : std_logic;
|
50
|
+
signal ce_r,ce_c : std_logic;
|
51
|
+
signal we_r,we_c : std_logic;
|
52
|
+
signal addr_r,addr_c : std_logic_vector(7 downto 0);
|
53
|
+
signal datain_r,data_c : std_logic_vector(DATA_WIDTH-1 downto 0);
|
54
|
+
-- debug
|
55
|
+
signal slow_clk, slow_tick : std_logic;
|
56
|
+
signal done_read, done_read_c : std_logic;
|
57
|
+
signal done_write, done_write_c : std_logic;
|
58
|
+
signal debug_idle : std_logic;
|
59
|
+
begin
|
60
|
+
|
61
|
+
uart_1 : entity work.uart
|
62
|
+
generic map (
|
63
|
+
DBIT => 8,
|
64
|
+
SB_TICK => 16,
|
65
|
+
DVSR => 325,
|
66
|
+
DVSR_BIT => 9,
|
67
|
+
FIFO_W => 3)
|
68
|
+
port map (
|
69
|
+
clk => clk,
|
70
|
+
reset_n => reset_n,
|
71
|
+
rd_uart => rd_uart,
|
72
|
+
wr_uart => wr_uart,
|
73
|
+
rx => rx,
|
74
|
+
w_data => w_data,
|
75
|
+
tx_full => tx_full,
|
76
|
+
rx_empty => rx_empty,
|
77
|
+
r_data => r_data,
|
78
|
+
tx => tx);
|
79
|
+
|
80
|
+
-- pump the internal UART FIFO *systematically* (when something is written in it)
|
81
|
+
-- no accumulation in the FIFO
|
82
|
+
rd_uart <= not(rx_empty);
|
83
|
+
|
84
|
+
sampling_data_p : process(reset_n, clk)
|
85
|
+
begin
|
86
|
+
if reset_n = '0' then
|
87
|
+
data_from_pc_r <= (others => '0');
|
88
|
+
data_from_pc_valid_r <= '0';
|
89
|
+
elsif rising_edge(clk) then
|
90
|
+
data_from_pc_valid_r <= '0';
|
91
|
+
if rd_uart = '1' then
|
92
|
+
data_from_pc_r <= r_data;
|
93
|
+
data_from_pc_valid_r <= '1';
|
94
|
+
end if;
|
95
|
+
end if;
|
96
|
+
end process;
|
97
|
+
|
98
|
+
debug_idle <= '1' when state=IDLE else '0';
|
99
|
+
debug <= "00000000" & data_from_pc_r(7 downto 0);
|
100
|
+
--================= BUS bridge =================
|
101
|
+
-- protocol using 8 bits UART :
|
102
|
+
-- for write :
|
103
|
+
-- byte 0 : 00010001=0x11
|
104
|
+
-- byte 1 : address
|
105
|
+
-- byte 2 : data
|
106
|
+
-- for read :
|
107
|
+
-- byte 0 : 00010000=0x10
|
108
|
+
-- byte 1 : address
|
109
|
+
-- =============================================
|
110
|
+
tick : process(reset_n, clk)
|
111
|
+
begin
|
112
|
+
if reset_n = '0' then
|
113
|
+
state <= IDLE;
|
114
|
+
ce_r <= '0';
|
115
|
+
we_r <= '0';
|
116
|
+
addr_r <= (others => '0');
|
117
|
+
datain_r <= (others => '0');
|
118
|
+
wr_uart <= '0';
|
119
|
+
w_data <= (others => '0');
|
120
|
+
done_read <= '0';
|
121
|
+
done_write <= '0';
|
122
|
+
byte_a <= NB_BYTES_PER_ADDR-1;
|
123
|
+
byte_d <= NB_BYTES_PER_DATA-1;
|
124
|
+
elsif rising_edge(clk) then
|
125
|
+
state <= state_c;
|
126
|
+
ce_r <= ce_c;
|
127
|
+
we_r <= we_c;
|
128
|
+
addr_r <= addr_c;
|
129
|
+
datain_r <= data_c;
|
130
|
+
wr_uart <= wr_uart_c;
|
131
|
+
w_data <= w_data_c;
|
132
|
+
done_read <= done_read_c;
|
133
|
+
done_write <= done_write_c;
|
134
|
+
byte_a <= byte_a_c;
|
135
|
+
byte_d <= byte_d_c;
|
136
|
+
end if;
|
137
|
+
end process;
|
138
|
+
|
139
|
+
ce <= ce_r;
|
140
|
+
we <= we_r;
|
141
|
+
address <= unsigned(addr_r);
|
142
|
+
datain <= datain_r;
|
143
|
+
|
144
|
+
comb : process(addr_r, data_from_pc_r, data_from_pc_valid_r, datain_r,
|
145
|
+
dataout, state, w_data, done_read, done_write,
|
146
|
+
byte_a,byte_d)
|
147
|
+
variable state_v : state_type;
|
148
|
+
variable ce_v : std_logic;
|
149
|
+
variable we_v : std_logic;
|
150
|
+
variable addr_v : std_logic_vector(7 downto 0);
|
151
|
+
variable data_v : std_logic_vector(DATA_WIDTH-1 downto 0);
|
152
|
+
variable wr_uart_v : std_logic;
|
153
|
+
variable w_data_v : std_logic_vector(7 downto 0);
|
154
|
+
--debug
|
155
|
+
variable done_read_v : std_logic;
|
156
|
+
variable done_write_v : std_logic;
|
157
|
+
variable byte_a_v : byte_a_type;
|
158
|
+
variable byte_d_v : byte_d_type;
|
159
|
+
begin
|
160
|
+
state_v := state;
|
161
|
+
--
|
162
|
+
ce_v := '0';
|
163
|
+
we_v := '0';
|
164
|
+
addr_v := addr_r;
|
165
|
+
data_v := datain_r;
|
166
|
+
--
|
167
|
+
wr_uart_v := '0';
|
168
|
+
w_data_v := w_data;
|
169
|
+
done_read_v := done_read;
|
170
|
+
done_write_v := done_write;
|
171
|
+
byte_a_v := byte_a;
|
172
|
+
byte_d_v := byte_d;
|
173
|
+
|
174
|
+
case state_v is
|
175
|
+
|
176
|
+
when IDLE =>
|
177
|
+
if data_from_pc_valid_r = '1' then
|
178
|
+
if data_from_pc_r = x"11" then
|
179
|
+
state_v := WRITING_RCV_ADDR;
|
180
|
+
elsif data_from_pc_r = x"10" then
|
181
|
+
state_v := READING_RCV_ADDR;
|
182
|
+
end if;
|
183
|
+
end if;
|
184
|
+
|
185
|
+
when WRITING_RCV_ADDR =>
|
186
|
+
if data_from_pc_valid_r = '1' then
|
187
|
+
addr_v((byte_a_v+1)*8-1 downto byte_a_v*8) := data_from_pc_r;--WHEN addr is 8 bits
|
188
|
+
if byte_a_v/=0 then
|
189
|
+
byte_a_v:=byte_a_v-1;
|
190
|
+
else
|
191
|
+
byte_a_v:=NB_BYTES_PER_ADDR-1;
|
192
|
+
state_v := WRITING_RCV_DATA;
|
193
|
+
end if;
|
194
|
+
end if;
|
195
|
+
|
196
|
+
when WRITING_RCV_DATA =>
|
197
|
+
if data_from_pc_valid_r = '1' then
|
198
|
+
data_v((byte_d_v+1)*8-1 downto byte_d_v*8) := data_from_pc_r;
|
199
|
+
if byte_d_v /=0 then
|
200
|
+
byte_d_v := byte_d_v-1;
|
201
|
+
else
|
202
|
+
ce_v := '1';
|
203
|
+
we_v := '1';
|
204
|
+
byte_d_v := NB_BYTES_PER_DATA-1;
|
205
|
+
state_v := IDLE;
|
206
|
+
done_read_v := '1';
|
207
|
+
end if;
|
208
|
+
end if;
|
209
|
+
|
210
|
+
when READING_RCV_ADDR =>
|
211
|
+
if data_from_pc_valid_r = '1' then
|
212
|
+
addr_v((byte_a_v+1)*8-1 downto byte_a_v*8) := data_from_pc_r;--WHEN addr is 8 bits
|
213
|
+
if byte_a_v/=0 then
|
214
|
+
byte_a_v:=byte_a_v-1;
|
215
|
+
else
|
216
|
+
ce_v := '1';
|
217
|
+
we_v := '0';
|
218
|
+
byte_a_v:=NB_BYTES_PER_ADDR-1;
|
219
|
+
state_v := READING_APPLY_PULSE_WS;
|
220
|
+
end if;
|
221
|
+
end if;
|
222
|
+
|
223
|
+
when READING_APPLY_PULSE_WS =>
|
224
|
+
state_v := READING_APPLY_PULSE;
|
225
|
+
|
226
|
+
when READING_APPLY_PULSE =>
|
227
|
+
wr_uart_v := '1';
|
228
|
+
w_data_v := dataout((byte_d_v+1)*8-1 downto (byte_d_v*8));
|
229
|
+
if byte_d_v /=0 then
|
230
|
+
byte_d_v := byte_d_v-1;
|
231
|
+
else
|
232
|
+
byte_d_v := NB_BYTES_PER_DATA-1;
|
233
|
+
state_v := IDLE;
|
234
|
+
done_read_v := '1';
|
235
|
+
end if;
|
236
|
+
when others =>
|
237
|
+
null;
|
238
|
+
end case;
|
239
|
+
|
240
|
+
state_c <= state_v;
|
241
|
+
--
|
242
|
+
ce_c <= ce_v;
|
243
|
+
we_c <= we_v;
|
244
|
+
addr_c <= addr_v;
|
245
|
+
data_c <= data_v;
|
246
|
+
--
|
247
|
+
wr_uart_c <= wr_uart_v;
|
248
|
+
w_data_c <= w_data_v;
|
249
|
+
done_read_c <= done_read_v;
|
250
|
+
done_read_c <= done_write_v;
|
251
|
+
byte_a_c <= byte_a_v;
|
252
|
+
byte_d_c <= byte_d_v;
|
253
|
+
|
254
|
+
end process;
|
255
|
+
|
256
|
+
end rtl;
|
data/assets/uart_rx.vhd
ADDED
@@ -0,0 +1,90 @@
|
|
1
|
+
library ieee;
|
2
|
+
use ieee.std_logic_1164.all;
|
3
|
+
use ieee.numeric_std.all;
|
4
|
+
entity uart_rx is
|
5
|
+
generic(
|
6
|
+
DBIT : integer := 8; -- # data bits
|
7
|
+
SB_TICK : integer := 16 -- # ticks for stop bits
|
8
|
+
);
|
9
|
+
port(
|
10
|
+
clk, reset_n : in std_logic;
|
11
|
+
rx : in std_logic;
|
12
|
+
s_tick : in std_logic;
|
13
|
+
rx_done_tick : out std_logic;
|
14
|
+
dout : out std_logic_vector(7 downto 0)
|
15
|
+
);
|
16
|
+
end uart_rx;
|
17
|
+
|
18
|
+
architecture arch of uart_rx is
|
19
|
+
type state_type is (idle, start, data, stop);
|
20
|
+
signal state_reg, state_next : state_type;
|
21
|
+
signal s_reg, s_next : unsigned(3 downto 0);
|
22
|
+
signal n_reg, n_next : unsigned(2 downto 0);
|
23
|
+
signal b_reg, b_next : std_logic_vector(7 downto 0);
|
24
|
+
begin
|
25
|
+
-- FSMD state & data registers
|
26
|
+
process(clk, reset_n)
|
27
|
+
begin
|
28
|
+
if reset_n = '0' then
|
29
|
+
state_reg <= idle;
|
30
|
+
s_reg <= (others => '0');
|
31
|
+
n_reg <= (others => '0');
|
32
|
+
b_reg <= (others => '0');
|
33
|
+
elsif (clk'event and clk = '1') then
|
34
|
+
state_reg <= state_next;
|
35
|
+
s_reg <= s_next;
|
36
|
+
n_reg <= n_next;
|
37
|
+
b_reg <= b_next;
|
38
|
+
end if;
|
39
|
+
end process;
|
40
|
+
-- next-state logic & data path functional units/routing
|
41
|
+
process(state_reg, s_reg, n_reg, b_reg, s_tick, rx)
|
42
|
+
begin
|
43
|
+
state_next <= state_reg;
|
44
|
+
s_next <= s_reg;
|
45
|
+
n_next <= n_reg;
|
46
|
+
b_next <= b_reg;
|
47
|
+
rx_done_tick <= '0';
|
48
|
+
case state_reg is
|
49
|
+
when idle =>
|
50
|
+
if rx = '0' then
|
51
|
+
state_next <= start;
|
52
|
+
s_next <= (others => '0');
|
53
|
+
end if;
|
54
|
+
when start =>
|
55
|
+
if (s_tick = '1') then
|
56
|
+
if s_reg = 7 then
|
57
|
+
state_next <= data;
|
58
|
+
s_next <= (others => '0');
|
59
|
+
n_next <= (others => '0');
|
60
|
+
else
|
61
|
+
s_next <= s_reg + 1;
|
62
|
+
end if;
|
63
|
+
end if;
|
64
|
+
when data =>
|
65
|
+
if (s_tick = '1') then
|
66
|
+
if s_reg = 15 then
|
67
|
+
s_next <= (others => '0');
|
68
|
+
b_next <= rx & b_reg(7 downto 1);
|
69
|
+
if n_reg = (DBIT-1) then
|
70
|
+
state_next <= stop;
|
71
|
+
else
|
72
|
+
n_next <= n_reg + 1;
|
73
|
+
end if;
|
74
|
+
else
|
75
|
+
s_next <= s_reg + 1;
|
76
|
+
end if;
|
77
|
+
end if;
|
78
|
+
when stop =>
|
79
|
+
if (s_tick = '1') then
|
80
|
+
if s_reg = (SB_TICK-1) then
|
81
|
+
state_next <= idle;
|
82
|
+
rx_done_tick <= '1';
|
83
|
+
else
|
84
|
+
s_next <= s_reg + 1;
|
85
|
+
end if;
|
86
|
+
end if;
|
87
|
+
end case;
|
88
|
+
end process;
|
89
|
+
dout <= b_reg;
|
90
|
+
end arch;
|