Генерация HDL-кода от системного объекта декодера Витерби

Этот пример показывает, как проверять, сгенерировать и проверить HDL-код из кода MATLAB®, который инстанцирует Системного объекта Декодера Витерби.

Проект MATLAB

Кодом MATLAB, используемым в этом примере, является Декодер Витерби, используемый в трудном решении сверточное декодирование, реализованное как Системный объект. Этот пример также показывает испытательный стенд MATLAB, который тестирует декодер.

design_name = 'mlhdlc_sysobj_viterbi';
testbench_name = 'mlhdlc_sysobj_viterbi_tb';

Давайте смотреть на проект MATLAB.

type(design_name);
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% MATLAB design: Viterbi Decoder 
% 
% Key Design pattern covered in this example: 
% (1) Using comm system toolbox ViterbiDecoder function
% (2) The 'step' method can be called only per system object in a design iteration
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

%   Copyright 2011-2015 The MathWorks, Inc.

function decodedBits = mlhdlc_sysobj_viterbi(inputSymbol)

persistent hVitDec;

if isempty(hVitDec)
    hVitDec = comm.ViterbiDecoder('InputFormat','Hard', 'OutputDataType', 'Logical');
end

decodedBits = step(hVitDec, inputSymbol);
type(testbench_name);
% Viterbi_tb - testbench for Viterbi_dut

%   Copyright 2011-2015 The MathWorks, Inc.

numErrors = 0;
% rand stream
original_rs = RandStream.getGlobalStream;
rs = RandStream.create('mrg32k3a', 'seed', 25);
%RandStream.getGlobalStream(rs);
rs.reset;
% convolutional encoder
hConvEnc = comm.ConvolutionalEncoder;
% BER
hBER = comm.ErrorRate;
hBER.ReceiveDelay = 34;
reset(hBER);

% clear persistent variables in the design between runs of the testbench
clear mlhdlc_msysobj_viterbi;

for numSymbols = 1:10000
    % generate a random bit
    inputBit = logical(randi([0 1], 1, 1));
        
    % encode it with the Convolutional Encoder - rate 1/2
    encodedSymbol = step(hConvEnc, inputBit);
    
    % optional - add noise
    
    %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    % call Viterbi Decoder DUT to decode the symbol
    %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    vitdecOut = mlhdlc_sysobj_viterbi(encodedSymbol);
    
    ber = step(hBER, inputBit, vitdecOut);
end

fprintf('%s\n', repmat('%', 1, 38));
fprintf('%%%%%%%%%%%%%% %s %%%%%%%%%%%%%%\n', 'Viterbi Decoder Output');
fprintf('%s\n', repmat('%', 1, 38));
fprintf('Number of bits %d, BER %g\n', numSymbols, ber(1));
fprintf('%s\n', repmat('%', 1, 38));

% EOF

Создайте новую папку и скопируйте соответствующие файлы

Выполните следующие строки кода, чтобы скопировать необходимые файлы в качестве примера во временную папку.

mlhdlc_demo_dir = fullfile(matlabroot, 'toolbox', 'hdlcoder', 'hdlcoderdemos', 'matlabhdlcoderdemos');
mlhdlc_temp_dir = [tempdir 'mlhdlc_so_viterbi'];

% Create a temporary folder and copy the MATLAB files.
cd(tempdir);
[~, ~, ~] = rmdir(mlhdlc_temp_dir, 's');
mkdir(mlhdlc_temp_dir);
cd(mlhdlc_temp_dir);

copyfile(fullfile(mlhdlc_demo_dir, [design_name,'.m*']), mlhdlc_temp_dir);
copyfile(fullfile(mlhdlc_demo_dir, [testbench_name,'.m*']), mlhdlc_temp_dir);

Моделируйте проект

Моделируйте проект с испытательным стендом до генерации кода, чтобы убедиться, что нет никаких ошибок периода выполнения.

mlhdlc_sysobj_viterbi_tb
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%% Viterbi Decoder Output %%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
Number of bits 10000, BER 0
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

Аппаратная реализация Viterbi декодирование алгоритма

Существует три основных компонента в Viterbi, декодирующем алгоритм. Они - метрическое вычисление ответвления (BMC), "добавьте, сравнивают выбор" (ACS) и декодирование traceback. Следующая схема иллюстрирует эти три модуля в Viterbi, декодирующем алгоритм.

Метод перенормализации

Декодер Витерби предотвращает переполнение метрик состояния в компоненте ACS путем вычитания минимального значения метрик состояния на каждом временном шаге, как показано в следующей фигуре.

Получение минимального значения всех метрических элементов состояния за один такт приводит к плохой частоте часов для схемы. Производительность схемы может улучшаться путем добавления конвейерных регистров. Однако просто вычитание минимального значения, задержанного конвейерными регистрами от метрик состояния, может все еще вести, чтобы переполниться.

Аппаратная архитектура изменяет метод перенормализации и избегает метрического переполнения состояния на трех шагах. Во-первых, архитектура вычисляет значения для порога и параметров шага, на основе структуры решетки и количества мягких битов решения. Во-вторых, задержанное минимальное значение сравнивается с порогом. Наконец, если минимальное значение больше, чем или равно пороговому значению, реализация вычитает значение шага из метрики состояния; в противном случае никакая корректировка не выполняется. Следующая фигура иллюстрирует измененный метод перенормализации.

Создайте новый проект HDL Coder

Чтобы создать новый проект, введите следующую команду:

coder -hdlcoder -new mlhdlc_viterbi

Затем, добавьте файл 'mlhdlc_sysobj_viterbi.m' в проект как функция MATLAB и 'mlhdlc_sysobj_viterbi_tb.m' как испытательный стенд MATLAB.

Можно обратиться к Началу работы с MATLAB к примеру по Рабочему процессу HDL для более полного примера при создании и заполнении проектов HDL Coder MATLAB.

Запустите преобразование фиксированной точки и генерацию HDL-кода

Запустите Советника по вопросам Рабочего процесса. В Советнике по вопросам Рабочего процесса щелкните правой кнопкой по 'Code Generation', продвигаются и выбирают опцию, 'Запущенную к выбранной задаче', чтобы запустить все шаги с начала через генерацию HDL-кода.

Исследуйте сгенерированный HDL-код путем щелчка по ссылкам в логарифмическом окне.

Поддерживаемые Системные объекты

Обратитесь к документации для списка Системных объектов, поддержанных для генерации HDL-кода.

Очистите Сгенерированные Файлы

Запустите следующие команды, чтобы очистить временную папку проекта.

mlhdlc_demo_dir = fullfile(matlabroot, 'toolbox', 'hdlcoder', 'hdlcoderdemos', 'matlabhdlcoderdemos');
mlhdlc_temp_dir = [tempdir 'mlhdlc_so_viterbi'];
clear mex;
cd (mlhdlc_demo_dir);
rmdir(mlhdlc_temp_dir, 's');