ミキサーの後に設けるアンチエイリアスフィルターです。 サンプリング周波数とクロックが同じなので、処理に何クロックも必要なFIRフィルターは使えません。 CICフィルターは、フィルター特性はイマイチですが、1クロックで処理できることと、フィルタリングとデシメーションが同時に行えるので、多用されています。
Basis3では、IPにCICフィルタが用意されいるので、そのまま利用しました。
IPだけで構成されているので、モジュールにする必要はないのですが、CICフィルター単独でシミュレーションしたかったのでモジュール化しました。
デシメーション率は1024にしました。 UARTの最大速度を実験的に確かめたところ、私の開発環境では、6Mbaudでは動作しませんでした。 現状、クロックを80MHzとしていますので、デシメーション率1024だとデシメーション後のサンプリング周波数は、78.125kHzになるので5MHzあれば転送できます。
ソースです。
1 2 3 4 5 6 7 8 9 10 11 12 |
module cicfilter( input cicCLK, input cicRST, input signed [15:0] DATAIN_Q, DATAIN_I, output signed [15:0] DATAOUT_Q, DATAOUT_I, output cicDATAVALID ); cic_1024 cic_q(.aclk(cicCLK), .s_axis_data_tdata(DATAIN_Q), .s_axis_data_tvalid(1), .m_axis_data_tdata(DATAOUT_Q), .m_axis_data_tvalid(cicDATAVALID)); cic_1024 cic_i(.aclk(cicCLK), .s_axis_data_tdata(DATAIN_I), .s_axis_data_tvalid(1), .m_axis_data_tdata(DATAOUT_I), .m_axis_data_tvalid()); endmodule |
I,Q信号それぞれをIPで生成したcicフィルタに入力しているだけです。
テストベンチです。
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 |
module CicFilter_sim; reg clk; reg rst; reg signed [15:0] datain_q_, datain_i_; wire datavalid; wire signed [15:0] dataout_q_, dataout_i_; reg [31:0] mem[0:4095]; reg [11:0] add = 0; parameter STEP = 12.5; always begin clk <= 0; #(STEP/2); clk <= 1; #(STEP/2); end always @(posedge clk) begin if(rst) add <= 0; else begin add <= add + 1; datain_q_ <= mem[add][31:16]; datain_i_ <= mem[add][15:0]; end end cicfilter cicfilter(.cicCLK(clk), .cicRST(rst), .DATAIN_Q(datain_q_), .DATAIN_I(datain_i_), .DATAOUT_Q(dataout_q_), .DATAOUT_I(dataout_i_), .cicDATAVALID(datavalid)); initial begin $readmemb("simdata.txt", mem); rst <= 0; #(STEP*16000); $finish; end endmodule |
あらかじめ、simdata.txtに20kHzと78kHzの複素信号のデータを書き込んでおいて、80MHzのクロックで読み出してcicフィルタに入力しているだけです。
20kHzの信号を入力した時のシミュレーション結果です。
入力信号が少し怪しいですが、正常に動作しているようです。 フィルターの出力は、デシメーションされて78.125kHzで出力されるので、角ばった信号になっていますが正常です。
78kHzを入力した時のシミュレーション結果です。
ほぼ、出力がありません。