BCJR implementation
WDM code added (Pol Cont., Opt MUX/DEMUX, Opt Atten, DP_Fiber) -> the codebase is not optimized to always work with dp signals!
This commit is contained in:
@@ -96,11 +96,11 @@ try
|
||||
adaption= 1;
|
||||
use_dd_mode = 1;
|
||||
|
||||
use_ffe = 0;
|
||||
use_dfe = 0;
|
||||
use_ffe = 1;
|
||||
use_dfe = 1;
|
||||
use_vnle_mlse = 1;
|
||||
use_dbtgt = 1;
|
||||
use_dbenc = 1;
|
||||
use_dbenc = 0;
|
||||
|
||||
addProcessingResultToDatabase = 0;
|
||||
|
||||
@@ -125,13 +125,12 @@ try
|
||||
|
||||
|
||||
%
|
||||
eq_ = EQ("Ne",ffe_order,"Nb",dfe_order,"training_length",len_tr,"training_loops",5,"dd_loops",5,"K",2,"DCmu",mu_dc,"DDmu",[mu_ffe mu_dfe],"DFEmu",0.005,"FFEmu",0,"plotfinal",0,"ideal_dfe",1);
|
||||
pf_ = Postfilter("ncoeff",pf_ncoeffs,"useBurg",1);
|
||||
% mlse_ = MLSE_viterbi("duobinary_output",0,'M',M,'trellis_states',PAMmapper(M,0).levels);
|
||||
mlse_ = MLSE("duobinary_output",0,'M',M,'trellis_states',PAMmapper(M,0).levels);
|
||||
mlse_db_ = MLSE("DIR",[1,1],"duobinary_output",0,"M",M,"trellis_states",PAMmapper(M,0).levels);
|
||||
|
||||
eq_post = FFE("epochs_tr",5,"epochs_dd",5,"len_tr",4096*2,"mu_dd",1e-4,"mu_tr",0,"order",2001,"sps",1,"decide",0,"adaption_technique","lms");
|
||||
|
||||
eq_post =FFE("epochs_tr",5,"epochs_dd",2,"len_tr",2^13,"mu_dd",mu_dd,"mu_tr",mu_tr,"order",25,"sps",2,"decide",0, "adaption",adaption_method(adaption),"dd_mode",use_dd_mode);
|
||||
% Duobinary signaling (db encoded)
|
||||
mlse_db_enc = MLSE("DIR", [1,1], "duobinary_output", 0, "M", M, "trellis_states", PAMmapper(M,0).levels);
|
||||
eq_db_enc = EQ("Ne", ffe_order, "Nb", dfe_order, "training_length", len_tr, ...
|
||||
@@ -194,60 +193,78 @@ try
|
||||
if use_vnle_mlse
|
||||
|
||||
pf_ncoeffs = 1;
|
||||
ffe_order = [50, 5, 5];
|
||||
eq_ = EQ("Ne",ffe_order,"Nb",dfe_order,"training_length",len_tr,"training_loops",5,"dd_loops",5,"K",2,"DCmu",mu_dc,"DDmu",[mu_ffe mu_dfe],"DFEmu",0.005,"FFEmu",0,"plotfinal",0,"ideal_dfe",1);
|
||||
pf_ = Postfilter("ncoeff",pf_ncoeffs,"useBurg",1);
|
||||
% mlse_ = MLSE_viterbi("duobinary_output",0,'M',M,'trellis_states',PAMmapper(M,0).levels);
|
||||
mlse_ = MLSE("duobinary_output",0,'M',M,'trellis_states',PAMmapper(M,0).levels);
|
||||
|
||||
useviterbi = 0;
|
||||
if useviterbi
|
||||
mlse_ = MLSE_viterbi("duobinary_output",0,'M',M,'trellis_states',PAMmapper(M,0).levels);
|
||||
else
|
||||
mlse_ = MLSE("duobinary_output",0,'M',M,'trellis_states',PAMmapper(M,0).levels);
|
||||
end
|
||||
|
||||
[ffe_results, mlse_results] = vnle_postfilter_mlse(eq_, pf_, mlse_, M, Scpe_sig, Symbols, Tx_bits, ...
|
||||
"precode_mode", duob_mode,...
|
||||
'showAnalysis', 1, ...
|
||||
'showAnalysis', 0, ...
|
||||
"postFFE", [],...
|
||||
"eth_style_symbol_mapping", 0);
|
||||
|
||||
ffe_results.metrics.print;
|
||||
ffe_results.config.equalizer_structure = "vnle";
|
||||
mlse_results.metrics.print;
|
||||
|
||||
|
||||
output.mlse_package{r} = mlse_results;
|
||||
output.vnle_package{r} = ffe_results;
|
||||
|
||||
|
||||
if options.append_to_db
|
||||
database.addProcessingResult(run_id, mlse_results.metrics, mlse_results.config);
|
||||
database.addProcessingResult(run_id, ffe_results.metrics, ffe_results.config);
|
||||
end
|
||||
|
||||
pf_ncoeffs = 2;
|
||||
eq_ = EQ("Ne",ffe_order,"Nb",dfe_order,"training_length",len_tr,"training_loops",5,"dd_loops",5,"K",2,"DCmu",mu_dc,"DDmu",[mu_ffe mu_dfe],"DFEmu",0.005,"FFEmu",0,"plotfinal",0,"ideal_dfe",1);
|
||||
pf_ = Postfilter("ncoeff",pf_ncoeffs,"useBurg",1);
|
||||
% mlse_ = MLSE_viterbi("duobinary_output",0,'M',M,'trellis_states',PAMmapper(M,0).levels);
|
||||
mlse_ = MLSE("duobinary_output",0,'M',M,'trellis_states',PAMmapper(M,0).levels);
|
||||
% pf_ncoeffs = 2;
|
||||
% eq_ = EQ("Ne",ffe_order,"Nb",dfe_order,"training_length",len_tr,"training_loops",5,"dd_loops",5,"K",2,"DCmu",mu_dc,"DDmu",[mu_ffe mu_dfe],"DFEmu",0.005,"FFEmu",0,"plotfinal",0,"ideal_dfe",1);
|
||||
% pf_ = Postfilter("ncoeff",pf_ncoeffs,"useBurg",1);
|
||||
% % mlse_ = MLSE_viterbi("duobinary_output",0,'M',M,'trellis_states',PAMmapper(M,0).levels);
|
||||
% mlse_ = MLSE("duobinary_output",0,'M',M,'trellis_states',PAMmapper(M,0).levels);
|
||||
%
|
||||
% [ffe_results, mlse_results] = vnle_postfilter_mlse(eq_, pf_, mlse_, M, Scpe_sig, Symbols, Tx_bits, ...
|
||||
% "precode_mode", duob_mode,...
|
||||
% 'showAnalysis', 0, ...
|
||||
% "postFFE", [],...
|
||||
% "eth_style_symbol_mapping", 0);
|
||||
%
|
||||
% ffe_results.metrics.print;
|
||||
% mlse_results.metrics.print;
|
||||
%
|
||||
% output.mlse_package{r} = mlse_results;
|
||||
% output.vnle_package{r} = ffe_results;
|
||||
%
|
||||
% if options.append_to_db
|
||||
% database.addProcessingResult(run_id, mlse_results.metrics, mlse_results.config);
|
||||
% database.addProcessingResult(run_id, ffe_results.metrics, ffe_results.config);
|
||||
% end
|
||||
|
||||
[ffe_results, mlse_results] = vnle_postfilter_mlse(eq_, pf_, mlse_, M, Scpe_sig, Symbols, Tx_bits, ...
|
||||
"precode_mode", duob_mode,...
|
||||
'showAnalysis', 1, ...
|
||||
"postFFE", [],...
|
||||
"eth_style_symbol_mapping", 0);
|
||||
|
||||
ffe_results.metrics.print;
|
||||
mlse_results.metrics.print;
|
||||
|
||||
output.mlse_package{r} = mlse_results;
|
||||
output.vnle_package{r} = ffe_results;
|
||||
|
||||
if options.append_to_db
|
||||
database.addProcessingResult(run_id, mlse_results.metrics, mlse_results.config);
|
||||
database.addProcessingResult(run_id, ffe_results.metrics, ffe_results.config);
|
||||
end
|
||||
end
|
||||
|
||||
if use_dbtgt
|
||||
|
||||
useviterbi = 0;
|
||||
if useviterbi
|
||||
mlse_db_ = MLSE_viterbi("duobinary_output",0,'M',M,'trellis_states',PAMmapper(M,0).levels);
|
||||
else
|
||||
mlse_db_ = MLSE("DIR",[1,1],"duobinary_output",0,"M",M,"trellis_states",PAMmapper(M,0).levels);
|
||||
end
|
||||
ffe_order = [50, 5, 5];
|
||||
eq_ = EQ("Ne",ffe_order,"Nb",dfe_order,"training_length",len_tr,"training_loops",5,"dd_loops",5,"K",2,"DCmu",mu_dc,"DDmu",[mu_ffe mu_dfe],"DFEmu",0.005,"FFEmu",0,"plotfinal",0,"ideal_dfe",1);
|
||||
|
||||
dbt_results = duobinary_target(eq_, mlse_db_, M, Scpe_sig, Symbols, Tx_bits, ...
|
||||
"precode_mode", duob_mode, ...
|
||||
'showAnalysis', 0,...
|
||||
"postFFE", []);
|
||||
|
||||
dbt_results.metrics.print;
|
||||
|
||||
output.dbtgt_package{r} = dbt_results;
|
||||
|
||||
if options.append_to_db
|
||||
|
||||
@@ -23,8 +23,14 @@ if ~isempty(options.postFFE)
|
||||
end
|
||||
|
||||
mlse_.DIR = [1,1];
|
||||
% mlse_sig_sd = mlse_.process(eq_signal);
|
||||
[mlse_sig_sd,LLR,GMI_MLSE] = mlse_.process(eq_signal,tx_symbols);
|
||||
%
|
||||
|
||||
if isa(mlse_,'MLSE_viterbi')
|
||||
mlse_sig_sd = mlse_.process(eq_signal);
|
||||
else
|
||||
[mlse_sig_sd,LLR,GMI_MLSE] = mlse_.process(eq_signal,tx_symbols);
|
||||
end
|
||||
|
||||
mlse_sig_hd = PAMmapper(M,0,"eth_style",options.eth_style_symbol_mapping).quantize(mlse_sig_sd);
|
||||
|
||||
% precoding to mitigate error propagation, most prominently used in
|
||||
@@ -43,8 +49,8 @@ switch options.precode_mode
|
||||
tx_symbols_precoded = Duobinary().decode(tx_symbols_precoded);
|
||||
|
||||
tx_bits_precoded = PAMmapper(M,0,"eth_style",options.eth_style_symbol_mapping).demap(tx_symbols_precoded);
|
||||
|
||||
rx_bits_mlse = PAMmapper(M,0,"eth_style",options.eth_style_symbol_mapping).demap(mlse_sig_hd_precoded);
|
||||
|
||||
[~,errors_db_diff_precoded,ber_db_diff_precoded,~] = calc_ber(rx_bits_mlse.signal,tx_bits_precoded.signal,"skip_front",100,"skip_end",150,"returnErrorLocation",1);
|
||||
|
||||
%B) Just determine BER
|
||||
@@ -59,24 +65,42 @@ switch options.precode_mode
|
||||
mlse_sig_hd_decoded = Duobinary().encode(mlse_sig_hd,"M",M);
|
||||
mlse_sig_hd_decoded = Duobinary().decode(mlse_sig_hd_decoded,"M",M);
|
||||
rx_bits_mlse_decoded = PAMmapper(M,0,"eth_style",options.eth_style_symbol_mapping).demap(mlse_sig_hd_decoded);
|
||||
[~,errors_db_diff_precoded,ber_db_diff_precoded,~] = calc_ber(rx_bits_mlse_decoded.signal,tx_bits.signal,"skip_front",100,"skip_end",150,"returnErrorLocation",1);
|
||||
|
||||
[~,errors_db_diff_precoded,ber_db_diff_precoded,a] = calc_ber(rx_bits_mlse_decoded.signal,tx_bits.signal,"skip_front",100,"skip_end",150,"returnErrorLocation",1);
|
||||
burst_db_precoded = count_error_bursts(a, 40);
|
||||
% B) Omit the Coding by comparing with demapped TX symbol sequence
|
||||
|
||||
tx_bits = PAMmapper(M,0,"eth_style",options.eth_style_symbol_mapping).demap(tx_symbols);
|
||||
rx_bits_mlse = PAMmapper(M,0,"eth_style",options.eth_style_symbol_mapping).demap(mlse_sig_hd);
|
||||
[bits_db,errors_db,ber_db,~] = calc_ber(rx_bits_mlse.signal,tx_bits.signal,"skip_front",100,"skip_end",150,"returnErrorLocation",1);
|
||||
[bits_db,errors_db,ber_db,a] = calc_ber(rx_bits_mlse.signal,tx_bits.signal,"skip_front",100,"skip_end",150,"returnErrorLocation",1);
|
||||
burst_db = count_error_bursts(a, 40);
|
||||
|
||||
cols = linspecer(8);
|
||||
figure();hold on;
|
||||
stem(1:40,burst_db,'LineWidth',1,'Color',cols(4,:),'Marker','_','DisplayName','w/o diff. precoder');
|
||||
stem(1:40,burst_db_precoded,'LineWidth',1,'Color',cols(3,:),'Marker','.','LineStyle','-','DisplayName','w diff. precoder');
|
||||
xlabel('Bit Error Burst Length')
|
||||
ylabel('Occurence')
|
||||
set(gca, 'yscale', 'log');
|
||||
end
|
||||
|
||||
% M = numel(unique(tx_symbols.signal));
|
||||
rx_bits = PAMmapper(M,0,"eth_style",options.eth_style_symbol_mapping).demap(mlse_sig_hd);
|
||||
|
||||
[bits_db,errors_db,ber_db,errorIndice_db] = calc_ber(rx_bits.signal,tx_bits.signal,"skip_front",100,"skip_end",150,"returnErrorLocation",1);
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
alpha = arburg(eq_noise.signal,1);%pf_.coefficients(2);
|
||||
alpha = alpha(2);
|
||||
gmi_mlse = GMI_MLSE;
|
||||
air_mlse = tx_symbols.fs .* floor(log2(double(M))*10)/10 .* gmi_mlse ./ log2(double(M));
|
||||
if isa(mlse_,'MLSE_viterbi')
|
||||
gmi_mlse = NaN;
|
||||
air_mlse = NaN;
|
||||
else
|
||||
gmi_mlse = GMI_MLSE;
|
||||
air_mlse = tx_symbols.fs .* floor(log2(double(M))*10)/10 .* gmi_mlse ./ log2(double(M));
|
||||
end
|
||||
|
||||
db_results = struct();
|
||||
db_results.metrics = Metricstruct;
|
||||
|
||||
@@ -49,7 +49,10 @@ eq_signal_hd = PAMmapper(M, 0).quantize(eq_signal_sd);
|
||||
|
||||
%% Calculate performance metrics
|
||||
[snr, snr_lvl] = calc_snr(tx_symbols.signal, eq_noise.signal);
|
||||
[gmi] = calc_air(eq_signal_sd, tx_symbols, "skip_front", 10000, "skip_end", 10000);
|
||||
% [gmi] = calc_air(eq_signal_sd, tx_symbols, "skip_front", 10000, "skip_end", 10000);
|
||||
[gmi] = calc_ngmi(eq_signal_sd,tx_symbols);
|
||||
gmi = max(gmi,0);
|
||||
|
||||
air = tx_symbols.fs .* floor(log2(double(M))*10)/10 .* gmi ./ log2(double(M));
|
||||
[evm_total, evm_lvl] = calc_evm(eq_signal_sd, tx_symbols);
|
||||
[std_total, std_lvl] = calc_std(eq_signal_sd, tx_symbols);
|
||||
|
||||
@@ -34,7 +34,7 @@ end
|
||||
% FFE or VNLE
|
||||
[eq_signal_sd, eq_noise] = eq_.process(rx_signal, tx_symbols);
|
||||
|
||||
% Apply post-FFE if provided
|
||||
% Apply post-FFE if provided (does not work properly at the moment...very sad)
|
||||
if ~isempty(options.postFFE)
|
||||
tic
|
||||
[eq_signal_sd, eq_noise] = options.postFFE.process(eq_signal_sd, tx_symbols);
|
||||
@@ -43,13 +43,18 @@ end
|
||||
|
||||
% Hard decision on VNLE output
|
||||
eq_signal_hd = PAMmapper(M, 0).quantize(eq_signal_sd);
|
||||
eq_signal_hd.spectrum("displayname",'after full response FFE','fignum',2025,'normalizeTo0dB',1);
|
||||
|
||||
% Process through postfilter and MLSE
|
||||
[mlse_sig_sd,whitened_noise] = pf_.process(eq_signal_sd, eq_noise);
|
||||
mlse_.DIR = pf_.coefficients;
|
||||
|
||||
[mlse_sig_sd,LLR,GMI_MLSE] = mlse_.process(mlse_sig_sd,tx_symbols);
|
||||
GMI_MLSE = NaN;
|
||||
if isa(mlse_,'MLSE_viterbi')
|
||||
[mlse_sig_sd] = mlse_.process(mlse_sig_sd);
|
||||
else
|
||||
[mlse_sig_sd,LLR,GMI_MLSE] = mlse_.process(mlse_sig_sd,tx_symbols);
|
||||
end
|
||||
|
||||
mlse_sig_hd = PAMmapper(M, 0, "eth_style", options.eth_style_symbol_mapping).quantize(mlse_sig_sd);
|
||||
|
||||
%% Calculate BER based on precoding mode
|
||||
@@ -58,7 +63,12 @@ mlse_sig_hd = PAMmapper(M, 0, "eth_style", options.eth_style_symbol_mapping).qua
|
||||
%% Calculate performance metrics
|
||||
% VNLE metrics
|
||||
[snr_vnle, snr_vnle_lvl] = calc_snr(tx_symbols.signal, eq_noise.signal);
|
||||
[gmi_vnle] = calc_air(eq_signal_sd, tx_symbols, "skip_front", 10000, "skip_end", 10000);
|
||||
% [gmi_vnle] = calc_air(eq_signal_sd, tx_symbols, "skip_front", 10000, "skip_end", 10000);
|
||||
|
||||
%calculate bitwise GMI
|
||||
[gmi_vnle] = calc_ngmi(eq_signal_sd,tx_symbols);
|
||||
gmi_vnle = max(gmi_vnle,0);
|
||||
|
||||
air_vnle = tx_symbols.fs .* floor(log2(double(M))*10)/10 .* gmi_vnle ./ log2(double(M));
|
||||
[evm_vnle_total, evm_vnle_lvl] = calc_evm(eq_signal_sd, tx_symbols);
|
||||
[std_vnle_total, std_vnle_lvl] = calc_std(eq_signal_sd, tx_symbols);
|
||||
@@ -67,7 +77,7 @@ air_vnle = tx_symbols.fs .* floor(log2(double(M))*10)/10 .* gmi_vnle ./ log2(dou
|
||||
% MLSE metrics
|
||||
alpha = arburg(eq_noise.signal,1);%pf_.coefficients(2);
|
||||
alpha = alpha(2);
|
||||
gmi_mlse = GMI_MLSE;
|
||||
gmi_mlse = max(GMI_MLSE,0);
|
||||
air_mlse = tx_symbols.fs .* floor(log2(double(M))*10)/10 .* gmi_mlse ./ log2(double(M));
|
||||
|
||||
%% Display analysis if requested
|
||||
@@ -77,6 +87,10 @@ end
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
%% Prepare output structures
|
||||
% Determine postFFE order
|
||||
if ~isempty(options.postFFE)
|
||||
@@ -119,8 +133,6 @@ ffe_results.config.eq = jsonencode(eq_);
|
||||
ffe_results.config.equalizer_structure = int32(equalizer_structure.vnle);
|
||||
ffe_results.config.comment = 'function: vnle_postfilter_mlse - FFE part';
|
||||
|
||||
|
||||
|
||||
mlse_results = struct();
|
||||
mlse_results.metrics = Metricstruct;
|
||||
mlse_results.metrics.result_id = NaN;
|
||||
@@ -141,7 +153,6 @@ mlse_results.metrics.Alpha = alpha;
|
||||
mlse_results.metrics.MLSE_dir = mlse_.DIR;
|
||||
|
||||
% Create MLSE results structure
|
||||
|
||||
mlse_results.config = Equalizerstruct();
|
||||
mlse_results.config.eq = jsonencode(eq_);
|
||||
mlse_.DIR = length(mlse_.DIR)-1;
|
||||
@@ -203,7 +214,7 @@ switch precode_mode
|
||||
mlse_sig_hd_decoded = Duobinary().encode(mlse_sig_hd, "M", M);
|
||||
mlse_sig_hd_decoded = Duobinary().decode(mlse_sig_hd_decoded, "M", M);
|
||||
rx_bits_mlse_decoded = mapper.demap(mlse_sig_hd_decoded);
|
||||
[~, errors.mlse_precoded, ber.mlse_precoded, ~] = calc_ber(rx_bits_mlse_decoded.signal, tx_bits.signal, "skip_front", 100, "skip_end", 150, "returnErrorLocation", 1);
|
||||
[~, errors.mlse_precoded, ber.mlse_precoded, err_loc_precoded] = calc_ber(rx_bits_mlse_decoded.signal, tx_bits.signal, "skip_front", 100, "skip_end", 150, "returnErrorLocation", 1);
|
||||
|
||||
% B) Omit the Coding by comparing with demapped TX symbol sequence
|
||||
tx_bits_demapped = mapper.demap(tx_symbols);
|
||||
@@ -213,6 +224,19 @@ switch precode_mode
|
||||
rx_bits_mlse = mapper.demap(mlse_sig_hd);
|
||||
[numbits.mlse, errors.mlse, ber.mlse, error_locations.mlse] = calc_ber(rx_bits_mlse.signal, tx_bits_demapped.signal, "skip_front", 100, "skip_end", 150, "returnErrorLocation", 1);
|
||||
end
|
||||
|
||||
% cols = linspecer(8);
|
||||
% burst_precoded = count_error_bursts(err_loc_precoded, 40);
|
||||
% burst_normal = count_error_bursts(error_locations.mlse, 40);
|
||||
% figure();hold on;
|
||||
% stem(1:40,burst_normal,'LineWidth',1,'Color',cols(1,:),'Marker','_','DisplayName','w/o diff. precoder');
|
||||
% stem(1:40,burst_precoded,'LineWidth',1,'Color',cols(2,:),'Marker','.','LineStyle','-','DisplayName','w diff. precoder');
|
||||
% xlabel('Bit Error Burst Length')
|
||||
% ylabel('Occurence')
|
||||
% set(gca, 'yscale', 'log');
|
||||
|
||||
|
||||
|
||||
end
|
||||
|
||||
|
||||
|
||||
85
Functions/EQ_visuals/show2Dconstellation.m
Normal file
85
Functions/EQ_visuals/show2Dconstellation.m
Normal file
@@ -0,0 +1,85 @@
|
||||
function [symbols_for_lvl,avg_for_lvl] = show2Dconstellation(eq_signal,ref_symbols,options)
|
||||
arguments
|
||||
eq_signal
|
||||
ref_symbols
|
||||
options.fignum (1,1) double = NaN % Default to NaN if not provided
|
||||
options.displayname (1,:) char = '' % Default to an empty string if not provided
|
||||
end
|
||||
|
||||
plot_shit = 1;
|
||||
|
||||
if isa(eq_signal,'Signal')
|
||||
eq_signal = eq_signal.signal;
|
||||
end
|
||||
if isa(ref_symbols,'Signal')
|
||||
ref_symbols = ref_symbols.signal;
|
||||
end
|
||||
|
||||
|
||||
if plot_shit
|
||||
% Determine the figure number to use or create a new figure
|
||||
if isnan(options.fignum)
|
||||
fig = figure; % Create a new figure and get its handle
|
||||
else
|
||||
fig = figure(options.fignum); % Use the specified figure number
|
||||
clf;
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
rx_symbols = eq_signal; %./ rms(eq_signal);
|
||||
correct_symbols = ref_symbols;
|
||||
|
||||
col = cbrewer2('Paired',numel(unique(correct_symbols))*2);
|
||||
ccnt = -1;
|
||||
|
||||
levels = unique(correct_symbols);
|
||||
M = numel(levels);
|
||||
symbols_for_lvl = NaN(numel(levels),length(correct_symbols));
|
||||
start = 1;
|
||||
ende = length(correct_symbols);
|
||||
|
||||
|
||||
|
||||
|
||||
for l = 1:numel(levels)
|
||||
ccnt = ccnt+2;
|
||||
|
||||
level_amplitude = levels(l);
|
||||
|
||||
symbols_for_lvl(l,correct_symbols==level_amplitude) = rx_symbols(correct_symbols==level_amplitude);
|
||||
|
||||
statistical_mean(l) = mean(symbols_for_lvl(l,:),'omitnan');
|
||||
|
||||
end
|
||||
|
||||
tx_even = correct_symbols(1:2:end);
|
||||
tx_odd = correct_symbols(2:2:end);
|
||||
|
||||
rx_even = rx_symbols(1:2:end);
|
||||
rx_odd = rx_symbols(2:2:end);
|
||||
|
||||
D_even = tx_even - rx_even;
|
||||
D_odd = tx_odd - rx_odd;
|
||||
|
||||
D = sqrt(D_even.^2 + D_odd.^2);
|
||||
|
||||
[X,Y] = meshgrid(levels, levels);
|
||||
[X_,Y_] = meshgrid(statistical_mean, statistical_mean);
|
||||
|
||||
hold on;
|
||||
scatter(rx_even,rx_odd,5*ones(1,length(D)),D,'.','DisplayName',['Even/Odd PAM-',num2str(M)],'MarkerEdgeColor',col(2,:));
|
||||
% colormap(gca,flip(cbrewer2('Spectral',100)))
|
||||
colormap(gca,'hsv');
|
||||
scatter(X_(:), Y_(:), 2, 'x', 'LineWidth', 10, 'MarkerEdgeColor', col(6,:),'DisplayName','Statistical Rx Levels');
|
||||
scatter(X(:), Y(:), 2, 'x', 'LineWidth', 10, 'MarkerEdgeColor', col(4,:),'DisplayName','Tx Levels');
|
||||
xlim([floor(min(X_(:)))-1, ceil(max(X_(:)))+1]);
|
||||
ylim([floor(min(Y_(:)))-1, ceil(max(Y_(:)))+1]);
|
||||
|
||||
yticks((levels(1:end-1) + levels(2:end)) / 2);
|
||||
xticks((levels(1:end-1) + levels(2:end)) / 2);
|
||||
legend
|
||||
xlabel('even symbols');
|
||||
ylabel('odd symbols');
|
||||
axis equal; grid on;
|
||||
end
|
||||
@@ -4,7 +4,7 @@ arguments
|
||||
ref_symbols
|
||||
options.fignum (1,1) double = NaN % Default to NaN if not provided
|
||||
options.displayname (1,:) char = '' % Default to an empty string if not provided
|
||||
options.f_sym = [];
|
||||
options.f_sym =1e6;
|
||||
end
|
||||
|
||||
plot_shit = 1;
|
||||
@@ -30,7 +30,7 @@ if plot_shit
|
||||
end
|
||||
|
||||
|
||||
rx_symbols = eq_signal ./ rms(eq_signal);
|
||||
rx_symbols = eq_signal; %./ rms(eq_signal);
|
||||
correct_symbols = ref_symbols;
|
||||
f_sym = options.f_sym;
|
||||
|
||||
@@ -47,7 +47,6 @@ for l = 1:numel(levels)
|
||||
|
||||
level_amplitude = levels(l);
|
||||
|
||||
|
||||
symbols_for_lvl(l,correct_symbols==level_amplitude) = rx_symbols(correct_symbols==level_amplitude);
|
||||
std_lvl(l) = std(symbols_for_lvl(l,:),'omitnan');
|
||||
xax_in_sec = ((1:length(correct_symbols)) / f_sym) * 1e6;
|
||||
@@ -68,7 +67,8 @@ for l = 1:numel(levels)
|
||||
ccnt = ccnt+2;
|
||||
level_amplitude = levels(l);
|
||||
|
||||
movmean = 1/250 .* movsum(rx_symbols(correct_symbols==level_amplitude),[250/2,250/2], 'Endpoints', 'fill');
|
||||
L = 500;
|
||||
movmean = 1/L .* movsum(rx_symbols(correct_symbols==level_amplitude),[L/2,L/2], 'Endpoints', 'fill');
|
||||
|
||||
avg_for_lvl(l,correct_symbols==level_amplitude) = movmean;
|
||||
|
||||
@@ -125,7 +125,7 @@ if 0
|
||||
end
|
||||
|
||||
if plot_shit
|
||||
yline(levels);
|
||||
% yline(levels);
|
||||
xlabel('Time in $\mu$s');
|
||||
ylabel('Normalized Amplitude');
|
||||
ylim([-3 3]);
|
||||
|
||||
@@ -12,12 +12,12 @@ function [Bits, Symbols, Scpe_cell, found_sync] = loadAndSyncSignalDataFromDb(da
|
||||
% found_sync - Boolean indicating if synchronization was successful
|
||||
|
||||
found_sync = 0;
|
||||
tempLocalStorage = 0;
|
||||
tempLocalStorage = 1;
|
||||
|
||||
% Define the fixed storage directory relative to the user's MATLAB preferences directory
|
||||
storage_dir = fullfile(prefdir, 'temp_sync_data');
|
||||
|
||||
% Part A: Check and load from local storage if available
|
||||
% Part A: Check and load from local storage if available-
|
||||
if tempLocalStorage == 1
|
||||
local_filename = fullfile(storage_dir, sprintf('sync_data_run_%s.mat', num2str(dataTable.run_id)));
|
||||
if exist(local_filename, 'file')
|
||||
|
||||
@@ -39,6 +39,5 @@ function [snr_all, snr_per_level] = calc_snr(tx_signal, eq_noise)
|
||||
% Compute the SNR for these indices
|
||||
snr_per_level(i) = snr(tx_signal(idx), eq_noise(idx));
|
||||
|
||||
histogram(eq_noise(idx));
|
||||
end
|
||||
end
|
||||
|
||||
@@ -21,8 +21,10 @@ function burst_count = count_error_bursts(err_pos, max_burst_length)
|
||||
|
||||
% Check if the burst length exceeds any of the thresholds
|
||||
for i = 1:max_burst_length
|
||||
if burst_length > i
|
||||
if burst_length == i
|
||||
burst_count(i) = burst_count(i) + 1;
|
||||
else
|
||||
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
Reference in New Issue
Block a user