% function ofdm_sync(x, nsym, ngrd) % Example: ofdm_sync(x, 1152, 128) function ofdm_rx(x, offset, nsym_soll, ngrd) % Init fa = 48000; fc = fa/4; F1 = 750; F2 = 2250; F3 = 3000; close all; do_evaluate = 1; alpha = 0.05; x = real(x); % Detection display('Sync detection'); nsym_ist = nsym_soll; xi = zeros(ngrd, 1); range_max = 24; range_min = 4; range_forget = 0.5; range = range_max; err = 0; k = 0; kk = 1; remain = length(x); progress_ival = 1; progress_last = -1; nfft = nsym_soll-ngrd bin_c = fix(nfft*fc/fa)+1 bin_f1 = fix(nfft*(fc+F1)/fa)+1 bin_f2 = fix(nfft*(fc+F2)/fa)+1 bin_f3 = fix(nfft*(fc+F3)/fa)+1 k_fft = 3/sqrt(nfft); phi_c_last = 0; phi_f1_last = 0; phi_f2_last = 0; phi_f3_last = 0; while remain > 2*nsym_ist, xsym = x(offset+k*nsym_ist+1:offset+k*nsym_ist+nsym_ist+range); [xcor, imax, jmax, xi] = xcc(xsym, nsym_ist, ngrd, -range, range, -range, range, xi); remain = remain - (length(offset+k*nsym_ist+1:offset+k*nsym_ist+nsym_ist+range)); err = -imax + jmax; offset = offset + imax; nsym_ist = max(round(nsym_ist + err), ngrd) sl_offset(kk) = offset; sl_err(kk) = err; sl_nsym_ist(kk) = nsym_ist; range = min(max(fix(range + abs(err) - range_forget), range_min), range_max); progress = round(100*(length(x)-remain)/length(x)); if (progress ~= progress_last) progress_last = progress_last + progress_ival; progress = progress end; if (do_evaluate == 1) X0 = k_fft*fft(xsym(1:nsym_ist-ngrd), nfft); phi_c(kk) = (1-alpha)*phi_c_last + alpha*angle(X0(bin_c)); phi_f1(kk) = (1-alpha)*phi_f1_last + alpha*angle(X0(bin_f1)); phi_f2(kk) = (1-alpha)*phi_f2_last + alpha*angle(X0(bin_f2)); phi_f3(kk) = (1-alpha)*phi_f3_last + alpha*angle(X0(bin_f3)); phi_c_last = phi_c(kk); phi_f1_last = phi_f1(kk); phi_f2_last = phi_f2(kk); phi_f3_last = phi_f3(kk); %pause; end; k = k + 1; kk = kk + 1; end; % Result display('Results:'); offset_stddev = sqrt(var(sl_offset)) err_mean = mean(sl_err) nsym_ist_mean = mean(nsym_ist) % Diagrams figure; plot(1:length(sl_offset), sl_offset); title('offset'); legend('offset'); grid; figure; subplot(2,1,1) plot(1:length(sl_err), sl_err); title('error'); legend('error'); grid; subplot(2,1,2) plot(1:length(sl_nsym_ist), sl_nsym_ist, 1:length(sl_nsym_ist), nsym_soll*ones(size(sl_nsym_ist))); title('Tracking'); legend('nsym_{ist}', 'nsym_{soll}'); grid; figure plot(1:length(phi_c), phi_c, 1:length(phi_f1), phi_f1, 1:length(phi_f2), phi_f2, 1:length(phi_f3), phi_f3); grid; legend('phi_{c}', 'phi_{f1}', 'phi_{f2}', 'phi_{f3}'); title('Phase'); % custom function % Correlation function [ccm, imax, jmax, xo] = xcc(x, Ns, Ng, i_low, i_high, j_low, j_high, xi) Nu = Ns - Ng; off = length(xi); xo = x(length(x)-off+1:length(x)); xs = [xi' x']'; ccm = 0; imax = 0; jmax = 0; for i_off=i_low:i_high, ii = off+i_off+1:off+Ng+i_off; xm_i = mean(xs(ii)); xi = xs(ii)-xm_i; var_i = var(xi); for j_off=j_low:j_high, jj = off+Nu+j_off+1:off+Nu+Ng+j_off; xm_j = mean(xs(jj)); xj = xs(jj) - xm_j; var_j = var(xj); cc = sum(xi.*xj)./sqrt(var_i*var_j); if (cc > ccm) imax = i_off; jmax = j_off; ccm = cc; end; end; end;