## HDL Coder |

This example shows how to use HDL Coder™ to check, generate, and verify HDL code for a 512-point complex serial FFT block built using the MATLAB Function blocks and Simulink® blocks.

On this page… |
---|

This model implements a simple OFDM transmitter and receiver. The OFDM receiver part contains a 512-point Radix-2 complex FFT to convert signal back to the frequency domain. There are two FFT implementations in this model:

The

**Behavioral FFT**block is the complex FFT block in DSP System Toolbox™ library. It calculates a 512-point vector input each sample and works at a sample rate of 512.

The

**FFT_512Pt_EML_Serial**block implements a serialized, streaming I/O FFT block using the MATLAB Function blocks and Simulink blocks and is suitable for hardware. This implementation accepts streaming complex input data and generates streaming complex results continuously after the initial pipelining latency.

The results of the two FFT implementations are shown to be equal after matching the initial pipelining latency.

**Additional Requirements:**

Communications System Toolbox

DSP System Toolbox

% To open this model, run the following commands: modelname = 'hdlcoder_ofdm_fft_eml'; open_system(modelname);

**Serial FFT Block Specification**

Cooley-Tukey Radix-2 Serialized FFT

Complex input, complex output

Streaming input, streaming output

Decimation in time

512 point

Bit width: 12 bits

Initial pipelining latency: 1298 clock cycles

Input ports:

enable -> enable signal indicates the first valid input data

data_in -> streaming input data

Output ports:

data_en -> enable signal indicates the first valid output data

data_out -> streaming output data

index_out -> index of output data

The **serialize** block generates the streaming input data for the FFT block. The original 512-point vector input is converted to one data point per sample by the **Unbuffer** block.

```
open_system([modelname '/serialize']);
```

In the **deserialize** block, the streaming output of the serial FFT block is converted back to a 512-element vector at the sample rate of 512 by the **Buffer** block.

```
open_system([modelname '/deserialize']);
```

This FFT block implements the Decimation-in-Time FFT algorithm which requires bit reverse-ordered input data. So the natural-ordered input data will pass through the stage **Start_BitReverse** in the beginning.

```
open_system([modelname '/FFT_512Pt_EML_Serial/Serialized_FFT']);
```

The serial FFT block is composed of log2(512)= 9 stages of radix-2 butterfly units. These FFT stages are pipelined and connected in tandem.

```
open_system([modelname '/FFT_512Pt_EML_Serial/Serialized_FFT/FFT_Stages']);
```

The following picture shows a typical 8-point FFT with 3 (log2(8)) stages. Each stage uses 4 (8/2) butterfly units. A serial FFT implemented in this model uses only one butterfly resource for each stage of implementation.

Each radix-2 FFT stage includes one radix-2 butterfly computing unit, memory blocks to cache the streaming data, a ROM to store the FFT twiddle factors, and control logic implemented in MATLAB Function blocks. The memory size of each stage equals the Stage Number.

```
open_system([modelname '/FFT_512Pt_EML_Serial/Serialized_FFT/FFT_Stages/FFT_Stage5']);
```

The radix-2 FFT butterfly algorithm is implemented in MATLAB file **hdlcoder_serial_fft_butterfly.m** on the MATLAB® path. All the **Butterfly_FFT2_Computing_Unit** blocks call this function.

The **Butterfly_FFT2_Computing_Unit** block uses a right shift to scale down the result data after every FFT stage to avoid overflow. In this model the **Scale** variable is set to 1 to turn off the scaling.

function [fft2_x, fft2_y] = fcn(fft2_u, fft2_v, fft2_twiddle) % FFT2 Computing Unit

```
% Scale down number for this stage. Need to be power of 2.
Scale = 1;
```

```
% Call function in MATLAB file hdlcoder_serial_fft_butterfly_scale.m on path
[x, y] = hdlcoder_serial_fft_butterfly(fft2_u, fft2_v, fft2_twiddle);
```

```
% scaling down by 2 for each FFT2 stage.
fft2_x = bitsra(x, log2(Scale));
fft2_y = bitsra(y, log2(Scale));
```

function [x, y] = hdlcoder_serial_fft_butterfly(u, v, twiddle) % FFT2 butterfly block % This function is used in hdlcoder_ofdm_fft_eml example model. %#codegen

nt = numerictype(u); fm = fimath(u);

```
% multiply twiddle and butterfly.
twv = fi(v * twiddle, nt, fm);
```

x = fi(u + twv, nt, fm); y = fi(u - twv, nt, fm);

**Check, Generate and Verify HDL**

checkhdl( [modelname '/FFT_512Pt_EML_Serial']); makehdl( [modelname '/FFT_512Pt_EML_Serial']); makehdltb([modelname '/FFT_512Pt_EML_Serial']);

This concludes the OFDM Receiver with 512-Point Serial FFT example.