% LPF and peak pick part of freq est, put in a function as we call it twice
-function [foff imax pilot_lpf_out S] = lpf_peak_pick(pilot_baseband, pilot_lpf, nin)
+function [foff imax pilot_lpf_out S] = lpf_peak_pick(pilot_baseband, pilot_lpf, nin, do_fft)
global M;
global Npilotlpf;
global Npilotbaseband;
k++;
end
- % decimate to improve DFT resolution, window and DFT
+ imax = 0;
+ foff = 0;
+ S = zeros(1, Mpilotfft);
- Mpilot = Fs/(2*200); % calc decimation rate given new sample rate is twice LPF freq
- h = hanning(Npilotlpf);
- s = pilot_lpf(1:Mpilot:Npilotlpf) .* h(1:Mpilot:Npilotlpf)';
- s = [s zeros(1,Mpilotfft-Npilotlpf/Mpilot)];
- S = fft(s, Mpilotfft);
+ if do_fft
+ % decimate to improve DFT resolution, window and DFT
+
+ Mpilot = Fs/(2*200); % calc decimation rate given new sample rate is twice LPF freq
+ h = hanning(Npilotlpf);
+ s = pilot_lpf(1:Mpilot:Npilotlpf) .* h(1:Mpilot:Npilotlpf)';
+ s = [s zeros(1,Mpilotfft-Npilotlpf/Mpilot)];
+ S = fft(s, Mpilotfft);
- % peak pick and convert to Hz
+ % peak pick and convert to Hz
- [imax ix] = max(abs(S));
- r = 2*200/Mpilotfft; % maps FFT bin to frequency in Hz
+ [imax ix] = max(abs(S));
+ r = 2*200/Mpilotfft; % maps FFT bin to frequency in Hz
- if ix > Mpilotfft/2
- foff = (ix - Mpilotfft - 1)*r;
- else
- foff = (ix - 1)*r;
- endif
+ if ix > Mpilotfft/2
+ foff = (ix - Mpilotfft - 1)*r;
+ else
+ foff = (ix - 1)*r;
+ endif
+ end
pilot_lpf_out = pilot_lpf;
% Estimate frequency offset of FDM signal using BPSK pilot. This is quite
% sensitive to pilot tone level wrt other carriers
-function [foff S1 S2] = rx_est_freq_offset(rx_fdm, pilot, pilot_prev, nin)
+function [foff S1 S2] = rx_est_freq_offset(rx_fdm, pilot, pilot_prev, nin, do_fft)
global M;
global Npilotbaseband;
global pilot_baseband1;
pilot_baseband2(Npilotbaseband-nin+i) = rx_fdm(i) * conj(pilot_prev(i));
end
- [foff1 max1 pilot_lpf1 S1] = lpf_peak_pick(pilot_baseband1, pilot_lpf1, nin);
- [foff2 max2 pilot_lpf2 S2] = lpf_peak_pick(pilot_baseband2, pilot_lpf2, nin);
+ [foff1 max1 pilot_lpf1 S1] = lpf_peak_pick(pilot_baseband1, pilot_lpf1, nin, do_fft);
+ [foff2 max2 pilot_lpf2 S2] = lpf_peak_pick(pilot_baseband2, pilot_lpf2, nin, do_fft);
if max1 > max2
foff = foff1;
figure(2)
plot(s1(st1:en1)-s2(st2:en2));
+ f=fopen("diff.raw","wb");
+ d = s1(st1:en1)-s2(st2:en2);
+ fwrite(f,d,"short");
endfunction
fbb_phase_rx /= mag;
[pilot prev_pilot pilot_lut_index prev_pilot_lut_index] = get_pilot(pilot_lut_index, prev_pilot_lut_index, nin);
- [foff_coarse S1 S2] = rx_est_freq_offset(rx_fdm, pilot, prev_pilot, nin);
+ [foff_coarse S1 S2] = rx_est_freq_offset(rx_fdm, pilot, prev_pilot, nin, !sync);
%sync = 0; % when debugging good idea to uncomment this to "open loop"
{ NULL, no_argument, NULL, 0 }
};
int num_opts=sizeof(long_options)/sizeof(struct option);
-
+ COMP Aw[FFT_ENC];
+
for(i=0; i<M; i++) {
Sn[i] = 1.0;
Sn_pre[i] = 1.0;
}
- aks_to_M2(fft_fwd_cfg, ak, order, &model, e, &snr, 1, simlpcpf, lpcpf, 1, LPCPF_BETA, LPCPF_GAMMA);
+ aks_to_M2(fft_fwd_cfg, ak, order, &model, e, &snr, 1, simlpcpf, lpcpf, 1, LPCPF_BETA, LPCPF_GAMMA, Aw);
apply_lpc_correction(&model);
#ifdef DUMP
interp_model.voiced = voiced1;
+ #ifdef FIX_ME
+ /* NOTE: need to get this woking again */
+ interpolate_lsp_ver2(lsps_interp, prev_lsps_, lsps_, 0.5)
+ aks_to_M2(fft_fwd_cfg, ak, order, &model, e, &snr, 1, simlpcpf, lpcpf, 1, LPCPF_BETA, LPCPF_GAMMA, Aw);
interpolate_lsp(fft_fwd_cfg, &interp_model, &prev_model, &model,
prev_lsps_, prev_e, lsps_, e, ak_interp, lsps_interp);
+ #endif
apply_lpc_correction(&interp_model);
/* used to compare with c2enc/c2dec version
#endif
if (phase0)
- phase_synth_zero_order(fft_fwd_cfg, &interp_model, ak_interp, ex_phase,
- order);
+ phase_synth_zero_order(fft_fwd_cfg, &interp_model, ex_phase, Aw);
if (postfilt)
postfilter(&interp_model, &bg_est);
synth_one_frame(fft_inv_cfg, buf, &interp_model, Sn_, Pn, prede, &de_mem, gain);
/* decode this frame */
if (phase0)
- phase_synth_zero_order(fft_fwd_cfg, &model, ak, ex_phase, order);
+ phase_synth_zero_order(fft_fwd_cfg, &model, ex_phase, Aw);
if (postfilt)
postfilter(&model, &bg_est);
synth_one_frame(fft_inv_cfg, buf, &model, Sn_, Pn, prede, &de_mem, gain);
/* no decimation - sythesise each 10ms frame immediately */
if (phase0)
- phase_synth_zero_order(fft_fwd_cfg, &model, ak, ex_phase, order);
+ phase_synth_zero_order(fft_fwd_cfg, &model, ex_phase, Aw);
if (postfilt)
postfilter(&model, &bg_est);
void analyse_one_frame(struct CODEC2 *c2, MODEL *model, short speech[]);
void synthesise_one_frame(struct CODEC2 *c2, short speech[], MODEL *model,
- float ak[]);
+ COMP Aw[]);
void codec2_encode_3200(struct CODEC2 *c2, unsigned char * bits, short speech[]);
void codec2_decode_3200(struct CODEC2 *c2, short speech[], const unsigned char * bits);
void codec2_encode_2400(struct CODEC2 *c2, unsigned char * bits, short speech[]);
float ak[2][LPC_ORD+1];
int i,j;
unsigned int nbit = 0;
+ COMP Aw[2][FFT_ENC];
assert(c2 != NULL);
for(i=0; i<2; i++) {
lsp_to_lpc(&lsps[i][0], &ak[i][0], LPC_ORD);
aks_to_M2(c2->fft_fwd_cfg, &ak[i][0], LPC_ORD, &model[i], e[i], &snr, 0, 0,
- c2->lpc_pf, c2->bass_boost, c2->beta, c2->gamma);
+ c2->lpc_pf, c2->bass_boost, c2->beta, c2->gamma, &Aw[i][0]);
apply_lpc_correction(&model[i]);
}
/* synthesise ------------------------------------------------*/
for(i=0; i<2; i++)
- synthesise_one_frame(c2, &speech[N*i], &model[i], &ak[i][0]);
+ synthesise_one_frame(c2, &speech[N*i], &model[i], &Aw[i][0]);
/* update memories for next frame ----------------------------*/
float ak[2][LPC_ORD+1];
int i,j;
unsigned int nbit = 0;
+ COMP Aw[2][FFT_ENC];
assert(c2 != NULL);
for(i=0; i<2; i++) {
lsp_to_lpc(&lsps[i][0], &ak[i][0], LPC_ORD);
aks_to_M2(c2->fft_fwd_cfg, &ak[i][0], LPC_ORD, &model[i], e[i], &snr, 0, 0,
- c2->lpc_pf, c2->bass_boost, c2->beta, c2->gamma);
+ c2->lpc_pf, c2->bass_boost, c2->beta, c2->gamma, &Aw[i][0]);
apply_lpc_correction(&model[i]);
}
/* synthesise ------------------------------------------------*/
for(i=0; i<2; i++)
- synthesise_one_frame(c2, &speech[N*i], &model[i], &ak[i][0]);
+ synthesise_one_frame(c2, &speech[N*i], &model[i], &Aw[i][0]);
/* update memories for next frame ----------------------------*/
int i,j;
unsigned int nbit = 0;
float weight;
+ COMP Aw[4][FFT_ENC];
assert(c2 != NULL);
for(i=0; i<4; i++) {
lsp_to_lpc(&lsps[i][0], &ak[i][0], LPC_ORD);
aks_to_M2(c2->fft_fwd_cfg, &ak[i][0], LPC_ORD, &model[i], e[i], &snr, 0, 0,
- c2->lpc_pf, c2->bass_boost, c2->beta, c2->gamma);
+ c2->lpc_pf, c2->bass_boost, c2->beta, c2->gamma, &Aw[i][0]);
apply_lpc_correction(&model[i]);
}
/* synthesise ------------------------------------------------*/
for(i=0; i<4; i++)
- synthesise_one_frame(c2, &speech[N*i], &model[i], &ak[i][0]);
+ synthesise_one_frame(c2, &speech[N*i], &model[i], &Aw[i][0]);
/* update memories for next frame ----------------------------*/
int i,j;
unsigned int nbit = 0;
float weight;
+ COMP Aw[4][FFT_ENC];
assert(c2 != NULL);
for(i=0; i<4; i++) {
lsp_to_lpc(&lsps[i][0], &ak[i][0], LPC_ORD);
aks_to_M2(c2->fft_fwd_cfg, &ak[i][0], LPC_ORD, &model[i], e[i], &snr, 0, 0,
- c2->lpc_pf, c2->bass_boost, c2->beta, c2->gamma);
+ c2->lpc_pf, c2->bass_boost, c2->beta, c2->gamma, &Aw[i][0]);
apply_lpc_correction(&model[i]);
}
/* synthesise ------------------------------------------------*/
for(i=0; i<4; i++)
- synthesise_one_frame(c2, &speech[N*i], &model[i], &ak[i][0]);
+ synthesise_one_frame(c2, &speech[N*i], &model[i], &Aw[i][0]);
/* update memories for next frame ----------------------------*/
int i,j;
unsigned int nbit = 0;
float weight;
+ COMP Aw[4][FFT_ENC];
PROFILE_VAR(recover_start);
assert(c2 != NULL);
for(i=0; i<4; i++) {
lsp_to_lpc(&lsps[i][0], &ak[i][0], LPC_ORD);
aks_to_M2(c2->fft_fwd_cfg, &ak[i][0], LPC_ORD, &model[i], e[i], &snr, 0, 0,
- c2->lpc_pf, c2->bass_boost, c2->beta, c2->gamma);
+ c2->lpc_pf, c2->bass_boost, c2->beta, c2->gamma, &Aw[i][0]);
apply_lpc_correction(&model[i]);
}
PROFILE_SAMPLE_AND_LOG2(recover_start, " recover");
/* synthesise ------------------------------------------------*/
for(i=0; i<4; i++)
- synthesise_one_frame(c2, &speech[N*i], &model[i], &ak[i][0]);
+ synthesise_one_frame(c2, &speech[N*i], &model[i], &Aw[i][0]);
/* update memories for next frame ----------------------------*/
int i,j;
unsigned int nbit = 0;
float weight;
+ COMP Aw[4][FFT_ENC];
assert(c2 != NULL);
for(i=0; i<4; i++) {
lsp_to_lpc(&lsps[i][0], &ak[i][0], LPC_ORD);
aks_to_M2(c2->fft_fwd_cfg, &ak[i][0], LPC_ORD, &model[i], e[i], &snr, 0, 0,
- c2->lpc_pf, c2->bass_boost, c2->beta, c2->gamma);
+ c2->lpc_pf, c2->bass_boost, c2->beta, c2->gamma, &Aw[i][0]);
apply_lpc_correction(&model[i]);
}
/* synthesise ------------------------------------------------*/
for(i=0; i<4; i++)
- synthesise_one_frame(c2, &speech[N*i], &model[i], &ak[i][0]);
+ synthesise_one_frame(c2, &speech[N*i], &model[i], &Aw[i][0]);
/* update memories for next frame ----------------------------*/
\*---------------------------------------------------------------------------*/
-void synthesise_one_frame(struct CODEC2 *c2, short speech[], MODEL *model, float ak[])
+void synthesise_one_frame(struct CODEC2 *c2, short speech[], MODEL *model, COMP Aw[])
{
int i;
PROFILE_VAR(phase_start, pf_start, synth_start);
PROFILE_SAMPLE(phase_start);
- phase_synth_zero_order(c2->fft_fwd_cfg, model, ak, &c2->ex_phase, LPC_ORD);
+ phase_synth_zero_order(c2->fft_fwd_cfg, model, &c2->ex_phase, Aw);
PROFILE_SAMPLE_AND_LOG(pf_start, phase_start, " phase_synth");
\*---------------------------------------------------------------------------*/
void lpf_peak_pick(float *foff, float *max, COMP pilot_baseband[],
- COMP pilot_lpf[], kiss_fft_cfg fft_pilot_cfg, COMP S[], int nin)
+ COMP pilot_lpf[], kiss_fft_cfg fft_pilot_cfg, COMP S[], int nin,
+ int do_fft)
{
int i,j,k;
int mpilot;
pilot_lpf[i] = cadd(pilot_lpf[i], fcmult(pilot_coeff[k], pilot_baseband[j-NPILOTCOEFF+1+k]));
}
- /* decimate to improve DFT resolution, window and DFT */
+ /* We only need to do FFTs if we are out of sync. Making them optional saves CPU in sync, which is when
+ we need to run the codec */
- mpilot = FS/(2*200); /* calc decimation rate given new sample rate is twice LPF freq */
+ imax = 0.0;
+ *foff = 0.0;
for(i=0; i<MPILOTFFT; i++) {
- s[i].real = 0.0; s[i].imag = 0.0;
- }
- for(i=0,j=0; i<NPILOTLPF; i+=mpilot,j++) {
- s[j] = fcmult(hanning[i], pilot_lpf[i]);
+ S[i].real = 0.0;
+ S[i].imag = 0.0;
}
- kiss_fft(fft_pilot_cfg, (kiss_fft_cpx *)s, (kiss_fft_cpx *)S);
+ if (do_fft) {
+
+ /* decimate to improve DFT resolution, window and DFT */
- /* peak pick and convert to Hz */
+ mpilot = FS/(2*200); /* calc decimation rate given new sample rate is twice LPF freq */
+ for(i=0; i<MPILOTFFT; i++) {
+ s[i].real = 0.0; s[i].imag = 0.0;
+ }
+ for(i=0,j=0; i<NPILOTLPF; i+=mpilot,j++) {
+ s[j] = fcmult(hanning[i], pilot_lpf[i]);
+ }
- imax = 0.0;
- ix = 0;
- for(i=0; i<MPILOTFFT; i++) {
- mag = S[i].real*S[i].real + S[i].imag*S[i].imag;
- if (mag > imax) {
- imax = mag;
- ix = i;
- }
- }
- r = 2.0*200.0/MPILOTFFT; /* maps FFT bin to frequency in Hz */
+ kiss_fft(fft_pilot_cfg, (kiss_fft_cpx *)s, (kiss_fft_cpx *)S);
+
+ /* peak pick and convert to Hz */
+
+ imax = 0.0;
+ ix = 0;
+ for(i=0; i<MPILOTFFT; i++) {
+ mag = S[i].real*S[i].real + S[i].imag*S[i].imag;
+ if (mag > imax) {
+ imax = mag;
+ ix = i;
+ }
+ }
+ r = 2.0*200.0/MPILOTFFT; /* maps FFT bin to frequency in Hz */
- if (ix >= MPILOTFFT/2)
- *foff = (ix - MPILOTFFT)*r;
- else
- *foff = (ix)*r;
+ if (ix >= MPILOTFFT/2)
+ *foff = (ix - MPILOTFFT)*r;
+ else
+ *foff = (ix)*r;
+ }
+
*max = imax;
}
\*---------------------------------------------------------------------------*/
-float rx_est_freq_offset(struct FDMDV *f, COMP rx_fdm[], int nin)
+float rx_est_freq_offset(struct FDMDV *f, COMP rx_fdm[], int nin, int do_fft)
{
int i,j;
COMP pilot[M+M/P];
f->pilot_baseband2[j] = cmult(rx_fdm[i], cconj(prev_pilot[i]));
}
- lpf_peak_pick(&foff1, &max1, f->pilot_baseband1, f->pilot_lpf1, f->fft_pilot_cfg, f->S1, nin);
- lpf_peak_pick(&foff2, &max2, f->pilot_baseband2, f->pilot_lpf2, f->fft_pilot_cfg, f->S2, nin);
+ lpf_peak_pick(&foff1, &max1, f->pilot_baseband1, f->pilot_lpf1, f->fft_pilot_cfg, f->S1, nin, do_fft);
+ lpf_peak_pick(&foff2, &max2, f->pilot_baseband2, f->pilot_lpf2, f->fft_pilot_cfg, f->S2, nin, do_fft);
if (max1 > max2)
foff = foff1;
/* freq offset estimation and correction */
PROFILE_SAMPLE(demod_start);
- foff_coarse = rx_est_freq_offset(fdmdv, rx_fdm_bb, *nin);
+ foff_coarse = rx_est_freq_offset(fdmdv, rx_fdm_bb, *nin, !fdmdv->sync);
PROFILE_SAMPLE_AND_LOG(fdmdv_freq_shift_start, demod_start, " rx_est_freq_offset");
if (fdmdv->sync == 0)
COMP phase_tx[], COMP freq[], COMP *fbb_phase, COMP fbb_rect);
void generate_pilot_fdm(COMP *pilot_fdm, int *bit, float *symbol, float *filter_mem, COMP *phase, COMP *freq);
void generate_pilot_lut(COMP pilot_lut[], COMP *pilot_freq);
-float rx_est_freq_offset(struct FDMDV *f, COMP rx_fdm[], int nin);
-void lpf_peak_pick(float *foff, float *max, COMP pilot_baseband[], COMP pilot_lpf[], kiss_fft_cfg fft_pilot_cfg, COMP S[], int nin);
+float rx_est_freq_offset(struct FDMDV *f, COMP rx_fdm[], int nin, int do_fft);
+void lpf_peak_pick(float *foff, float *max, COMP pilot_baseband[], COMP pilot_lpf[], kiss_fft_cfg fft_pilot_cfg, COMP S[], int nin, int do_fft);
void fdm_downconvert(COMP rx_baseband[NC+1][M+M/P], int Nc, COMP rx_fdm[], COMP phase_rx[], COMP freq[], int nin);
void rxdec_filter(COMP rx_fdm_filter[], COMP rx_fdm[], COMP rxdec_lpf_mem[], int nin);
void rx_filter(COMP rx_filt[NC+1][P+1], int Nc, COMP rx_baseband[NC+1][M+M/P], COMP rx_filter_memory[NC+1][NFILTER], int nin);
return log_amp;
}
+#ifdef NOT_NEEDED
+
/*---------------------------------------------------------------------------*\
FUNCTION....: interp_lsp()
aks_to_M2(fft_fwd_cfg, ak_interp, LPC_ORD, interp, e, &snr, 0, 0, 1, 1, LPCPF_BETA, LPCPF_GAMMA);
//printf(" interp: ak[1]: %f A[1] %f\n", ak_interp[1], interp->A[1]);
}
-
+#endif
/*---------------------------------------------------------------------------*\
#include <string.h>
#include <stdlib.h>
-/*---------------------------------------------------------------------------*\
-
- aks_to_H()
-
- Samples the complex LPC synthesis filter spectrum at the harmonic
- frequencies.
-
-\*---------------------------------------------------------------------------*/
-
-void aks_to_H(
- kiss_fft_cfg fft_fwd_cfg,
- MODEL *model, /* model parameters */
- float aks[], /* LPC's */
- float G, /* energy term */
- COMP H[], /* complex LPC spectral samples */
- int order
-)
-{
- COMP pw[FFT_ENC]; /* power spectrum (input) */
- COMP Pw[FFT_ENC]; /* power spectrum (output) */
- int i,m; /* loop variables */
- int am,bm; /* limits of current band */
- float r; /* no. rads/bin */
- float Em; /* energy in band */
- float Am; /* spectral amplitude sample */
- int b; /* centre bin of harmonic */
- float phi_; /* phase of LPC spectra */
-
- r = TWO_PI/(FFT_ENC);
-
- /* Determine DFT of A(exp(jw)) ------------------------------------------*/
-
- for(i=0; i<FFT_ENC; i++) {
- pw[i].real = 0.0;
- pw[i].imag = 0.0;
- }
-
- for(i=0; i<=order; i++)
- pw[i].real = aks[i];
-
- kiss_fft(fft_fwd_cfg, (kiss_fft_cpx *)pw, (kiss_fft_cpx *)Pw);
-
- /* Sample magnitude and phase at harmonics */
-
- for(m=1; m<=model->L; m++) {
- am = (int)((m - 0.5)*model->Wo/r + 0.5);
- bm = (int)((m + 0.5)*model->Wo/r + 0.5);
- b = (int)(m*model->Wo/r + 0.5);
-
- Em = 0.0;
- for(i=am; i<bm; i++)
- Em += G/(Pw[i].real*Pw[i].real + Pw[i].imag*Pw[i].imag);
- Am = sqrtf(fabsf(Em/(bm-am)));
-
- phi_ = -atan2f(Pw[b].imag,Pw[b].real);
- H[m].real = Am*cosf(phi_);
- H[m].imag = Am*sinf(phi_);
- }
-}
-
/*---------------------------------------------------------------------------*\
void phase_synth_zero_order(
kiss_fft_cfg fft_fwd_cfg,
MODEL *model,
- float aks[],
float *ex_phase, /* excitation phase of fundamental */
- int order
+ COMP A[]
)
{
- int m;
- float new_phi;
- COMP Ex[MAX_AMP+1]; /* excitation samples */
- COMP A_[MAX_AMP+1]; /* synthesised harmonic samples */
- COMP H[MAX_AMP+1]; /* LPC freq domain samples */
- float G;
-
- G = 1.0;
- aks_to_H(fft_fwd_cfg, model, aks, G, H, order);
-
- /*
- Update excitation fundamental phase track, this sets the position
- of each pitch pulse during voiced speech. After much experiment
- I found that using just this frame's Wo improved quality for UV
- sounds compared to interpolating two frames Wo like this:
+ int m, b;
+ float phi_, new_phi, r;
+ COMP Ex[MAX_AMP+1]; /* excitation samples */
+ COMP A_[MAX_AMP+1]; /* synthesised harmonic samples */
+ COMP H[MAX_AMP+1]; /* LPC freq domain samples */
+
+ r = TWO_PI/(FFT_ENC);
+
+ /* Sample phase at harmonics */
+
+ for(m=1; m<=model->L; m++) {
+ b = (int)(m*model->Wo/r + 0.5);
+ phi_ = -atan2f(A[b].imag, A[b].real);
+ H[m].real = cosf(phi_);
+ H[m].imag = sinf(phi_);
+ }
+
+ /*
+ Update excitation fundamental phase track, this sets the position
+ of each pitch pulse during voiced speech. After much experiment
+ I found that using just this frame's Wo improved quality for UV
+ sounds compared to interpolating two frames Wo like this:
- ex_phase[0] += (*prev_Wo+model->Wo)*N/2;
- */
+ ex_phase[0] += (*prev_Wo+model->Wo)*N/2;
+ */
- ex_phase[0] += (model->Wo)*N;
- ex_phase[0] -= TWO_PI*floorf(ex_phase[0]/TWO_PI + 0.5);
+ ex_phase[0] += (model->Wo)*N;
+ ex_phase[0] -= TWO_PI*floorf(ex_phase[0]/TWO_PI + 0.5);
- for(m=1; m<=model->L; m++) {
+ for(m=1; m<=model->L; m++) {
- /* generate excitation */
+ /* generate excitation */
- if (model->voiced) {
+ if (model->voiced) {
- Ex[m].real = cosf(ex_phase[0]*m);
- Ex[m].imag = sinf(ex_phase[0]*m);
- }
- else {
-
- /* When a few samples were tested I found that LPC filter
- phase is not needed in the unvoiced case, but no harm in
- keeping it.
- */
- float phi = TWO_PI*(float)codec2_rand()/CODEC2_RAND_MAX;
- Ex[m].real = cosf(phi);
- Ex[m].imag = sinf(phi);
- }
+ Ex[m].real = cosf(ex_phase[0]*m);
+ Ex[m].imag = sinf(ex_phase[0]*m);
+ }
+ else {
+
+ /* When a few samples were tested I found that LPC filter
+ phase is not needed in the unvoiced case, but no harm in
+ keeping it.
+ */
+ float phi = TWO_PI*(float)codec2_rand()/CODEC2_RAND_MAX;
+ Ex[m].real = cosf(phi);
+ Ex[m].imag = sinf(phi);
+ }
- /* filter using LPC filter */
+ /* filter using LPC filter */
- A_[m].real = H[m].real*Ex[m].real - H[m].imag*Ex[m].imag;
- A_[m].imag = H[m].imag*Ex[m].real + H[m].real*Ex[m].imag;
+ A_[m].real = H[m].real*Ex[m].real - H[m].imag*Ex[m].imag;
+ A_[m].imag = H[m].imag*Ex[m].real + H[m].real*Ex[m].imag;
- /* modify sinusoidal phase */
+ /* modify sinusoidal phase */
- new_phi = atan2f(A_[m].imag, A_[m].real+1E-12);
- model->phi[m] = new_phi;
- }
+ new_phi = atan2f(A_[m].imag, A_[m].real+1E-12);
+ model->phi[m] = new_phi;
+ }
}
#define __PHASE__
#include "kiss_fft.h"
+#include "comp.h"
void phase_synth_zero_order(kiss_fft_cfg fft_dec_cfg,
MODEL *model,
- float aks[],
- float *ex_phase,
- int order);
+ float *ex_phase,
+ COMP A[]);
#endif
{
int i;
COMP x[FFT_ENC]; /* input to FFTs */
- COMP Aw[FFT_ENC]; /* LPC analysis filter spectrum */
COMP Ww[FFT_ENC]; /* weighting spectrum */
float Rw[FFT_ENC]; /* R = WA */
float e_before, e_after, gain;
int pf, /* true to LPC post filter */
int bass_boost, /* enable LPC filter 0-1khz 3dB boost */
float beta,
- float gamma /* LPC post filter parameters */
+ float gamma, /* LPC post filter parameters */
+ COMP Aw[] /* output power spectrum */
)
{
- COMP pw[FFT_ENC]; /* input to FFT for power spectrum */
+ COMP a[FFT_ENC]; /* input to FFT for power spectrum */
COMP Pw[FFT_ENC]; /* output power spectrum */
int i,m; /* loop variables */
int am,bm; /* limits of current band */
/* Determine DFT of A(exp(jw)) --------------------------------------------*/
for(i=0; i<FFT_ENC; i++) {
- pw[i].real = 0.0;
- pw[i].imag = 0.0;
+ a[i].real = 0.0;
+ a[i].imag = 0.0;
+ Pw[i].real = 0.0;
+ Pw[i].imag = 0.0;
}
for(i=0; i<=order; i++)
- pw[i].real = ak[i];
- kiss_fft(fft_fwd_cfg, (kiss_fft_cpx *)pw, (kiss_fft_cpx *)Pw);
-
+ a[i].real = ak[i];
+ kiss_fft(fft_fwd_cfg, (kiss_fft_cpx *)a, (kiss_fft_cpx *)Aw);
+
PROFILE_SAMPLE_AND_LOG(tfft, tstart, " fft");
/* Determine power spectrum P(w) = E/(A(exp(jw))^2 ------------------------*/
for(i=0; i<FFT_ENC/2; i++)
- Pw[i].real = 1.0/(Pw[i].real*Pw[i].real + Pw[i].imag*Pw[i].imag);
+ Pw[i].real = 1.0/(Aw[i].real*Aw[i].real + Aw[i].imag*Aw[i].imag);
PROFILE_SAMPLE_AND_LOG(tpw, tfft, " Pw");
#define __QUANTISE__
#include "kiss_fft.h"
+#include "comp.h"
#define WO_BITS 7
#define WO_LEVELS (1<<WO_BITS)
int lsp,float ak[]);
void aks_to_M2(kiss_fft_cfg fft_fwd_cfg, float ak[], int order, MODEL *model,
float E, float *snr, int dump, int sim_pf,
- int pf, int bass_boost, float beta, float gamma);
+ int pf, int bass_boost, float beta, float gamma, COMP Aw[]);
int encode_Wo(float Wo);
float decode_Wo(int index);
/* freq offset estimation and correction */
- foff_coarse = rx_est_freq_offset(fdmdv, rx_fdm, nin);
-
//fdmdv->sync = 0; // when debugging good idea to uncomment this to "open loop"
+ foff_coarse = rx_est_freq_offset(fdmdv, rx_fdm, nin, !fdmdv->sync);
+
if (fdmdv->sync == 0)
fdmdv->foff = foff_coarse;
fdmdv_freq_shift(rx_fdm_fcorr, rx_fdm, -fdmdv->foff, &fdmdv->foff_phase_rect, nin);
int lsp_indexes[LPC_ORD], found_bit;
float snr, snr_sum;
int frames, i, mask, index;
+ COMP Aw[FFT_ENC];
c2 = codec2_create(CODEC2_MODE_2400);
fft_fwd_cfg = kiss_fft_alloc(FFT_ENC, 0, NULL, NULL);
check_lsp_order(lsps, LPC_ORD);
bw_expand_lsps(lsps, LPC_ORD, 50.0, 100.0);
lsp_to_lpc(lsps, ak, LPC_ORD);
- aks_to_M2(fft_fwd_cfg, ak, LPC_ORD, &model, e, &snr, 0, 0, 1, 1, LPCPF_BETA, LPCPF_GAMMA);
+ aks_to_M2(fft_fwd_cfg, ak, LPC_ORD, &model, e, &snr, 0, 0, 1, 1, LPCPF_BETA, LPCPF_GAMMA, Aw);
snr_sum += snr;
frames++;
}