%%% Taks 
%%clear all; close all
M = 16;              % Alphabet size - Use 16-QAM modulation.
mu=log2(M);           % Bits/symbol
Nsyms = 2^10;        % Frame size - Number of modulated symbols per data frame
nloops = 100;         % Maximum number of bits transmitted = nloops*mu*Nsyms

%% Define a convolutional encoder
% Set the trellis structure and traceback length for a rate 1/2, constraint length 7, convolutional code.
trellis = poly2trellis(7,[171 133]);
tbl = 32; % Tracebck length - Insufficient tranceback length increases error rate
rate = 1/2; % Code rate

% Define EbN0 and find SNR
EbN0Vec = (0:1:18);
snrVec = EbN0Vec + 10*log10(mu*rate); % Find SNR from given EbNo, remember to include the code rate

% Set the ResetInputPort property to true to enable the error rate calculator to be reset during the simulation.
num_berrs = zeros(1, length(EbN0Vec));

for n=1:length(EbN0Vec),
    
    for l = 1:nloops % errros collected for a given SNR to maxBitErrors.
         dataIn = randi([0 1],Nsyms*mu,1);  % Message signal
% Convolutionally encode the data
        dataEnc = convenc(dataIn,trellis);      
% Modulate
        % modulated_symbols = zeros(1,Nsyms);
        modulated_symbols = qammod(dataEnc, M, 'InputType', 'bit', 'UnitAveragePower', 1);
% Add AWGN
        ynoisy = awgn(modulated_symbols ,snrVec(n));
% Demodulate to recover the message.
        dataOut = qamdemod(ynoisy, M, 'OutputType', 'bit', 'UnitAveragePower', 1);
% Viterbi decode the demodulated data
        dataHard = vitdec(dataOut,trellis,tbl,'cont','hard');
% Estimate errors
        num_berrs(n) = num_berrs(n) + biterr(dataIn(1:end-tbl),dataHard(tbl+1:end)); % Collect errors
    end
end
%figure
% Use the berawgn/berfading function to determine the theoretical BER.
[berT,~] = berawgn(EbN0Vec,'qam',M,1);
berS = num_berrs/(nloops*Nsyms*mu);
semilogy(EbN0Vec,berS,'r:o');
hold on
semilogy(EbN0Vec,berT,'k');
title('Performance of Rate 1/2 Covolutional Code in AWGN Chanells');
legend('Coded Simulation','Uncoded Theory','Location','Best');
xlabel('Eb/No (dB)'); ylabel('Bit Error Rate');
grid on