-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathfilter_generic_m.vhd
163 lines (143 loc) · 3.84 KB
/
filter_generic_m.vhd
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
-- Filtro genérico con mejoras añadidas
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
entity filter_generic_m is
-- utilizamos genericos para poder reutilizar
-- la implementación del filtro con los distintos valores
-- de coeficientes
generic(
-- Los coeficientes estan escalados por 1024, lo que
-- corresponde a utilizar una representación en coma
-- binaria de 6 bits enteros y 10 fraccionarios
b0 : integer := 1024;
b1 : integer := 0;
b2 : integer := -1024;
a1 : integer := 1024;
a2 : integer := 1024;
gs : integer := 1024);
port (
sin : in signed (15 downto 0);
sout : out signed (15 downto 0);
clk : in bit);
end;
architecture filter_arch_mod of filter_generic_m is
COMPONENT multiplier_16x16b
port (
sigA : in signed (15 downto 0);
sigB : in signed (15 downto 0);
mult : out signed (31 downto 0)
);
END COMPONENT;
COMPONENT adder_16b
port (
sig1 : in signed (15 downto 0);
sig2 : in signed (15 downto 0);
cin : in std_logic;
cout : out std_logic;
sum : out signed (15 downto 0)
);
END COMPONENT;
signal historia0 : signed (15 downto 0) := to_signed(0,16);
signal historia1 : signed (15 downto 0) := to_signed(0,16);
signal a1neg : signed(15 downto 0) := to_signed(-a1,16);
signal a2neg : signed(15 downto 0) := to_signed(-a2,16);
signal b0sig : signed(15 downto 0) := to_signed(b0,16);
signal b1sig : signed(15 downto 0) := to_signed(b1,16);
signal b2sig : signed(15 downto 0) := to_signed(b2,16);
signal gssig : signed(15 downto 0) := to_signed(gs,16);
signal gsin : signed (15 downto 0) := to_signed(0,16);
signal prod0 : signed(31 downto 0); -- b0*sin
signal prod1 : signed(31 downto 0); -- (-a1)*historia0
signal prod2 : signed(31 downto 0); -- (-a2)*historia1
signal prod3 : signed(31 downto 0); -- b1*historia0
signal prod4 : signed(31 downto 0); -- b2*historia1
signal suma0 : signed(15 downto 0); -- prod0 + prod1
signal suma1 : signed(15 downto 0); -- suma0 + prod2 <-- Esto va a la historia0
signal suma2 : signed(15 downto 0); -- suma1 + prod3
signal suma3 : signed(15 downto 0); -- suma2 + prod4
signal prodsin : signed(31 downto 0); -- gs*sin
begin
--aplicamos primero la ganancia final para evitar saturación en puntos intermedios
mult_s : multiplier_16x16b
PORT MAP(
sigA => gssig,
sigB => sin,
mult => prodsin
);
gsin <= prodsin(25 downto 10);
mult0 : multiplier_16x16b
PORT MAP(
sigA => b0sig,
sigB => gsin,
mult => prod0
);
mult1 : multiplier_16x16b
PORT MAP(
sigA => a1neg,
sigB => historia0,
mult => prod1
);
mult2 : multiplier_16x16b
PORT MAP(
sigA => a2neg,
sigB => historia1,
mult => prod2
);
mult3 : multiplier_16x16b
PORT MAP(
sigA => b1sig,
sigB => historia0,
mult => prod3
);
mult4 : multiplier_16x16b
PORT MAP(
sigA => b2sig,
sigB => historia1,
mult => prod4
);
add0 : adder_16b
PORT MAP(
sig1 => prod0(25 downto 10),
sig2 => prod1(25 downto 10),
cin => '0',
cout => open,
sum => suma0
);
add1 : adder_16b
PORT MAP(
sig1 => suma0,
sig2 => prod2(25 downto 10),
cin => '0',
cout => open,
sum => suma1
);
add2 : adder_16b
PORT MAP(
sig1 => suma1,
sig2 => prod3(25 downto 10),
cin => '0',
cout => open,
sum => suma2
);
add3 : adder_16b
PORT MAP(
sig1 => suma2,
sig2 => prod4(25 downto 10),
cin => '0',
cout => open,
sum => suma3
);
filter_proc: process(clk)
variable sum1 : signed (15 downto 0);
variable sum2 : signed (15 downto 0);
variable mult : signed (31 downto 0);
begin
if (clk'event and clk = '1') then
--sout <= prod5(25 downto 10);
sout <= suma3;
historia1 <= historia0;
historia0 <= suma1;
end if;
end process;
end filter_arch_mod;