![]() |
|
|
|||||||
![]() |
VHDL - Having trouble with my FIR filter, help much appreciated. |
|
|
Thread Tools | Search this Thread |
|
|
#1 |
|
Hi, I am doing my FYP and it involves the usage of an FIR filter with
dynamic updating coefficients. my issue is I needed to redesign it to get data, coefficients and perform the MAC process independently and concurrently. This meant I needed to use signals (previously used variables) this has cause me no end of grief and I cant understand why. Basically I have split the MAC operation into a component called tap, I need to process 20 taps before new data can be accepted. since I am using signals instead of variables I can just wrap around the operation to the next cycle or at least not sure how. basically I have been about to get 5 taps done in 1 clock but not sure how to do the remaining 15, after looking at my code it will be more coherent. (another issue is that now the component wont connect to the signals, have no clue why.) Heres the code for the FIR section (taps not included as its trivial and I know that part works): --------------------------------header of fir filter------------------------------- library ieee; use ieee.std_logic_1164.all; entity fir is generic( ntaps: integer:= 20; nbits: integer:= 10 ); port( coef_i, coef_q: in std_logic_vector(nbits-1 downto 0); data_i, data_q: in std_logic_vector(nbits-1 downto 0); clk: in std_logic; send_coef, send_data: in std_logic; request_coef, request_data: out std_logic; result_i, result_q: out std_logic_vector(nbits-1 downto 0) ); end fir; -----------------------------body of fir filter------------------------------------ architecture behaviour of fir is type reg1 is array (ntaps-1 downto 0) of std_logic_vector(nbits-1 downto 0); type reg2 is array (ntaps downto 0) of std_logic_vector(nbits-1 downto 0); signal coefreg_i, coefreg_q: reg1; signal sum_i, sum_q: reg2; signal datareg_i, datareg_q: reg1; signal clk_slow: std_logic; signal i, count: integer := 0; component tap generic( nbits: integer ); port( clk: in std_logic; cin_i, cin_q: in std_logic_vector(nbits-1 downto 0); din_i, din_q: in std_logic_vector(nbits-1 downto 0); prv_sum_i, prv_sum_q: in std_logic_vector(nbits-1 downto 0); nxt_sum_i, nxt_sum_q: out std_logic_vector(nbits-1 downto 0) ); end component; begin ----------------------combinational requesting logic--------------------- request_coef <= '1' when send_coef = '0' else '0'; request_data <= '1' when send_data = '0' and count = 3 else '0'; --create multiple processes so that the filter is pipelined thus no --process is dependent on a previous process so no waiting ----------------------------gets coeficients----------------------------- get_coef: process(clk, send_coef) begin --when there is a change of clk and its high process the statements below if (clk'event and clk = '1') then --get new coeficient, store into coeficient register when coef_load high if(send_coef = '1') then coefreg_i(i) <= coef_i; coefreg_q(i) <= coef_q; if i < ntaps-1 then i <= i+1; else i <= 0; end if; end if; else end if; end process get_coef; ---------------------------frequency division---------------------------- slow_clk: process(clk) begin if (clk'event and clk = '1') then if count < 3 then count <= count + 1; else clk_slow <= not(clk_slow); count <= 0; end if; end if; end process slow_clk; -----------------------------gets new data------------------------------- get_data: process(clk_slow, send_data) begin if (clk_slow'event and clk_slow = '1') then --get new data, perform first tap and store result when data_load high if(send_data = '1') then datareg_i <= data_i & datareg_i(ntaps-1 downto 1); datareg_q <= data_q & datareg_q(ntaps-1 downto 1); end if; else end if; end process get_data; -----------------------------perform tap n------------------------------- tapgen: for k in 0 to 4 generate tapcore: tap generic map( nbits => nbits ) port map( clk => clk, cin_i => coefreg_i(k), cin_q => coefreg_q(k), din_i => datareg_i(k), din_q => datareg_q(k), prv_sum_i => sum_i(k), prv_sum_q => sum_q(k), nxt_sum_i => sum_i(k+1), nxt_sum_q => sum_q(k+1) ); end generate tapgen; result_i <= sum_i(5); result_q <= sum_i(5); end behaviour; ------------------------------end of fir filter------------------------------------ Any helps much appreciated. Thanks Marlan McLeish marlan.mcleish@googlemail.com |
|
|
|
|
#2 |
|
Posts: n/a
|
On Feb 1, 9:24 pm, marlan.mcle...@googlemail.com wrote:
> Hi, I am doing my FYP and it involves the usage of an FIR filter with > dynamic updating coefficients. my issue is I needed to redesign it to > get data, coefficients and perform the MAC process independently and > concurrently. This meant I needed to use signals (previously used > variables) this has cause me no end of grief and I cant understand > why. Basically I have split the MAC operation into a component called > tap, I need to process 20 taps before new data can be accepted. since > I am using signals instead of variables I can just wrap around the > operation to the next cycle or at least not sure how. basically I have > been about to get 5 taps done in 1 clock but not sure how to do the > remaining 15, after looking at my code it will be more coherent. > (another issue is that now the component wont connect to the signals, > have no clue why.) Heres the code for the FIR section (taps not > included as its trivial and I know that part works): > > --------------------------------header of fir > filter------------------------------- > library ieee; > use ieee.std_logic_1164.all; > > entity fir is > generic( > ntaps: integer:= 20; > nbits: integer:= 10 > ); > > port( > coef_i, coef_q: in std_logic_vector(nbits-1 downto 0); > data_i, data_q: in std_logic_vector(nbits-1 downto 0); > clk: in std_logic; > send_coef, send_data: in std_logic; > request_coef, request_data: out std_logic; > result_i, result_q: out std_logic_vector(nbits-1 downto 0) > ); > end fir; > -----------------------------body of fir > filter------------------------------------ > architecture behaviour of fir is > type reg1 is array (ntaps-1 downto 0) of std_logic_vector(nbits-1 > downto 0); > type reg2 is array (ntaps downto 0) of std_logic_vector(nbits-1 > downto 0); > > signal coefreg_i, coefreg_q: reg1; > signal sum_i, sum_q: reg2; > signal datareg_i, datareg_q: reg1; > signal clk_slow: std_logic; > signal i, count: integer := 0; > > component tap > generic( > nbits: integer > ); > port( > clk: in std_logic; > cin_i, cin_q: in std_logic_vector(nbits-1 downto 0); > din_i, din_q: in std_logic_vector(nbits-1 downto 0); > prv_sum_i, prv_sum_q: in std_logic_vector(nbits-1 downto 0); > nxt_sum_i, nxt_sum_q: out std_logic_vector(nbits-1 downto 0) > ); > end component; > > begin > ----------------------combinational requesting > logic--------------------- > request_coef <= '1' when send_coef = '0' else '0'; > request_data <= '1' when send_data = '0' and count = 3 else '0'; > --create multiple processes so that the filter is pipelined thus no > --process is dependent on a previous process so no waiting > ----------------------------gets > coeficients----------------------------- > get_coef: process(clk, send_coef) > begin > --when there is a change of clk and its high process the statements > below > if (clk'event and clk = '1') then > --get new coeficient, store into coeficient register when coef_load > high > if(send_coef = '1') then > coefreg_i(i) <= coef_i; > coefreg_q(i) <= coef_q; > if i < ntaps-1 then > i <= i+1; > else > i <= 0; > end if; > end if; > else > end if; > end process get_coef; > ---------------------------frequency > division---------------------------- > slow_clk: process(clk) > begin > if (clk'event and clk = '1') then > if count < 3 then > count <= count + 1; > else > clk_slow <= not(clk_slow); > count <= 0; > end if; > end if; > end process slow_clk; > -----------------------------gets new > data------------------------------- > get_data: process(clk_slow, send_data) > begin > if (clk_slow'event and clk_slow = '1') then > --get new data, perform first tap and store result when data_load high > if(send_data = '1') then > datareg_i <= data_i & datareg_i(ntaps-1 downto 1); > datareg_q <= data_q & datareg_q(ntaps-1 downto 1); > end if; > else > end if; > end process get_data; > -----------------------------perform tap > n------------------------------- > tapgen: for k in 0 to 4 generate > tapcore: tap > generic map( > nbits => nbits > ) > port map( > clk => clk, > cin_i => coefreg_i(k), cin_q => coefreg_q(k), > din_i => datareg_i(k), din_q => datareg_q(k), > prv_sum_i => sum_i(k), prv_sum_q => sum_q(k), > nxt_sum_i => sum_i(k+1), nxt_sum_q => sum_q(k+1) > ); > end generate tapgen; > > result_i <= sum_i(5); > result_q <= sum_i(5); > end behaviour; > ------------------------------end of fir > filter------------------------------------ > > Any helps much appreciated. > > Thanks > > Marlan McLeish Looks like you are taking each co-eff at a time, so that means you will take 20 clocks just to laod the coeffts so there is no point in doing all your calc in one cycle. You can just do a coefft*data_sample operation each clock and put it in the acculmulator and do like wise in subsequent clock cycles adding to the accumulator your results so after 20 clock cycles you will have your first ouput ready and then you will have outputs each clock cycle. cheers Neo |
|
|
|
#3 |
|
Posts: n/a
|
Hi, sorry I didnt explain properly, the filter will start with 20
coefficients already pre-loaded, I have just not put that part in yet. I need to evaluate all 20 taps within 4 clock cycles. marlan.mcleish@googlemail.com |
|
|
|
#4 |
|
Posts: n/a
|
On Feb 2, 11:45 pm, "marlan.mcle...@googlemail.com"
<marlan.mcle...@googlemail.com> wrote: > Hi, sorry I didnt explain properly, the filter will start with 20 > coefficients already pre-loaded, I have just not put that part in yet. > I need to evaluate all 20 taps within 4 clock cycles. So if thats all you want you just have to do 5MAC operations per clock. From your code above that has to be done by your tap_core. If your 5 tap_core modules output is finally getting added up( is it?) then that result is what you are looking for. hope this helps. Neo |
|
|
|
#5 |
|
Posts: n/a
|
On Feb 2, 11:45 pm, "marlan.mcle...@googlemail.com"
<marlan.mcle...@googlemail.com> wrote: > Hi, sorry I didnt explain properly, the filter will start with 20 > coefficients already pre-loaded, I have just not put that part in yet. > I need to evaluate all 20 taps within 4 clock cycles. Oops I am sorry, I forgot, what about the 20 inputs you need? do you get it in 20 clocks? then still my first reply holds. Neo |
|
|
|
#6 |
|
Posts: n/a
|
On 6 Feb, 08:21, "Neo" <zingafri...@yahoo.com> wrote:
> On Feb 2, 11:45 pm, "marlan.mcle...@googlemail.com" > > <marlan.mcle...@googlemail.com> wrote: > > Hi, sorry I didnt explain properly, the filter will start with 20 > > coefficients already pre-loaded, I have just not put that part in yet. > > I need to evaluate all 20 taps within 4 clock cycles. > > Oops I am sorry, I forgot, what about the 20 inputs you need? do you > get it in 20 clocks? then still my first reply holds. Hi, yes I get 20 inputs over 20 clocks , in a continuous system whereby a further 20 taps come in and the previous 20 taps must already of been process by that time so yes my code above does this. my issue is that I cant get it to increment properly, after I do the first 5 I am unsure how to do the next 15 remaining taps. I cant make the value of the index increment e.g. (k+i) where i = i+8 (incremented per clock), as I get an error stating that the index is not static. How would I go about incrementing the index. marlan.mcleish@googlemail.com |
|
![]() |
| Thread Tools | Search this Thread |
|
|
Similar Threads
|
||||
| Thread | Thread Starter | Forum | Replies | Last Post |
| Help on auto conversion from Matlab to vhdl on filter design | hardheart | Hardware | 0 | 12-07-2007 09:19 AM |
| any way to filter or add a color in an avi file? | Mario | DVD Video | 5 | 10-19-2007 04:35 AM |
| Trouble bridging | Journey44 | Hardware | 0 | 09-10-2006 05:07 PM |
| Videocard trouble | tanya004 | Hardware | 1 | 07-22-2006 02:17 PM |
| Re: Anyone HAve Trouble With Maxtor Rebates? | Pikoro | A+ Certification | 3 | 08-14-2003 07:07 PM |