%% Initialization script for commhdlQPSKTxRx.slx. 
% This script initializes commhdlQPSKTxRx.slx. It is called in the InitFcn
% callback of the model commhdlQPSKTxRx.slx.
% 
% Define the following variables before running this script.
% Default values are assigned, if not defined.
% dataBits               - User information bits that are used for
%                          transmission. The number of bits this
%                          variable holds must be an integer multiple of
%                          data bits per packet (2240). It defaults to
%                          randomly generated bits by the function
%                          randsrc
% Rsym                   - Symbol rate. Default value is 1.92 Msps.
% EbN0dB                 - Eb/N0 in dB. Eb is energy per bit. N0/2 is
%                          the two-sided white gaussian noise power
%                          spectral density. It defaults to 30.
% CFO                    - Carrier frequency offset in Hz. Default value
%                          is 2300 Hz.
% CPO                    - Carrier phase offset in degrees. Default 
%                          value is 135 degrees. 
% fractionalTimingOffset - Fractional timing offset to be introduced in 
%                          the input waveform. The possible values of 
%                          this variable must be in the range greater 
%                          than or equal to 0 and less than 1. Default 
%                          value is 0.2. 
% timingFrequencyOffset  - Fractional timing drift to be introduced in 
%                          the input waveform. It is specified in parts 
%                          per million (PPM). Default value is 1 PPM

%   Copyright 2020 The MathWorks, Inc. 


if ~exist('dataBits','var')
    dataBits = randsrc(2240*10,1,[0,1]);
else
    validateattributes(dataBits,{'double'},{'binary','column','finite'},'','dataBits');
end
if ~exist('fractionalTimingOffset','var')
    fractionalTimingOffset = 0.2;
else
    validateattributes(fractionalTimingOffset,{'double'},{'finite','scalar','nonnegative','>=',0,'<',1},'','fractionalTimingOffset');
end
if ~exist('timingFrequencyOffset','var')
    timingFrequencyOffset = 1;
else
    validateattributes(timingFrequencyOffset,{'double'},{'finite','scalar','nonnegative'},'','timingFrequencyOffset');
end
if ~exist('EbN0dB','var')
    EbN0dB = 30;
else
    validateattributes(EbN0dB,{'double'},{'scalar'},'','EbN0dB');
end
if ~exist('CFO','var')
    CFO = 2300;  % in Hz
else
    validateattributes(CFO,{'double'},{'finite','scalar',},'','CFO');
end
if ~exist('CPO','var')
    CPO = 135;   % in degrees
else
    validateattributes(CPO,{'double'},{'finite','scalar'},'','CPO');
end
if ~exist('Rsym','var')
    Rsym = 1.92e6;
else
    validateattributes(Rsym,{'double'},{'finite','scalar','positive'},'','Rsym');
end

Config = commhdlQPSKTxRxParameters;

%% 
Nframes             = length(dataBits)/Config.DataBitsPerPacket;
if (Nframes - floor(Nframes)) ~= 0
    error('Number of dataBits must be integer multiple for 2240');
end

dataIn              = dataBits;
validIn             = true(size(dataIn));

% Generate validIn according to effective bit rate
dataIn = [zeros(length(Config.Preamble),Nframes);reshape(dataIn,Config.DataBitsPerPacket,Nframes)];
validIn = [false(length(Config.Preamble),Nframes);reshape(validIn,Config.DataBitsPerPacket,Nframes)];
dataIn = dataIn(:);
validIn = validIn(:);

CSLatency              = 5;
SSLatency              = 17;
PDLatency              = 44;
PALatency              = 101;
FCLatency              = 2;
QPSKDemodLatency       = 3;
DescramblerLatency     = 2;

stopTime =  (CSLatency + SSLatency)/(4*Rsym) + (DescramblerLatency+12)/(2*Rsym) ...
    + (PDLatency + PALatency + FCLatency + QPSKDemodLatency + 8)/Rsym ...
    + ((Nframes+1+1) * Config.BitsPerPacket/2)/Rsym;

 BitsPerSymbol = 2;      % QPSK
 EbN0          = 10^(EbN0dB/10);
 EsN0          = BitsPerSymbol*EbN0;
 noiseVariance = 1/EsN0;  % QPSK symbol energy is normalized to 1 i.e. Es = 1
