www.gusucode.com > hdlverifier 案例代码 matlab源码程序 > hdlfilter/hdlfarrow.m
%% HDL Fractional Delay (Farrow) Filter % This example illustrates how to generate HDL code for a fractional % delay (Farrow) filter for timing recovery in a digital modem. A Farrow filter % structure provides variable fractional delay for the received data stream % prior to downstream symbol sampling. This special FIR filter structure % permits simple handling of filter coefficients by an efficient % polynomial interpolation formula implementation to provide variable % fractional resampling. % % In a typical digital modem application, the fractionally resampled data % output from a Farrow filter is passed along to a symbol sampler % with optional carrier recovery. For more details of this complete application % please refer to "Timing Recovery Using Fixed-Rate Resampling" % for Simulink(R) and Communications System Toolbox(TM). % Copyright 2004-2012 The MathWorks, Inc. %% Design the Filter % To design a fractional delay filter using the Cubic Lagrange interpolation % method, first create a specification object with filter order |3| and an % arbitrary fractional delay of |0.3|. Next, create a farrow filter object % |Hd|, using the design method of the specification object with argument % |lagrange|. This method is also called with property |FilterStructure| % and its value |fd|. You can look into the details of the filter object % |Hd| by using the |info| command. fDelay = 0.3; filtdes = fdesign.fracdelay(fDelay, 'N', 3); Hd = design(filtdes,'lagrange', 'FilterStructure', 'farrowfd'); info(Hd) %% % The fractional delay for the Farrow filter is tunable and can be altered % to lead a different magnitude response. You can see this by creating a set % of filters that are copies of the pre-designed filter |Hd| with each % differing in their |fracdelay| values. for d=0:9, h(d+1) = copy(Hd); h(d+1).fracdelay = d/10; end fvtool(h,'Color','white') fvtool(h,'Analysis','PhaseDelay','Color','white') %% Quantize the Filter % Set the filter object to fixed-point mode to quantize it. Assume % eight-bit fixed-point input data with eight-bit coefficients. Modify the % fixed-point data word lengths and fraction lengths accordingly. The % |CoeffFracLength| property is set automatically because coefficient % autoscaling is set to |on| by default by the property |CoeffAutoscale|. Hd.arithmetic = 'fixed'; Hd.InputWordLength = 8; Hd.InputFracLength = 7; Hd.CoeffWordLength = 8; %% Generate HDL Code from the Quantized Filter % Starting with the correctly quantized filter, you can generate VHDL or % Verilog code using the |generatehdl| command. You create a temporary work % directory and then use the |generatehdl| command using the appropriate % property-value pairs. After generating the HDL code using |VHDL| for the % |TargetLanguage| property in this case, you can open the generated VHDL file in % the editor by clicking on the hyperlink displayed in the command line display % messages. workingdir = tempname; generatehdl(Hd, 'Name', 'hdlfarrow', ... 'TargetLanguage', 'VHDL',... 'TargetDirectory', workingdir); %% Generate HDL Test Bench % To verify the HDL code, you can generate an HDL test bench to simulate the % HDL code using an HDL simulator. The test bench will verify the results of % the HDL code with the results of the MATLAB(R) |filter| command. The % stimuli for the filter input |filter_in| port and fractional delay % |filter_fd| port can be specified using properties |TestbenchStimulus|, % |TestbenchUserStimulus| and |TestbenchFracDelayStimulus|. % % Predefined stimulus for the filter input |filter_in| port can be specified % for input data stimulus using the property |TestbenchStimulus| as with the other % filter structures. You can specify your own stimulus for the input data by % using the property |TestbenchUserStimulus| and passing a MATLAB vector as % the value. % % You can specify the fractional delay stimulus using the property % |TestbenchFracdelayStimulus|. A vector of double between |0| and |1| is % generated automatically by specifying either |RandSweep| or |RampSweep|. % The default behavior is to provide a fractional delay stimulus of a % constant set to the |fracdelay| value of the filter object. % % The following command specifies the input stimulus to |chirp|, and the % fractional delay vector is set to a constant |0.3| for all the simulation % time. This is the default behavior when the |TestbenchFracDelayStimulus| % property is not set otherwise. generatehdl(Hd, 'Name', 'hdlfarrow', ... 'GenerateHDLTestbench', 'on', ... 'TestBenchName', 'hdlfarrow_default_tb',... 'TargetLanguage', 'VHDL',... 'TargetDirectory', workingdir); %% % To automatically generate the test vector for a fractional delay port, % specify |RampSweep| for |TestBenchFracDelayStimulus|. It generates a % vector of values between |0| and |1| sweeping in a linear fashion. The length % of this vector is equal to the input stimulus vector. generatehdl(Hd, 'Name', 'hdlfarrow', ... 'GenerateHDLTestbench', 'on', ... 'TestBenchName', 'hdlfarrow_rampsweep_tb',... 'TargetLanguage', 'VHDL',... 'TestBenchStimulus', 'chirp',... 'TestbenchFracDelaystimulus', 'Rampsweep', ... 'TargetDirectory', workingdir); %% % You can generate a customized input stimulus vector using MATLAB commands % and pass it to the test bench stimulus properties for the user defined input % and |fracdelay| stimuli. An input test vector |userinputstim| is generated % using the |chirp| command and the fractional delay test vector |userfdstim| is % generated of length equal to the input test vector. t=-2:0.01:2; % +/-2 secs @ 100 Hz sample rate userinputstim = chirp(t,100,1,200,'q'); % Start @100Hz, cross 200Hz at t=1sec leninput = length(userinputstim); samplefdvalues = [0.1, 0.34, 0.78, 0.56, 0.93, 0.25, 0.68, 0.45]; samplesheld = ceil(leninput/length(samplefdvalues)); ix = 1; for n = 1:length(samplefdvalues)-1 userfdstim(ix: ix + samplesheld-1) = repmat(samplefdvalues(n),1, samplesheld); ix = ix + samplesheld; end userfdstim(ix:leninput)= repmat(samplefdvalues(end),1 , leninput-length(userfdstim)); generatehdl(Hd, 'Name', 'hdlfarrow', ... 'GenerateHDLTestbench', 'on', ... 'TestBenchName', 'hdlfarrow_userdefined_tb',... 'TargetLanguage', 'VHDL',... 'TestBenchUserStimulus', userinputstim,... 'TestbenchFracDelaystimulus', userfdstim, ... 'TargetDirectory', workingdir); %% ModelSim(R) Simulation Results % The following display shows the ModelSim(R) HDL simulator after running % the VHDL test bench. %% % <<../hdlfarrow_screen.JPG>> % %% Conclusion % In this example, we showed how you can design a double-precision fractional % delay filter to meet the given specifications. We also showed how you can % quantize the filter and generate VHDL code. Then we showed how you can % generate VHDL test benches using several options to specify the input % and fracdelay stimulus vector. % % You can use any HDL simulator to verify these results. You % can also experiment with Verilog for both filters and % test benches.