From 40f7ecdaa005faa042a52d83449694d6608414a1 Mon Sep 17 00:00:00 2001 From: f4exb Date: Thu, 18 Jul 2024 02:08:05 +0200 Subject: [PATCH] WDSP: more double precision calculation --- wdsp/RXA.cpp | 6 +- wdsp/amd.cpp | 34 ++++-- wdsp/amsq.cpp | 37 ++++++- wdsp/amsq.hpp | 4 +- wdsp/anf.cpp | 52 ++++++---- wdsp/anf.hpp | 46 ++++----- wdsp/anr.cpp | 69 ++++++++----- wdsp/anr.hpp | 47 +++++---- wdsp/bandpass.cpp | 28 ++--- wdsp/bandpass.hpp | 30 ++++-- wdsp/cblock.cpp | 22 ++-- wdsp/cblock.hpp | 21 ++-- wdsp/emnr.cpp | 246 +++++++++++++++++++++++++++++++++++--------- wdsp/emnr.hpp | 8 +- wdsp/eq.cpp | 8 +- wdsp/fcurve.cpp | 8 +- wdsp/fmsq.cpp | 46 +++++++-- wdsp/fmsq.hpp | 4 +- wdsp/iir.cpp | 239 +++++++++++++++++++++++++----------------- wdsp/iir.hpp | 129 +++++++++++++---------- wdsp/patchpanel.cpp | 22 ++-- wdsp/patchpanel.hpp | 20 ++-- wdsp/snba.cpp | 46 ++++++++- wdsp/wcpAGC.cpp | 91 +++++++++------- wdsp/wcpAGC.hpp | 20 ++-- 25 files changed, 837 insertions(+), 446 deletions(-) diff --git a/wdsp/RXA.cpp b/wdsp/RXA.cpp index 54773fa64..745ef73bb 100644 --- a/wdsp/RXA.cpp +++ b/wdsp/RXA.cpp @@ -506,9 +506,9 @@ RXA* RXA::create_rxa ( // Dolly filter (multiple peak filter) - default is 2 for RTTY { int def_enable[2] = {1, 1}; - float def_freq[2] = {2125.0, 2295.0}; - float def_bw[2] = {75.0, 75.0}; - float def_gain[2] = {1.0, 1.0}; + double def_freq[2] = {2125.0, 2295.0}; + double def_bw[2] = {75.0, 75.0}; + double def_gain[2] = {1.0, 1.0}; rxa->mpeak.p = MPEAK::create_mpeak ( 0, // run rxa->dsp_size, // size diff --git a/wdsp/amd.cpp b/wdsp/amd.cpp index a5acbc4f8..354d56c06 100644 --- a/wdsp/amd.cpp +++ b/wdsp/amd.cpp @@ -134,6 +134,7 @@ void AMD::xamd (AMD *a) double ai, bi, aq, bq; double ai_ps, bi_ps, aq_ps, bq_ps; int j, k; + if (a->run) { switch (a->mode) @@ -143,16 +144,21 @@ void AMD::xamd (AMD *a) { for (i = 0; i < a->buff_size; i++) { - audio = sqrt(a->in_buff[2 * i + 0] * a->in_buff[2 * i + 0] + a->in_buff[2 * i + 1] * a->in_buff[2 * i + 1]); + double xr = a->in_buff[2 * i + 0]; + double xi = a->in_buff[2 * i + 1]; + audio = sqrt(xr*xr + xi*xi); + if (a->levelfade) { a->dc = a->mtauR * a->dc + a->onem_mtauR * audio; a->dc_insert = a->mtauI * a->dc_insert + a->onem_mtauI * audio; audio += a->dc_insert - a->dc; } + a->out_buff[2 * i + 0] = audio; a->out_buff[2 * i + 1] = audio; } + break; } @@ -185,6 +191,7 @@ void AMD::xamd (AMD *a) a->c[k + 3] = a->c0[j] * (a->c[k] - a->c[k + 5]) + a->c[k + 2]; a->d[k + 3] = a->c1[j] * (a->d[k] - a->d[k + 5]) + a->d[k + 2]; } + ai_ps = a->a[OUT_IDX]; bi_ps = a->b[OUT_IDX]; bq_ps = a->c[OUT_IDX]; @@ -227,20 +234,33 @@ void AMD::xamd (AMD *a) a->dc_insert = a->mtauI * a->dc_insert + a->onem_mtauI * corr[0]; audio += a->dc_insert - a->dc; } + a->out_buff[2 * i + 0] = audio; a->out_buff[2 * i + 1] = audio; - if ((corr[0] == 0.0) && (corr[1] == 0.0)) corr[0] = 1.0; + if ((corr[0] == 0.0) && (corr[1] == 0.0)) + corr[0] = 1.0; + det = atan2(corr[1], corr[0]); del_out = a->fil_out; a->omega += a->g2 * det; - if (a->omega < a->omega_min) a->omega = a->omega_min; - if (a->omega > a->omega_max) a->omega = a->omega_max; + + if (a->omega < a->omega_min) + a->omega = a->omega_min; + + if (a->omega > a->omega_max) + a->omega = a->omega_max; + a->fil_out = a->g1 * det + a->omega; a->phs += del_out; - while (a->phs >= 2 * M_PI) a->phs -= 2 * M_PI; - while (a->phs < 0.0) a->phs += 2 * M_PI; + + while (a->phs >= 2 * M_PI) + a->phs -= 2 * M_PI; + + while (a->phs < 0.0) + a->phs += 2 * M_PI; } + break; } } @@ -277,6 +297,7 @@ void AMD::setSize_amd (AMD *a, int size) void AMD::SetAMDRun(RXA& rxa, int run) { AMD *a = rxa.amd.p; + if (a->run != run) { RXA::bp1Check ( @@ -287,6 +308,7 @@ void AMD::SetAMDRun(RXA& rxa, int run) rxa.anf.p->run, rxa.anr.p->run ); + a->run = run; RXA::bp1Set (rxa); } diff --git a/wdsp/amsq.cpp b/wdsp/amsq.cpp index 86b89284d..476a8ed03 100644 --- a/wdsp/amsq.cpp +++ b/wdsp/amsq.cpp @@ -38,13 +38,16 @@ void AMSQ::compute_slews(AMSQ *a) double delta, theta; delta = PI / (double)a->ntup; theta = 0.0; + for (i = 0; i <= a->ntup; i++) { a->cup[i] = a->muted_gain + (1.0 - a->muted_gain) * 0.5 * (1.0 - cos (theta)); theta += delta; } + delta = PI / (double)a->ntdown; theta = 0.0; + for (i = 0; i <= a->ntdown; i++) { a->cdown[i] = a->muted_gain + (1.0 - a->muted_gain) * 0.5 * (1.0 + cos (theta)); @@ -62,8 +65,8 @@ void AMSQ::calc_amsq(AMSQ *a) // level change a->ntup = (int)(a->tup * a->rate); a->ntdown = (int)(a->tdown * a->rate); - a->cup = new float[(a->ntup + 1) * 2]; // (float *)malloc0((a->ntup + 1) * sizeof(float)); - a->cdown = new float[(a->ntdown + 1) * 2]; // (float *)malloc0((a->ntdown + 1) * sizeof(float)); + a->cup = new double[(a->ntup + 1) * 2]; // (float *)malloc0((a->ntup + 1) * sizeof(float)); + a->cdown = new double[(a->ntdown + 1) * 2]; // (float *)malloc0((a->ntdown + 1) * sizeof(float)); compute_slews(a); // control a->state = 0; @@ -140,10 +143,12 @@ void AMSQ::xamsq (AMSQ *a) { int i; double sig, siglimit; + for (i = 0; i < a->size; i++) { sig = sqrt (a->trigsig[2 * i + 0] * a->trigsig[2 * i + 0] + a->trigsig[2 * i + 1] * a->trigsig[2 * i + 1]); a->avsig = a->avm * a->avsig + a->onem_avm * sig; + switch (a->state) { case MUTED: @@ -152,47 +157,68 @@ void AMSQ::xamsq (AMSQ *a) a->state = INCREASE; a->count = a->ntup; } + a->out[2 * i + 0] = a->muted_gain * a->in[2 * i + 0]; a->out[2 * i + 1] = a->muted_gain * a->in[2 * i + 1]; + break; + case INCREASE: a->out[2 * i + 0] = a->in[2 * i + 0] * a->cup[a->ntup - a->count]; a->out[2 * i + 1] = a->in[2 * i + 1] * a->cup[a->ntup - a->count]; + if (a->count-- == 0) a->state = UNMUTED; + break; + case UNMUTED: if (a->avsig < a->tail_thresh) { a->state = TAIL; - if ((siglimit = a->avsig) > 1.0) siglimit = 1.0; + + if ((siglimit = a->avsig) > 1.0) + siglimit = 1.0; + a->count = (int)((a->min_tail + (a->max_tail - a->min_tail) * (1.0 - siglimit)) * a->rate); } + a->out[2 * i + 0] = a->in[2 * i + 0]; a->out[2 * i + 1] = a->in[2 * i + 1]; + break; + case TAIL: a->out[2 * i + 0] = a->in[2 * i + 0]; a->out[2 * i + 1] = a->in[2 * i + 1]; + if (a->avsig > a->unmute_thresh) + { a->state = UNMUTED; + } else if (a->count-- == 0) { a->state = DECREASE; a->count = a->ntdown; } + break; + case DECREASE: a->out[2 * i + 0] = a->in[2 * i + 0] * a->cdown[a->ntdown - a->count]; a->out[2 * i + 1] = a->in[2 * i + 1] * a->cdown[a->ntdown - a->count]; + if (a->count-- == 0) a->state = MUTED; + break; } } } else if (a->in != a->out) + { std::copy( a->in, a->in + a->size * 2, a->out); + } } void AMSQ::xamsqcap (AMSQ *a) @@ -243,7 +269,10 @@ void AMSQ::SetAMSQMaxTail (RXA& rxa, double tail) { AMSQ *a; a = rxa.amsq.p; - if (tail < a->min_tail) tail = a->min_tail; + + if (tail < a->min_tail) + tail = a->min_tail; + a->max_tail = tail; } diff --git a/wdsp/amsq.hpp b/wdsp/amsq.hpp index 41a3f820b..333acf355 100644 --- a/wdsp/amsq.hpp +++ b/wdsp/amsq.hpp @@ -54,8 +54,8 @@ public: double tdown; int ntup; int ntdown; - float* cup; - float* cdown; + double* cup; + double* cdown; double tail_thresh; double unmute_thresh; double min_tail; diff --git a/wdsp/anf.cpp b/wdsp/anf.cpp index 4f8e10588..6d8db0935 100644 --- a/wdsp/anf.cpp +++ b/wdsp/anf.cpp @@ -45,15 +45,15 @@ ANF* ANF::create_anf( int dline_size, int n_taps, int delay, - float two_mu, - float gamma, - float lidx, - float lidx_min, - float lidx_max, - float ngamma, - float den_mult, - float lincr, - float ldecr + double two_mu, + double gamma, + double lidx, + double lidx_min, + double lidx_max, + double ngamma, + double den_mult, + double lincr, + double ldecr ) { ANF *a = new ANF; @@ -77,8 +77,8 @@ ANF* ANF::create_anf( a->lincr = lincr; a->ldecr = ldecr; - memset (a->d, 0, sizeof(float) * ANF_DLINE_SIZE); - memset (a->w, 0, sizeof(float) * ANF_DLINE_SIZE); + memset (a->d, 0, sizeof(double) * ANF_DLINE_SIZE); + memset (a->w, 0, sizeof(double) * ANF_DLINE_SIZE); return a; } @@ -91,9 +91,10 @@ void ANF::destroy_anf (ANF *a) void ANF::xanf(ANF *a, int position) { int i, j, idx; - float c0, c1; - float y, error, sigma, inv_sigp; - float nel, nev; + double c0, c1; + double y, error, sigma, inv_sigp; + double nel, nev; + if (a->run && (a->position == position)) { for (i = 0; i < a->buff_size; i++) @@ -109,14 +110,19 @@ void ANF::xanf(ANF *a, int position) y += a->w[j] * a->d[idx]; sigma += a->d[idx] * a->d[idx]; } + inv_sigp = 1.0 / (sigma + 1e-10); error = a->d[a->in_idx] - y; a->out_buff[2 * i + 0] = error; a->out_buff[2 * i + 1] = 0.0; - if((nel = error * (1.0 - a->two_mu * sigma * inv_sigp)) < 0.0) nel = -nel; - if((nev = a->d[a->in_idx] - (1.0 - a->two_mu * a->ngamma) * y - a->two_mu * error * sigma * inv_sigp) < 0.0) nev = -nev; + if ((nel = error * (1.0 - a->two_mu * sigma * inv_sigp)) < 0.0) + nel = -nel; + + if ((nev = a->d[a->in_idx] - (1.0 - a->two_mu * a->ngamma) * y - a->two_mu * error * sigma * inv_sigp) < 0.0) + nev = -nev; + if (nev < nel) { if ((a->lidx += a->lincr) > a->lidx_max) a->lidx = a->lidx_max; @@ -125,6 +131,7 @@ void ANF::xanf(ANF *a, int position) { if ((a->lidx -= a->ldecr) < a->lidx_min) a->lidx = a->lidx_min; } + a->ngamma = a->gamma * (a->lidx * a->lidx) * (a->lidx * a->lidx) * a->den_mult; c0 = 1.0 - a->two_mu * a->ngamma; @@ -135,17 +142,20 @@ void ANF::xanf(ANF *a, int position) idx = (a->in_idx + j + a->delay) & a->mask; a->w[j] = c0 * a->w[j] + c1 * a->d[idx]; } + a->in_idx = (a->in_idx + a->mask) & a->mask; } } else if (a->in_buff != a->out_buff) + { std::copy(a->in_buff, a->in_buff + a->buff_size * 2, a->out_buff); + } } void ANF::flush_anf (ANF *a) { - memset (a->d, 0, sizeof(float) * ANF_DLINE_SIZE); - memset (a->w, 0, sizeof(float) * ANF_DLINE_SIZE); + memset (a->d, 0, sizeof(double) * ANF_DLINE_SIZE); + memset (a->w, 0, sizeof(double) * ANF_DLINE_SIZE); a->in_idx = 0; } @@ -193,7 +203,7 @@ void ANF::SetANFRun (RXA& rxa, int run) } -void ANF::SetANFVals (RXA& rxa, int taps, int delay, float gain, float leakage) +void ANF::SetANFVals (RXA& rxa, int taps, int delay, double gain, double leakage) { rxa.anf.p->n_taps = taps; rxa.anf.p->delay = delay; @@ -214,13 +224,13 @@ void ANF::SetANFDelay (RXA& rxa, int delay) flush_anf (rxa.anf.p); } -void ANF::SetANFGain (RXA& rxa, float gain) +void ANF::SetANFGain (RXA& rxa, double gain) { rxa.anf.p->two_mu = gain; flush_anf (rxa.anf.p); } -void ANF::SetANFLeakage (RXA& rxa, float leakage) +void ANF::SetANFLeakage (RXA& rxa, double leakage) { rxa.anf.p->gamma = leakage; flush_anf (rxa.anf.p); diff --git a/wdsp/anf.hpp b/wdsp/anf.hpp index cd38cb8ca..6b9ef6006 100644 --- a/wdsp/anf.hpp +++ b/wdsp/anf.hpp @@ -48,18 +48,18 @@ public: int mask; int n_taps; int delay; - float two_mu; - float gamma; - float d [ANF_DLINE_SIZE]; - float w [ANF_DLINE_SIZE]; + double two_mu; + double gamma; + double d [ANF_DLINE_SIZE]; + double w [ANF_DLINE_SIZE]; int in_idx; - float lidx; - float lidx_min; - float lidx_max; - float ngamma; - float den_mult; - float lincr; - float ldecr; + double lidx; + double lidx_min; + double lidx_max; + double ngamma; + double den_mult; + double lincr; + double ldecr; static ANF* create_anf( int run, @@ -70,15 +70,15 @@ public: int dline_size, int n_taps, int delay, - float two_mu, - float gamma, - float lidx, - float lidx_min, - float lidx_max, - float ngamma, - float den_mult, - float lincr, - float ldecr + double two_mu, + double gamma, + double lidx, + double lidx_min, + double lidx_max, + double ngamma, + double den_mult, + double lincr, + double ldecr ); static void destroy_anf (ANF *a); static void flush_anf (ANF *a); @@ -88,11 +88,11 @@ public: static void setSize_anf (ANF *a, int size); // RXA Properties static void SetANFRun (RXA& rxa, int setit); - static void SetANFVals (RXA& rxa, int taps, int delay, float gain, float leakage); + static void SetANFVals (RXA& rxa, int taps, int delay, double gain, double leakage); static void SetANFTaps (RXA& rxa, int taps); static void SetANFDelay (RXA& rxa, int delay); - static void SetANFGain (RXA& rxa, float gain); - static void SetANFLeakage (RXA& rxa, float leakage); + static void SetANFGain (RXA& rxa, double gain); + static void SetANFLeakage (RXA& rxa, double leakage); static void SetANFPosition (RXA& rxa, int position); }; diff --git a/wdsp/anr.cpp b/wdsp/anr.cpp index 7aaabff67..b4c9f1831 100644 --- a/wdsp/anr.cpp +++ b/wdsp/anr.cpp @@ -45,16 +45,15 @@ ANR* ANR::create_anr ( int dline_size, int n_taps, int delay, - float two_mu, - float gamma, - - float lidx, - float lidx_min, - float lidx_max, - float ngamma, - float den_mult, - float lincr, - float ldecr + double two_mu, + double gamma, + double lidx, + double lidx_min, + double lidx_max, + double ngamma, + double den_mult, + double lincr, + double ldecr ) { ANR *a = new ANR; @@ -78,8 +77,8 @@ ANR* ANR::create_anr ( a->lincr = lincr; a->ldecr = ldecr; - memset (a->d, 0, sizeof(float) * ANR_DLINE_SIZE); - memset (a->w, 0, sizeof(float) * ANR_DLINE_SIZE); + memset (a->d, 0, sizeof(double) * ANR_DLINE_SIZE); + memset (a->w, 0, sizeof(double) * ANR_DLINE_SIZE); return a; } @@ -92,9 +91,10 @@ void ANR::destroy_anr (ANR *a) void ANR::xanr (ANR *a, int position) { int i, j, idx; - float c0, c1; - float y, error, sigma, inv_sigp; - float nel, nev; + double c0, c1; + double y, error, sigma, inv_sigp; + double nel, nev; + if (a->run && (a->position == position)) { for (i = 0; i < a->buff_size; i++) @@ -110,24 +110,30 @@ void ANR::xanr (ANR *a, int position) y += a->w[j] * a->d[idx]; sigma += a->d[idx] * a->d[idx]; } + inv_sigp = 1.0 / (sigma + 1e-10); error = a->d[a->in_idx] - y; a->out_buff[2 * i + 0] = y; a->out_buff[2 * i + 1] = 0.0; - if((nel = error * (1.0 - a->two_mu * sigma * inv_sigp)) < 0.0) nel = -nel; - if((nev = a->d[a->in_idx] - (1.0 - a->two_mu * a->ngamma) * y - a->two_mu * error * sigma * inv_sigp) < 0.0) nev = -nev; + if ((nel = error * (1.0 - a->two_mu * sigma * inv_sigp)) < 0.0) + nel = -nel; + if ((nev = a->d[a->in_idx] - (1.0 - a->two_mu * a->ngamma) * y - a->two_mu * error * sigma * inv_sigp) < 0.0) + nev = -nev; + if (nev < nel) { - if ((a->lidx += a->lincr) > a->lidx_max) a->lidx = a->lidx_max; + if ((a->lidx += a->lincr) > a->lidx_max) + a->lidx = a->lidx_max; } else { - if ((a->lidx -= a->ldecr) < a->lidx_min) a->lidx = a->lidx_min; + if ((a->lidx -= a->ldecr) < a->lidx_min) + a->lidx = a->lidx_min; } - a->ngamma = a->gamma * (a->lidx * a->lidx) * (a->lidx * a->lidx) * a->den_mult; + a->ngamma = a->gamma * (a->lidx * a->lidx) * (a->lidx * a->lidx) * a->den_mult; c0 = 1.0 - a->two_mu * a->ngamma; c1 = a->two_mu * error * inv_sigp; @@ -136,17 +142,20 @@ void ANR::xanr (ANR *a, int position) idx = (a->in_idx + j + a->delay) & a->mask; a->w[j] = c0 * a->w[j] + c1 * a->d[idx]; } + a->in_idx = (a->in_idx + a->mask) & a->mask; } } else if (a->in_buff != a->out_buff) + { std::copy(a->in_buff, a->in_buff + a->buff_size * 2, a->out_buff); + } } void ANR::flush_anr (ANR *a) { - memset (a->d, 0, sizeof(float) * ANR_DLINE_SIZE); - memset (a->w, 0, sizeof(float) * ANR_DLINE_SIZE); + memset (a->d, 0, sizeof(double) * ANR_DLINE_SIZE); + memset (a->w, 0, sizeof(double) * ANR_DLINE_SIZE); a->in_idx = 0; } @@ -179,15 +188,21 @@ void ANR::SetANRRun (RXA& rxa, int run) if (a->run != run) { - RXA::bp1Check (rxa, rxa.amd.p->run, rxa.snba.p->run, - rxa.emnr.p->run, rxa.anf.p->run, run); + RXA::bp1Check ( + rxa, + rxa.amd.p->run, + rxa.snba.p->run, + rxa.emnr.p->run, + rxa.anf.p->run, + run + ); a->run = run; RXA::bp1Set (rxa); flush_anr (a); } } -void ANR::SetANRVals (RXA& rxa, int taps, int delay, float gain, float leakage) +void ANR::SetANRVals (RXA& rxa, int taps, int delay, double gain, double leakage) { rxa.anr.p->n_taps = taps; rxa.anr.p->delay = delay; @@ -208,13 +223,13 @@ void ANR::SetANRDelay (RXA& rxa, int delay) flush_anr (rxa.anr.p); } -void ANR::SetANRGain (RXA& rxa, float gain) +void ANR::SetANRGain (RXA& rxa, double gain) { rxa.anr.p->two_mu = gain; flush_anr (rxa.anr.p); } -void ANR::SetANRLeakage (RXA& rxa, float leakage) +void ANR::SetANRLeakage (RXA& rxa, double leakage) { rxa.anr.p->gamma = leakage; flush_anr (rxa.anr.p); diff --git a/wdsp/anr.hpp b/wdsp/anr.hpp index 5179af878..c951c0c14 100644 --- a/wdsp/anr.hpp +++ b/wdsp/anr.hpp @@ -48,19 +48,19 @@ public: int mask; int n_taps; int delay; - float two_mu; - float gamma; - float d [ANR_DLINE_SIZE]; - float w [ANR_DLINE_SIZE]; + double two_mu; + double gamma; + double d [ANR_DLINE_SIZE]; + double w [ANR_DLINE_SIZE]; int in_idx; - float lidx; - float lidx_min; - float lidx_max; - float ngamma; - float den_mult; - float lincr; - float ldecr; + double lidx; + double lidx_min; + double lidx_max; + double ngamma; + double den_mult; + double lincr; + double ldecr; static ANR* create_anr ( int run, @@ -71,16 +71,15 @@ public: int dline_size, int n_taps, int delay, - float two_mu, - float gamma, - - float lidx, - float lidx_min, - float lidx_max, - float ngamma, - float den_mult, - float lincr, - float ldecr + double two_mu, + double gamma, + double lidx, + double lidx_min, + double lidx_max, + double ngamma, + double den_mult, + double lincr, + double ldecr ); static void destroy_anr (ANR *a); @@ -91,11 +90,11 @@ public: static void setSize_anr (ANR *a, int size); // RXA Properties static void SetANRRun (RXA& rxa, int setit); - static void SetANRVals (RXA& rxa, int taps, int delay, float gain, float leakage); + static void SetANRVals (RXA& rxa, int taps, int delay, double gain, double leakage); static void SetANRTaps (RXA& rxa, int taps); static void SetANRDelay (RXA& rxa, int delay); - static void SetANRGain (RXA& rxa, float gain); - static void SetANRLeakage (RXA& rxa, float leakage); + static void SetANRGain (RXA& rxa, double gain); + static void SetANRLeakage (RXA& rxa, double leakage); static void SetANRPosition (RXA& rxa, int position); }; diff --git a/wdsp/bandpass.cpp b/wdsp/bandpass.cpp index 2d5ff8f59..a9e53e050 100644 --- a/wdsp/bandpass.cpp +++ b/wdsp/bandpass.cpp @@ -48,11 +48,11 @@ BANDPASS* BANDPASS::create_bandpass ( int mp, float* in, float* out, - float f_low, - float f_high, + double f_low, + double f_high, int samplerate, int wintype, - float gain + double gain ) { // NOTE: 'nc' must be >= 'size' @@ -76,7 +76,7 @@ BANDPASS* BANDPASS::create_bandpass ( a->samplerate, a->wintype, 1, - a->gain / (float)(2 * a->size) + a->gain / (double)(2 * a->size) ); a->p = FIRCORE::create_fircore (a->size, a->in, a->out, a->nc, a->mp, impulse); delete[] impulse; @@ -144,7 +144,7 @@ void BANDPASS::setSize_bandpass (BANDPASS *a, int size) delete[] (impulse); } -void BANDPASS::setGain_bandpass (BANDPASS *a, float gain, int update) +void BANDPASS::setGain_bandpass (BANDPASS *a, double gain, int update) { a->gain = gain; float* impulse = FIR::fir_bandpass ( @@ -154,13 +154,13 @@ void BANDPASS::setGain_bandpass (BANDPASS *a, float gain, int update) a->samplerate, a->wintype, 1, - a->gain / (float)(2 * a->size) + a->gain / (double)(2 * a->size) ); FIRCORE::setImpulse_fircore (a->p, impulse, update); delete[] (impulse); } -void BANDPASS::CalcBandpassFilter (BANDPASS *a, float f_low, float f_high, float gain) +void BANDPASS::CalcBandpassFilter (BANDPASS *a, double f_low, double f_high, double gain) { if ((a->f_low != f_low) || (a->f_high != f_high) || (a->gain != gain)) { @@ -174,7 +174,7 @@ void BANDPASS::CalcBandpassFilter (BANDPASS *a, float f_low, float f_high, float a->samplerate, a->wintype, 1, - a->gain / (float)(2 * a->size) + a->gain / (double)(2 * a->size) ); FIRCORE::setImpulse_fircore (a->p, impulse, 1); delete[] (impulse); @@ -187,7 +187,7 @@ void BANDPASS::CalcBandpassFilter (BANDPASS *a, float f_low, float f_high, float * * ********************************************************************************************************/ -void BANDPASS::SetBandpassFreqs (RXA& rxa, float f_low, float f_high) +void BANDPASS::SetBandpassFreqs (RXA& rxa, double f_low, double f_high) { BANDPASS *a = rxa.bp1.p; @@ -200,7 +200,7 @@ void BANDPASS::SetBandpassFreqs (RXA& rxa, float f_low, float f_high) a->samplerate, a->wintype, 1, - a->gain / (float)(2 * a->size) + a->gain / (double)(2 * a->size) ); FIRCORE::setImpulse_fircore (a->p, impulse, 0); @@ -227,7 +227,7 @@ void BANDPASS::SetBandpassNC (RXA& rxa, int nc) a->samplerate, a->wintype, 1, - a->gain / (float)(2 * a->size) + a->gain / (double)(2 * a->size) ); FIRCORE::setNc_fircore (a->p, a->nc, impulse); delete[] (impulse); @@ -302,7 +302,7 @@ void BANDPASS::SetBandpassNC (TXA& txa, int nc) a->samplerate, a->wintype, 1, - a->gain / (float)(2 * a->size) + a->gain / (double)(2 * a->size) ); FIRCORE::setNc_fircore (a->p, a->nc, impulse); delete[] (impulse); @@ -320,7 +320,7 @@ void BANDPASS::SetBandpassNC (TXA& txa, int nc) a->samplerate, a->wintype, 1, - a->gain / (float)(2 * a->size) + a->gain / (double)(2 * a->size) ); FIRCORE::setNc_fircore (a->p, a->nc, impulse); delete[] (impulse); @@ -338,7 +338,7 @@ void BANDPASS::SetBandpassNC (TXA& txa, int nc) a->samplerate, a->wintype, 1, - a->gain / (float)(2 * a->size) + a->gain / (double)(2 * a->size) ); FIRCORE::setNc_fircore (a->p, a->nc, impulse); delete[] (impulse); diff --git a/wdsp/bandpass.hpp b/wdsp/bandpass.hpp index 2a22b7c87..c72ac3a8f 100644 --- a/wdsp/bandpass.hpp +++ b/wdsp/bandpass.hpp @@ -59,25 +59,37 @@ public: int mp; float* in; float* out; - float f_low; - float f_high; - float samplerate; + double f_low; + double f_high; + double samplerate; int wintype; - float gain; + double gain; FIRCORE *p; - static BANDPASS *create_bandpass (int run, int position, int size, int nc, int mp, float* in, float* out, - float f_low, float f_high, int samplerate, int wintype, float gain); + static BANDPASS *create_bandpass ( + int run, + int position, + int size, + int nc, + int mp, + float* in, + float* out, + double f_low, + double f_high, + int samplerate, + int wintype, + double gain + ); static void destroy_bandpass (BANDPASS *a); static void flush_bandpass (BANDPASS *a); static void xbandpass (BANDPASS *a, int pos); static void setBuffers_bandpass (BANDPASS *a, float* in, float* out); static void setSamplerate_bandpass (BANDPASS *a, int rate); static void setSize_bandpass (BANDPASS *a, int size); - static void setGain_bandpass (BANDPASS *a, float gain, int update); - static void CalcBandpassFilter (BANDPASS *a, float f_low, float f_high, float gain); + static void setGain_bandpass (BANDPASS *a, double gain, int update); + static void CalcBandpassFilter (BANDPASS *a, double f_low, double f_high, double gain); // RXA Prototypes - static void SetBandpassFreqs (RXA& rxa, float f_low, float f_high); + static void SetBandpassFreqs (RXA& rxa, double f_low, double f_high); static void SetBandpassNC (RXA& rxa, int nc); static void SetBandpassMP (RXA& rxa, int mp); // TXA Prototypes diff --git a/wdsp/cblock.cpp b/wdsp/cblock.cpp index ae762d4b2..20214a59f 100644 --- a/wdsp/cblock.cpp +++ b/wdsp/cblock.cpp @@ -40,16 +40,15 @@ void CBL::calc_cbl (CBL *a) a->mtau = exp(-1.0 / (a->sample_rate * a->tau)); } -CBL* CBL::create_cbl - ( +CBL* CBL::create_cbl( int run, int buff_size, float *in_buff, float *out_buff, int mode, int sample_rate, - float tau - ) + double tau +) { CBL *a = new CBL; a->run = run; @@ -57,7 +56,7 @@ CBL* CBL::create_cbl a->in_buff = in_buff; a->out_buff = out_buff; a->mode = mode; - a->sample_rate = (float)sample_rate; + a->sample_rate = (double) sample_rate; a->tau = tau; calc_cbl (a); return a; @@ -81,7 +80,8 @@ void CBL::xcbl (CBL *a) if (a->run) { int i; - float tempI, tempQ; + double tempI, tempQ; + for (i = 0; i < a->buff_size; i++) { tempI = a->in_buff[2 * i + 0]; @@ -90,12 +90,18 @@ void CBL::xcbl (CBL *a) a->out_buff[2 * i + 1] = a->in_buff[2 * i + 1] - a->prevQin + a->mtau * a->prevQout; a->prevIin = tempI; a->prevQin = tempQ; - if (fabs(a->prevIout = a->out_buff[2 * i + 0]) < 1.0e-100) a->prevIout = 0.0; - if (fabs(a->prevQout = a->out_buff[2 * i + 1]) < 1.0e-100) a->prevQout = 0.0; + + if (fabs(a->prevIout = a->out_buff[2 * i + 0]) < 1.0e-20) + a->prevIout = 0.0; + + if (fabs(a->prevQout = a->out_buff[2 * i + 1]) < 1.0e-20) + a->prevQout = 0.0; } } else if (a->in_buff != a->out_buff) + { std::copy(a->in_buff, a->in_buff + a->buff_size * 2, a->out_buff); + } } void CBL::setBuffers_cbl (CBL *a, float* in, float* out) diff --git a/wdsp/cblock.hpp b/wdsp/cblock.hpp index b44a7226f..167a2a3b9 100644 --- a/wdsp/cblock.hpp +++ b/wdsp/cblock.hpp @@ -42,24 +42,23 @@ public: float *in_buff; //pointer to input buffer float *out_buff; //pointer to output buffer int mode; - float sample_rate; //sample rate - float prevIin; - float prevQin; - float prevIout; - float prevQout; - float tau; //carrier removal time constant - float mtau; //carrier removal multiplier + double sample_rate; //sample rate + double prevIin; + double prevQin; + double prevIout; + double prevQout; + double tau; //carrier removal time constant + double mtau; //carrier removal multiplier - static CBL* create_cbl - ( + static CBL* create_cbl( int run, int buff_size, float *in_buff, float *out_buff, int mode, int sample_rate, - float tau - ); + double tau + ); static void destroy_cbl (CBL *a); static void flush_cbl (CBL *a); static void xcbl (CBL *a); diff --git a/wdsp/emnr.cpp b/wdsp/emnr.cpp index 2767df663..a4d86dc6d 100644 --- a/wdsp/emnr.cpp +++ b/wdsp/emnr.cpp @@ -53,11 +53,16 @@ namespace WDSP { double EMNR::bessI0 (double x) { double res, p; + if (x == 0.0) + { res = 1.0; + } else { - if (x < 0.0) x = -x; + if (x < 0.0) + x = -x; + if (x <= 3.75) { p = x / 3.75; @@ -92,11 +97,16 @@ double EMNR::bessI1 (double x) { double res, p; + if (x == 0.0) + { res = 0.0; + } else { - if (x < 0.0) x = -x; + if (x < 0.0) + x = -x; + if (x <= 3.75) { p = x / 3.75; @@ -125,6 +135,7 @@ double EMNR::bessI1 (double x) + 0.39894228); } } + return res; } @@ -138,8 +149,11 @@ double EMNR::e1xb (double x) { double e1, ga, r, t, t0; int k, m; + if (x == 0.0) - e1 = 1.0e300; + { + e1 = std::numeric_limits::max();; + } else if (x <= 1.0) { e1 = 1.0; @@ -149,6 +163,7 @@ double EMNR::e1xb (double x) { r = -r * k * x / ((k + 1.0)*(k + 1.0)); e1 = e1 + r; + if ( fabs (r) <= fabs (e1) * 1.0e-15 ) break; } @@ -160,11 +175,14 @@ double EMNR::e1xb (double x) { m = 20 + (int)(80.0 / x); t0 = 0.0; + for (k = m; k >= 1; k--) t0 = (float)k / (1.0 + k / (x + t0)); + t = 1.0 / (x + t0); e1 = exp (- x) * t; } + return e1; } @@ -177,20 +195,25 @@ double EMNR::e1xb (double x) void EMNR::calc_window (EMNR *a) { int i; - float arg, sum, inv_coherent_gain; + double arg, sum, inv_coherent_gain; + switch (a->wintype) { case 0: - arg = 2.0 * PI / (float)a->fsize; + arg = 2.0 * PI / (double) a->fsize; sum = 0.0; + for (i = 0; i < a->fsize; i++) { a->window[i] = sqrt (0.54 - 0.46 * cos((float)i * arg)); sum += a->window[i]; } - inv_coherent_gain = (float)a->fsize / sum; + + inv_coherent_gain = (double) a->fsize / sum; + for (i = 0; i < a->fsize; i++) a->window[i] *= inv_coherent_gain; + break; } } @@ -198,14 +221,21 @@ void EMNR::calc_window (EMNR *a) void EMNR::interpM (double* res, double x, int nvals, double* xvals, double* yvals) { if (x <= xvals[0]) + { *res = yvals[0]; + } else if (x >= xvals[nvals - 1]) + { *res = yvals[nvals - 1]; + } else { int idx = 0; double xllow, xlhigh, frac; - while (x >= xvals[idx]) idx++; + + while (x >= xvals[idx]) + idx++; + xllow = log10 (xvals[idx - 1]); xlhigh = log10(xvals[idx]); frac = (log10 (x) - xllow) / (xlhigh - xllow); @@ -224,16 +254,22 @@ void EMNR::calc_emnr(EMNR *a) // 3.100, 3.380, 4.150, 4.350, 4.250, 3.900, 4.100, 4.700, 5.000 }; a->incr = a->fsize / a->ovrlp; a->gain = a->ogain / a->fsize / (float)a->ovrlp; + if (a->fsize > a->bsize) a->iasize = a->fsize; else a->iasize = a->bsize + a->fsize - a->incr; + a->iainidx = 0; a->iaoutidx = 0; + if (a->fsize > a->bsize) { - if (a->bsize > a->incr) a->oasize = a->bsize; - else a->oasize = a->incr; + if (a->bsize > a->incr) + a->oasize = a->bsize; + else + a->oasize = a->incr; + a->oainidx = (a->fsize - a->bsize - a->incr) % a->oasize; } else @@ -241,6 +277,7 @@ void EMNR::calc_emnr(EMNR *a) a->oasize = a->bsize; a->oainidx = a->fsize - a->incr; } + a->init_oainidx = a->oainidx; a->oaoutidx = 0; a->msize = a->fsize / 2 + 1; @@ -253,13 +290,26 @@ void EMNR::calc_emnr(EMNR *a) a->revfftin = new float[a->msize * 2]; // (float *)malloc0(a->msize * sizeof(complex)); a->revfftout = new float[a->fsize]; // (float *)malloc0(a->fsize * sizeof(float)); a->save = new float*[a->ovrlp]; // (float **)malloc0(a->ovrlp * sizeof(float *)); + for (i = 0; i < a->ovrlp; i++) a->save[i] = new float[a->fsize]; // (float *)malloc0(a->fsize * sizeof(float)); + a->outaccum = new float[a->oasize]; // (float *)malloc0(a->oasize * sizeof(float)); a->nsamps = 0; a->saveidx = 0; - a->Rfor = fftwf_plan_dft_r2c_1d(a->fsize, a->forfftin, (fftwf_complex *)a->forfftout, FFTW_ESTIMATE); - a->Rrev = fftwf_plan_dft_c2r_1d(a->fsize, (fftwf_complex *)a->revfftin, a->revfftout, FFTW_ESTIMATE); + a->Rfor = fftwf_plan_dft_r2c_1d( + a->fsize, + a->forfftin, + (fftwf_complex *)a->forfftout, + FFTW_ESTIMATE + ); + a->Rrev = fftwf_plan_dft_c2r_1d( + a->fsize, + (fftwf_complex *)a->revfftin, + a->revfftout, + FFTW_ESTIMATE + ); + calc_window(a); a->g.msize = a->msize; @@ -272,21 +322,24 @@ void EMNR::calc_emnr(EMNR *a) a->g.gf1p5 = sqrt(PI) / 2.0; { - float tau = -128.0 / 8000.0 / log(0.98); + double tau = -128.0 / 8000.0 / log(0.98); a->g.alpha = exp(-a->incr / a->rate / tau); } a->g.eps_floor = std::numeric_limits::min(); a->g.gamma_max = 1000.0; a->g.q = 0.2; + for (i = 0; i < a->g.msize; i++) { a->g.prev_mask[i] = 1.0; a->g.prev_gamma[i] = 1.0; } + a->g.gmax = 10000.0; // a->g.GG = new double[241 * 241]; // (float *)malloc0(241 * 241 * sizeof(float)); a->g.GGS = new double[241 * 241]; // (float *)malloc0(241 * 241 * sizeof(float)); + if ((a->g.fileb = fopen("calculus", "rb"))) { std::size_t lgg = fread(a->g.GG, sizeof(float), 241 * 241, a->g.fileb); @@ -313,24 +366,24 @@ void EMNR::calc_emnr(EMNR *a) a->np.lambda_d = a->g.lambda_d; { - float tau = -128.0 / 8000.0 / log(0.7); + double tau = -128.0 / 8000.0 / log(0.7); a->np.alphaCsmooth = exp(-a->np.incr / a->np.rate / tau); } { - float tau = -128.0 / 8000.0 / log(0.96); + double tau = -128.0 / 8000.0 / log(0.96); a->np.alphaMax = exp(-a->np.incr / a->np.rate / tau); } { - float tau = -128.0 / 8000.0 / log(0.7); + double tau = -128.0 / 8000.0 / log(0.7); a->np.alphaCmin = exp(-a->np.incr / a->np.rate / tau); } { - float tau = -128.0 / 8000.0 / log(0.3); + double tau = -128.0 / 8000.0 / log(0.3); a->np.alphaMin_max_value = exp(-a->np.incr / a->np.rate / tau); } a->np.snrq = -a->np.incr / (0.064 * a->np.rate); { - float tau = -128.0 / 8000.0 / log(0.8); + double tau = -128.0 / 8000.0 / log(0.8); a->np.betamax = exp(-a->np.incr / a->np.rate / tau); } a->np.invQeqMax = 0.5; @@ -338,17 +391,22 @@ void EMNR::calc_emnr(EMNR *a) a->np.Dtime = 8.0 * 12.0 * 128.0 / 8000.0; a->np.U = 8; a->np.V = (int)(0.5 + (a->np.Dtime * a->np.rate / (a->np.U * a->np.incr))); - if (a->np.V < 4) a->np.V = 4; - if ((a->np.U = (int)(0.5 + (a->np.Dtime * a->np.rate / (a->np.V * a->np.incr)))) < 1) a->np.U = 1; + + if (a->np.V < 4) + a->np.V = 4; + + if ((a->np.U = (int)(0.5 + (a->np.Dtime * a->np.rate / (a->np.V * a->np.incr)))) < 1) + a->np.U = 1; + a->np.D = a->np.U * a->np.V; interpM(&a->np.MofD, a->np.D, 18, Dvals, Mvals); interpM(&a->np.MofV, a->np.V, 18, Dvals, Mvals); a->np.invQbar_points[0] = 0.03; a->np.invQbar_points[1] = 0.05; a->np.invQbar_points[2] = 0.06; - a->np.invQbar_points[3] = 1.0e300; + a->np.invQbar_points[3] = std::numeric_limits::max();; { - float db; + double db; db = 10.0 * log10(8.0) / (12.0 * 128 / 8000); a->np.nsmax[0] = pow(10.0, db / 10.0 * a->np.V * a->np.incr / a->np.rate); db = 10.0 * log10(4.0) / (12.0 * 128 / 8000); @@ -374,6 +432,7 @@ void EMNR::calc_emnr(EMNR *a) a->np.lmin_flag = new int[a->np.msize]; // (int *)malloc0(a->np.msize * sizeof(int)); a->np.pmin_u = new double[a->np.msize]; // (float *)malloc0(a->np.msize * sizeof(float)); a->np.actminbuff = new double*[a->np.U]; // (float**)malloc0(a->np.U * sizeof(float*)); + for (i = 0; i < a->np.U; i++) a->np.actminbuff[i] = new double[a->np.msize]; // (float *)malloc0(a->np.msize * sizeof(float)); @@ -382,19 +441,25 @@ void EMNR::calc_emnr(EMNR *a) a->np.alphaC = 1.0; a->np.subwc = a->np.V; a->np.amb_idx = 0; - for (k = 0; k < a->np.msize; k++) a->np.lambda_y[k] = 0.5; + + for (k = 0; k < a->np.msize; k++) + a->np.lambda_y[k] = 0.5; + std::copy(a->np.lambda_y, a->np.lambda_y + a->np.msize, a->np.p); std::copy(a->np.lambda_y, a->np.lambda_y + a->np.msize, a->np.sigma2N); std::copy(a->np.lambda_y, a->np.lambda_y + a->np.msize, a->np.pbar); std::copy(a->np.lambda_y, a->np.lambda_y + a->np.msize, a->np.pmin_u); + for (k = 0; k < a->np.msize; k++) { a->np.p2bar[k] = a->np.lambda_y[k] * a->np.lambda_y[k]; - a->np.actmin[k] = 1.0e300; - a->np.actmin_sub[k] = 1.0e300; + a->np.actmin[k] = std::numeric_limits::max(); + a->np.actmin_sub[k] = std::numeric_limits::max();; + for (ku = 0; ku < a->np.U; ku++) - a->np.actminbuff[ku][k] = 1.0e300; + a->np.actminbuff[ku][k] = std::numeric_limits::max();; } + std::fill(a->np.lmin_flag, a->np.lmin_flag + a->np.msize, 0); } @@ -405,13 +470,14 @@ void EMNR::calc_emnr(EMNR *a) a->nps.lambda_d = a->g.lambda_d; { - float tau = -128.0 / 8000.0 / log(0.8); + double tau = -128.0 / 8000.0 / log(0.8); a->nps.alpha_pow = exp(-a->nps.incr / a->nps.rate / tau); } { - float tau = -128.0 / 8000.0 / log(0.9); + double tau = -128.0 / 8000.0 / log(0.9); a->nps.alpha_Pbar = exp(-a->nps.incr / a->nps.rate / tau); } + a->nps.epsH1 = pow(10.0, 15.0 / 10.0); a->nps.epsH1r = a->nps.epsH1 / (1.0 + a->nps.epsH1); @@ -447,6 +513,7 @@ void EMNR::decalc_emnr(EMNR *a) for (i = 0; i < a->np.U; i++) delete[] (a->np.actminbuff[i]); + delete[] (a->np.actminbuff); delete[] (a->np.pmin_u); delete[] (a->np.lmin_flag); @@ -472,9 +539,12 @@ void EMNR::decalc_emnr(EMNR *a) fftwf_destroy_plan(a->Rrev); fftwf_destroy_plan(a->Rfor); + delete[] (a->outaccum); + for (i = 0; i < a->ovrlp; i++) delete[] (a->save[i]); + delete[] (a->save); delete[] (a->revfftout); delete[] (a->revfftin); @@ -495,7 +565,7 @@ EMNR* EMNR::create_emnr ( int ovrlp, int rate, int wintype, - float gain, + double gain, int gain_method, int npe_method, int ae_run @@ -524,8 +594,10 @@ void EMNR::flush_emnr (EMNR *a) { int i; std::fill(a->inaccum, a->inaccum + a->iasize, 0); + for (i = 0; i < a->ovrlp; i++) std::fill(a->save[i], a->save[i] + a->fsize, 0); + std::fill(a->outaccum, a->outaccum + a->oasize, 0); a->nsamps = 0; a->iainidx = 0; @@ -559,30 +631,39 @@ void EMNR::LambdaD(EMNR *a) sum_prev_p = 0.0; sum_lambda_y = 0.0; sum_prev_sigma2N = 0.0; + for (k = 0; k < a->np.msize; k++) { sum_prev_p += a->np.p[k]; sum_lambda_y += a->np.lambda_y[k]; sum_prev_sigma2N += a->np.sigma2N[k]; } + for (k = 0; k < a->np.msize; k++) { f0 = a->np.p[k] / a->np.sigma2N[k] - 1.0; a->np.alphaOptHat[k] = 1.0 / (1.0 + f0 * f0); } + SNR = sum_prev_p / sum_prev_sigma2N; alphaMin = std::min (a->np.alphaMin_max_value, pow (SNR, a->np.snrq)); + for (k = 0; k < a->np.msize; k++) if (a->np.alphaOptHat[k] < alphaMin) a->np.alphaOptHat[k] = alphaMin; + f1 = sum_prev_p / sum_lambda_y - 1.0; alphaCtilda = 1.0 / (1.0 + f1 * f1); a->np.alphaC = a->np.alphaCsmooth * a->np.alphaC + (1.0 - a->np.alphaCsmooth) * std::max (alphaCtilda, a->np.alphaCmin); f2 = a->np.alphaMax * a->np.alphaC; + for (k = 0; k < a->np.msize; k++) a->np.alphaHat[k] = f2 * a->np.alphaOptHat[k]; + for (k = 0; k < a->np.msize; k++) a->np.p[k] = a->np.alphaHat[k] * a->np.p[k] + (1.0 - a->np.alphaHat[k]) * a->np.lambda_y[k]; + invQbar = 0.0; + for (k = 0; k < a->np.msize; k++) { beta = std::min (a->np.betamax, a->np.alphaHat[k] * a->np.alphaHat[k]); @@ -594,8 +675,9 @@ void EMNR::LambdaD(EMNR *a) a->np.Qeq[k] = 1.0 / invQeq; invQbar += invQeq; } - invQbar /= (float)a->np.msize; + invQbar /= (double) a->np.msize; bc = 1.0 + a->np.av * sqrt (invQbar); + for (k = 0; k < a->np.msize; k++) { QeqTilda = (a->np.Qeq[k] - 2.0 * a->np.MofD) / (1.0 - a->np.MofD); @@ -603,10 +685,13 @@ void EMNR::LambdaD(EMNR *a) a->np.bmin[k] = 1.0 + 2.0 * (a->np.D - 1.0) / QeqTilda; a->np.bmin_sub[k] = 1.0 + 2.0 * (a->np.V - 1.0) / QeqTildaSub; } + std::fill(a->np.k_mod, a->np.k_mod + a->np.msize, 0); + for (k = 0; k < a->np.msize; k++) { f3 = a->np.p[k] * a->np.bmin[k] * bc; + if (f3 < a->np.actmin[k]) { a->np.actmin[k] = f3; @@ -614,24 +699,37 @@ void EMNR::LambdaD(EMNR *a) a->np.k_mod[k] = 1; } } + if (a->np.subwc == a->np.V) { - if (invQbar < a->np.invQbar_points[0]) noise_slope_max = a->np.nsmax[0]; - else if (invQbar < a->np.invQbar_points[1]) noise_slope_max = a->np.nsmax[1]; - else if (invQbar < a->np.invQbar_points[2]) noise_slope_max = a->np.nsmax[2]; - else noise_slope_max = a->np.nsmax[3]; + if (invQbar < a->np.invQbar_points[0]) + noise_slope_max = a->np.nsmax[0]; + else if (invQbar < a->np.invQbar_points[1]) + noise_slope_max = a->np.nsmax[1]; + else if (invQbar < a->np.invQbar_points[2]) + noise_slope_max = a->np.nsmax[2]; + else + noise_slope_max = a->np.nsmax[3]; for (k = 0; k < a->np.msize; k++) { int ku; - float min; + double min; + if (a->np.k_mod[k]) a->np.lmin_flag[k] = 0; + a->np.actminbuff[a->np.amb_idx][k] = a->np.actmin[k]; - min = 1.0e300; + min = std::numeric_limits::max();; + for (ku = 0; ku < a->np.U; ku++) - if (a->np.actminbuff[ku][k] < min) min = a->np.actminbuff[ku][k]; + { + if (a->np.actminbuff[ku][k] < min) + min = a->np.actminbuff[ku][k]; + } + a->np.pmin_u[k] = min; + if ((a->np.lmin_flag[k] == 1) && (a->np.actmin_sub[k] < noise_slope_max * a->np.pmin_u[k]) && (a->np.actmin_sub[k] > a->np.pmin_u[k])) @@ -640,11 +738,15 @@ void EMNR::LambdaD(EMNR *a) for (ku = 0; ku < a->np.U; ku++) a->np.actminbuff[ku][k] = a->np.actmin_sub[k]; } + a->np.lmin_flag[k] = 0; - a->np.actmin[k] = 1.0e300; - a->np.actmin_sub[k] = 1.0e300; + a->np.actmin[k] = std::numeric_limits::max();; + a->np.actmin_sub[k] = std::numeric_limits::max();; } - if (++a->np.amb_idx == a->np.U) a->np.amb_idx = 0; + + if (++a->np.amb_idx == a->np.U) + a->np.amb_idx = 0; + a->np.subwc = 1; } else @@ -661,23 +763,29 @@ void EMNR::LambdaD(EMNR *a) } } } + ++a->np.subwc; } + std::copy(a->np.sigma2N, a->np.sigma2N + a->np.msize, a->np.lambda_d); } void EMNR::LambdaDs (EMNR *a) { int k; + for (k = 0; k < a->nps.msize; k++) { a->nps.PH1y[k] = 1.0 / (1.0 + (1.0 + a->nps.epsH1) * exp (- a->nps.epsH1r * a->nps.lambda_y[k] / a->nps.sigma2N[k])); a->nps.Pbar[k] = a->nps.alpha_Pbar * a->nps.Pbar[k] + (1.0 - a->nps.alpha_Pbar) * a->nps.PH1y[k]; + if (a->nps.Pbar[k] > 0.99) a->nps.PH1y[k] = std::min (a->nps.PH1y[k], 0.99); + a->nps.EN2y[k] = (1.0 - a->nps.PH1y[k]) * a->nps.lambda_y[k] + a->nps.PH1y[k] * a->nps.sigma2N[k]; a->nps.sigma2N[k] = a->nps.alpha_pow * a->nps.sigma2N[k] + (1.0 - a->nps.alpha_pow) * a->nps.EN2y[k]; } + std::copy(a->nps.sigma2N, a->nps.sigma2N + a->nps.msize, a->nps.lambda_d); } @@ -685,24 +793,30 @@ void EMNR::aepf(EMNR *a) { int k, m; int N, n; - float sumPre, sumPost, zeta, zetaT; + double sumPre, sumPost, zeta, zetaT; sumPre = 0.0; sumPost = 0.0; + for (k = 0; k < a->ae.msize; k++) { sumPre += a->ae.lambda_y[k]; sumPost += a->mask[k] * a->mask[k] * a->ae.lambda_y[k]; } + zeta = sumPost / sumPre; + if (zeta >= a->ae.zetaThresh) zetaT = 1.0; else zetaT = zeta; + if (zetaT == 1.0) N = 1; else N = 1 + 2 * (int)(0.5 + a->ae.psi * (1.0 - zetaT / a->ae.zetaThresh)); + n = N / 2; + for (k = n; k < (a->ae.msize - n); k++) { a->ae.nmask[k] = 0.0; @@ -710,6 +824,7 @@ void EMNR::aepf(EMNR *a) a->ae.nmask[k] += a->mask[m]; a->ae.nmask[k] /= (float)N; } + std::copy(a->ae.nmask, a->ae.nmask + (a->ae.msize - 2 * n), a->mask + n); } @@ -719,6 +834,7 @@ double EMNR::getKey(double* type, double gamma, double xi) double tg, tx, dg, dx; const double dmin = 0.001; const double dmax = 1000.0; + if (gamma <= dmin) { ngamma1 = ngamma2 = 0; @@ -735,6 +851,7 @@ double EMNR::getKey(double* type, double gamma, double xi) ngamma1 = (int)(4.0 * tg); ngamma2 = ngamma1 + 1; } + if (xi <= dmin) { nxi1 = nxi2 = 0; @@ -751,6 +868,7 @@ double EMNR::getKey(double* type, double gamma, double xi) nxi1 = (int)(4.0 * tx); nxi2 = nxi1 + 1; } + dg = (tg - 0.25 * ngamma1) / 0.25; dx = (tx - 0.25 * nxi1) / 0.25; return (1.0 - dg) * (1.0 - dx) * type[241 * nxi1 + ngamma1] @@ -762,12 +880,14 @@ double EMNR::getKey(double* type, double gamma, double xi) void EMNR::calc_gain (EMNR *a) { int k; + for (k = 0; k < a->g.msize; k++) { double y0 = a->g.y[2 * k + 0]; double y1 = a->g.y[2 * k + 1]; a->g.lambda_y[k] = y0 * y0 + y1 * y1; } + switch (a->g.npe_method) { case 0: @@ -777,11 +897,13 @@ void EMNR::calc_gain (EMNR *a) LambdaDs(a); break; } + switch (a->g.gain_method) { case 0: { double gamma, eps_hat, v; + for (k = 0; k < a->msize; k++) { gamma = std::min (a->g.lambda_y[k] / a->g.lambda_d[k], a->g.gamma_max); @@ -797,16 +919,24 @@ void EMNR::calc_gain (EMNR *a) double witchHat = (1.0 - a->g.q) / a->g.q * exp (v2) / (1.0 + eps); a->g.mask[k] *= witchHat / (1.0 + witchHat); } - if (a->g.mask[k] > a->g.gmax) a->g.mask[k] = a->g.gmax; - if (a->g.mask[k] != a->g.mask[k]) a->g.mask[k] = 0.01; + + if (a->g.mask[k] > a->g.gmax) + a->g.mask[k] = a->g.gmax; + + if (a->g.mask[k] != a->g.mask[k]) + a->g.mask[k] = 0.01; + a->g.prev_gamma[k] = gamma; a->g.prev_mask[k] = a->g.mask[k]; } + break; } + case 1: { double gamma, eps_hat, v, ehr; + for (k = 0; k < a->g.msize; k++) { gamma = std::min (a->g.lambda_y[k] / a->g.lambda_d[k], a->g.gamma_max); @@ -814,16 +944,24 @@ void EMNR::calc_gain (EMNR *a) + (1.0 - a->g.alpha) * std::max (gamma - 1.0f, a->g.eps_floor); ehr = eps_hat / (1.0 + eps_hat); v = ehr * gamma; - if((a->g.mask[k] = ehr * exp (std::min (700.0, 0.5 * e1xb(v)))) > a->g.gmax) a->g.mask[k] = a->g.gmax; - if (a->g.mask[k] != a->g.mask[k])a->g.mask[k] = 0.01; + + if ((a->g.mask[k] = ehr * exp (std::min (700.0, 0.5 * e1xb(v)))) > a->g.gmax) + a->g.mask[k] = a->g.gmax; + + if (a->g.mask[k] != a->g.mask[k]) + a->g.mask[k] = 0.01; + a->g.prev_gamma[k] = gamma; a->g.prev_mask[k] = a->g.mask[k]; } + break; } + case 2: { double gamma, eps_hat, eps_p; + for (k = 0; k < a->msize; k++) { gamma = std::min(a->g.lambda_y[k] / a->g.lambda_d[k], a->g.gamma_max); @@ -834,10 +972,13 @@ void EMNR::calc_gain (EMNR *a) a->g.prev_gamma[k] = gamma; a->g.prev_mask[k] = a->g.mask[k]; } + break; } } - if (a->g.ae_run) aepf(a); + + if (a->g.ae_run) + aepf(a); } void EMNR::xemnr (EMNR *a, int pos) @@ -845,34 +986,43 @@ void EMNR::xemnr (EMNR *a, int pos) if (a->run && pos == a->position) { int i, j, k, sbuff, sbegin; - float g1; + double g1; + for (i = 0; i < 2 * a->bsize; i += 2) { a->inaccum[a->iainidx] = a->in[i]; a->iainidx = (a->iainidx + 1) % a->iasize; } + a->nsamps += a->bsize; + while (a->nsamps >= a->fsize) { for (i = 0, j = a->iaoutidx; i < a->fsize; i++, j = (j + 1) % a->iasize) a->forfftin[i] = a->window[i] * a->inaccum[j]; + a->iaoutidx = (a->iaoutidx + a->incr) % a->iasize; a->nsamps -= a->incr; fftwf_execute (a->Rfor); calc_gain(a); + for (i = 0; i < a->msize; i++) { g1 = a->gain * a->mask[i]; a->revfftin[2 * i + 0] = g1 * a->forfftout[2 * i + 0]; a->revfftin[2 * i + 1] = g1 * a->forfftout[2 * i + 1]; } + fftwf_execute (a->Rrev); + for (i = 0; i < a->fsize; i++) a->save[a->saveidx][i] = a->window[i] * a->revfftout[i]; + for (i = a->ovrlp; i > 0; i--) { sbuff = (a->saveidx + i) % a->ovrlp; sbegin = a->incr * (a->ovrlp - i); + for (j = sbegin, k = a->oainidx; j < a->incr + sbegin; j++, k = (k + 1) % a->oasize) { if ( i == a->ovrlp) @@ -881,9 +1031,11 @@ void EMNR::xemnr (EMNR *a, int pos) a->outaccum[k] += a->save[sbuff][j]; } } + a->saveidx = (a->saveidx + 1) % a->ovrlp; a->oainidx = (a->oainidx + a->incr) % a->oasize; } + for (i = 0; i < a->bsize; i++) { a->out[2 * i + 0] = a->outaccum[a->oaoutidx]; @@ -892,7 +1044,9 @@ void EMNR::xemnr (EMNR *a, int pos) } } else if (a->out != a->in) + { std::copy(a->in, a->in + a->bsize * 2, a->out); + } } void EMNR::setBuffers_emnr (EMNR *a, float* in, float* out) diff --git a/wdsp/emnr.hpp b/wdsp/emnr.hpp index 077fa9d0c..b3024194d 100644 --- a/wdsp/emnr.hpp +++ b/wdsp/emnr.hpp @@ -58,10 +58,10 @@ public: float** save; int oasize; float* outaccum; - float rate; + double rate; int wintype; - float ogain; - float gain; + double ogain; + double gain; int nsamps; int iainidx; int iaoutidx; @@ -173,7 +173,7 @@ public: int ovrlp, int rate, int wintype, - float gain, + double gain, int gain_method, int npe_method, int ae_run diff --git a/wdsp/eq.cpp b/wdsp/eq.cpp index cd6e0ca4e..a10158e07 100644 --- a/wdsp/eq.cpp +++ b/wdsp/eq.cpp @@ -115,7 +115,7 @@ float* EQP::eq_impulse (int N, int nfreqs, float* F, float* G, float samplerate, { f = (float)k / (float)mid; lowmag *= (f * f * f * f) / flow4; - if (lowmag < 1.0e-100) lowmag = 1.0e-100; + if (lowmag < 1.0e-20) lowmag = 1.0e-20; A[k] = lowmag; } k = high; @@ -123,7 +123,7 @@ float* EQP::eq_impulse (int N, int nfreqs, float* F, float* G, float samplerate, { f = (float)k / (float)mid; highmag *= fhigh4 / (f * f * f * f); - if (highmag < 1.0e-100) highmag = 1.0e-100; + if (highmag < 1.0e-20) highmag = 1.0e-20; A[k] = highmag; } } @@ -140,7 +140,7 @@ float* EQP::eq_impulse (int N, int nfreqs, float* F, float* G, float samplerate, { f = (float)k / (float)mid; lowmag *= (f * f * f * f) / flow4; - if (lowmag < 1.0e-100) lowmag = 1.0e-100; + if (lowmag < 1.0e-20) lowmag = 1.0e-20; A[k] = lowmag; } k = high; @@ -148,7 +148,7 @@ float* EQP::eq_impulse (int N, int nfreqs, float* F, float* G, float samplerate, { f = (float)k / (float)mid; highmag *= fhigh4 / (f * f * f * f); - if (highmag < 1.0e-100) highmag = 1.0e-100; + if (highmag < 1.0e-20) highmag = 1.0e-20; A[k] = highmag; } } diff --git a/wdsp/fcurve.cpp b/wdsp/fcurve.cpp index d63faf932..a6124ec2c 100644 --- a/wdsp/fcurve.cpp +++ b/wdsp/fcurve.cpp @@ -102,7 +102,7 @@ float* FCurve::fc_impulse (int nc, float f0, float f1, float g0, float, int curv { f = (float)k / (float)mid; lowmag *= (f * f * f * f) / flow4; - if (lowmag < 1.0e-100) lowmag = 1.0e-100; + if (lowmag < 1.0e-20) lowmag = 1.0e-20; A[k] = lowmag; } k = high; @@ -110,7 +110,7 @@ float* FCurve::fc_impulse (int nc, float f0, float f1, float g0, float, int curv { f = (float)k / (float)mid; highmag *= fhigh4 / (f * f * f * f); - if (highmag < 1.0e-100) highmag = 1.0e-100; + if (highmag < 1.0e-20) highmag = 1.0e-20; A[k] = highmag; } } @@ -127,7 +127,7 @@ float* FCurve::fc_impulse (int nc, float f0, float f1, float g0, float, int curv { f = (float)k / (float)mid; lowmag *= (f * f * f * f) / flow4; - if (lowmag < 1.0e-100) lowmag = 1.0e-100; + if (lowmag < 1.0e-20) lowmag = 1.0e-20; A[k] = lowmag; } k = high; @@ -135,7 +135,7 @@ float* FCurve::fc_impulse (int nc, float f0, float f1, float g0, float, int curv { f = (float)k / (float)mid; highmag *= fhigh4 / (f * f * f * f); - if (highmag < 1.0e-100) highmag = 1.0e-100; + if (highmag < 1.0e-20) highmag = 1.0e-20; A[k] = highmag; } } diff --git a/wdsp/fmsq.cpp b/wdsp/fmsq.cpp index 4e2d3124d..1f520a121 100644 --- a/wdsp/fmsq.cpp +++ b/wdsp/fmsq.cpp @@ -35,7 +35,7 @@ namespace WDSP { void FMSQ::calc_fmsq (FMSQ *a) { - float delta, theta; + double delta, theta; float* impulse; int i; // noise filter @@ -61,17 +61,20 @@ void FMSQ::calc_fmsq (FMSQ *a) // level change a->ntup = (int)(a->tup * a->rate); a->ntdown = (int)(a->tdown * a->rate); - a->cup = new float[a->ntup + 1]; // (float *)malloc0 ((a->ntup + 1) * sizeof(float)); - a->cdown = new float[a->ntdown + 1]; //(float *)malloc0 ((a->ntdown + 1) * sizeof(float)); - delta = PI / (float)a->ntup; + a->cup = new double[a->ntup + 1]; // (float *)malloc0 ((a->ntup + 1) * sizeof(float)); + a->cdown = new double[a->ntdown + 1]; //(float *)malloc0 ((a->ntdown + 1) * sizeof(float)); + delta = PI / (double) a->ntup; theta = 0.0; + for (i = 0; i <= a->ntup; i++) { a->cup[i] = 0.5 * (1.0 - cos(theta)); theta += delta; } - delta = PI / (float)a->ntdown; + + delta = PI / (double) a->ntdown; theta = 0.0; + for (i = 0; i <= a->ntdown; i++) { a->cdown[i] = 0.5 * (1 + cos(theta)); @@ -170,6 +173,7 @@ void FMSQ::xfmsq (FMSQ *a) int i; double noise, lnlimit; FIRCORE::xfircore (a->p); + for (i = 0; i < a->size; i++) { double noise0 = a->noise[2 * i + 0]; @@ -177,8 +181,12 @@ void FMSQ::xfmsq (FMSQ *a) noise = sqrt(noise0 * noise0 + noise1 * noise1); a->avnoise = a->avm * a->avnoise + a->onem_avm * noise; a->longnoise = a->longavm * a->longnoise + a->onem_longavm * noise; - if (!a->ready) a->ramp += a->rstep; - if (a->ramp >= a->tdelay) a->ready = 1; + + if (!a->ready) + a->ramp += a->rstep; + + if (a->ramp >= a->tdelay) + a->ready = 1; switch (a->state) { @@ -188,47 +196,68 @@ void FMSQ::xfmsq (FMSQ *a) a->state = INCREASE; a->count = a->ntup; } + a->outsig[2 * i + 0] = 0.0; a->outsig[2 * i + 1] = 0.0; + break; + case INCREASE: a->outsig[2 * i + 0] = a->insig[2 * i + 0] * a->cup[a->ntup - a->count]; a->outsig[2 * i + 1] = a->insig[2 * i + 1] * a->cup[a->ntup - a->count]; + if (a->count-- == 0) a->state = UNMUTED; + break; + case UNMUTED: if (a->avnoise > a->tail_thresh) { a->state = TAIL; - if ((lnlimit = a->longnoise) > 1.0) lnlimit = 1.0; + + if ((lnlimit = a->longnoise) > 1.0) + lnlimit = 1.0; + a->count = (int)((a->min_tail + (a->max_tail - a->min_tail) * lnlimit) * a->rate); } + a->outsig[2 * i + 0] = a->insig[2 * i + 0]; a->outsig[2 * i + 1] = a->insig[2 * i + 1]; + break; + case TAIL: a->outsig[2 * i + 0] = a->insig[2 * i + 0]; a->outsig[2 * i + 1] = a->insig[2 * i + 1]; + if (a->avnoise < a->unmute_thresh) + { a->state = UNMUTED; + } else if (a->count-- == 0) { a->state = DECREASE; a->count = a->ntdown; } + break; + case DECREASE: a->outsig[2 * i + 0] = a->insig[2 * i + 0] * a->cdown[a->ntdown - a->count]; a->outsig[2 * i + 1] = a->insig[2 * i + 1] * a->cdown[a->ntdown - a->count]; + if (a->count-- == 0) a->state = MUTED; + break; } } } else if (a->insig != a->outsig) + { std::copy(a->insig, a->insig + a->size * 2, a->outsig); + } } void FMSQ::setBuffers_fmsq (FMSQ *a, float* in, float* out, float* trig) @@ -289,6 +318,7 @@ void FMSQ::SetFMSQMP (RXA& rxa, int mp) { FMSQ *a; a = rxa.fmsq.p; + if (a->mp != mp) { a->mp = mp; diff --git a/wdsp/fmsq.hpp b/wdsp/fmsq.hpp index 5f083b9ba..d5baafc07 100644 --- a/wdsp/fmsq.hpp +++ b/wdsp/fmsq.hpp @@ -63,8 +63,8 @@ public: double tdown; int ntup; int ntdown; - float* cup; - float* cdown; + double* cup; + double* cdown; double tail_thresh; double unmute_thresh; double min_tail; diff --git a/wdsp/iir.cpp b/wdsp/iir.cpp index 01cfea88a..fcb9c0e44 100644 --- a/wdsp/iir.cpp +++ b/wdsp/iir.cpp @@ -40,7 +40,7 @@ namespace WDSP { void SNOTCH::calc_snotch (SNOTCH *a) { - float fn, qk, qr, csn; + double fn, qk, qr, csn; fn = a->f / (float)a->rate; csn = cos (TWOPI * fn); qr = 1.0 - 3.0 * a->bw; @@ -53,7 +53,7 @@ void SNOTCH::calc_snotch (SNOTCH *a) flush_snotch (a); } -SNOTCH* SNOTCH::create_snotch (int run, int size, float* in, float* out, int rate, float f, float bw) +SNOTCH* SNOTCH::create_snotch (int run, int size, float* in, float* out, int rate, double f, double bw) { SNOTCH *a = new SNOTCH; a->run = run; @@ -93,7 +93,9 @@ void SNOTCH::xsnotch (SNOTCH *a) } } else if (a->out != a->in) + { std::copy( a->in, a->in + a->size * 2, a->out); + } } void SNOTCH::setBuffers_snotch (SNOTCH *a, float* in, float* out) @@ -120,7 +122,7 @@ void SNOTCH::setSize_snotch (SNOTCH *a, int size) * * ********************************************************************************************************/ -void SNOTCH::SetSNCTCSSFreq (SNOTCH *a, float freq) +void SNOTCH::SetSNCTCSSFreq (SNOTCH *a, double freq) { a->f = freq; calc_snotch (a); @@ -140,8 +142,8 @@ void SNOTCH::SetSNCTCSSRun (SNOTCH *a, int run) void SPEAK::calc_speak (SPEAK *a) { - float ratio; - float f_corr, g_corr, bw_corr, bw_parm, A, f_min; + double ratio; + double f_corr, g_corr, bw_corr, bw_parm, A, f_min; switch (a->design) { @@ -161,11 +163,11 @@ void SPEAK::calc_speak (SPEAK *a) break; } { - float fn, qk, qr, csn; + double fn, qk, qr, csn; a->fgain = a->gain / g_corr; - fn = a->f / (float)a->rate / f_corr; + fn = a->f / (double)a->rate / f_corr; csn = cos (TWOPI * fn); - qr = 1.0 - 3.0 * a->bw / (float)a->rate * bw_parm; + qr = 1.0 - 3.0 * a->bw / (double)a->rate * bw_parm; qk = (1.0 - 2.0 * qr * csn + qr * qr) / (2.0 * (1.0 - csn)); a->a0 = 1.0 - qk; a->a1 = 2.0 * (qk - qr) * csn; @@ -195,9 +197,9 @@ void SPEAK::calc_speak (SPEAK *a) break; } { - float w0, sn, c, den; + double w0, sn, c, den; if (a->f < f_min) a->f = f_min; - w0 = TWOPI * a->f / (float)a->rate; + w0 = TWOPI * a->f / (double)a->rate; sn = sin (w0); a->cbw = bw_corr * a->f; c = sn * sinh(0.5 * log((a->f + 0.5 * a->cbw * bw_parm) / (a->f - 0.5 * a->cbw * bw_parm)) * w0 / sn); @@ -207,14 +209,25 @@ void SPEAK::calc_speak (SPEAK *a) a->a2 = (1 - c * A) / den; a->b1 = - a->a1; a->b2 = - (1 - c / A ) / den; - a->fgain = a->gain / pow (A * A, (float)a->nstages); + a->fgain = a->gain / pow (A * A, (double)a->nstages); } break; } flush_speak (a); } -SPEAK* SPEAK::create_speak (int run, int size, float* in, float* out, int rate, float f, float bw, float gain, int nstages, int design) +SPEAK* SPEAK::create_speak ( + int run, + int size, + float* in, + float* out, + int rate, + double f, + double bw, + double gain, + int nstages, + int design +) { SPEAK *a = new SPEAK; a->run = run; @@ -227,12 +240,12 @@ SPEAK* SPEAK::create_speak (int run, int size, float* in, float* out, int rate, a->gain = gain; a->nstages = nstages; a->design = design; - a->x0 = new float[a->nstages * 2]; // (float *) malloc0 (a->nstages * sizeof (complex)); - a->x1 = new float[a->nstages * 2]; // (float *) malloc0 (a->nstages * sizeof (complex)); - a->x2 = new float[a->nstages * 2]; //(float *) malloc0 (a->nstages * sizeof (complex)); - a->y0 = new float[a->nstages * 2]; // (float *) malloc0 (a->nstages * sizeof (complex)); - a->y1 = new float[a->nstages * 2]; // (float *) malloc0 (a->nstages * sizeof (complex)); - a->y2 = new float[a->nstages * 2]; // (float *) malloc0 (a->nstages * sizeof (complex)); + a->x0 = new double[a->nstages * 2]; // (float *) malloc0 (a->nstages * sizeof (complex)); + a->x1 = new double[a->nstages * 2]; // (float *) malloc0 (a->nstages * sizeof (complex)); + a->x2 = new double[a->nstages * 2]; //(float *) malloc0 (a->nstages * sizeof (complex)); + a->y0 = new double[a->nstages * 2]; // (float *) malloc0 (a->nstages * sizeof (complex)); + a->y1 = new double[a->nstages * 2]; // (float *) malloc0 (a->nstages * sizeof (complex)); + a->y2 = new double[a->nstages * 2]; // (float *) malloc0 (a->nstages * sizeof (complex)); calc_speak (a); return a; } @@ -272,12 +285,13 @@ void SPEAK::xspeak (SPEAK *a) for (n = 0; n < a->nstages; n++) { - if (n > 0) a->x0[2 * n + j] = a->y0[2 * (n - 1) + j]; - a->y0[2 * n + j] = a->a0 * a->x0[2 * n + j] - + a->a1 * a->x1[2 * n + j] - + a->a2 * a->x2[2 * n + j] - + a->b1 * a->y1[2 * n + j] - + a->b2 * a->y2[2 * n + j]; + if (n > 0) + a->x0[2 * n + j] = a->y0[2 * (n - 1) + j]; + a->y0[2 * n + j] = a->a0 * a->x0[2 * n + j] + + a->a1 * a->x1[2 * n + j] + + a->a2 * a->x2[2 * n + j] + + a->b1 * a->y1[2 * n + j] + + a->b2 * a->y2[2 * n + j]; a->y2[2 * n + j] = a->y1[2 * n + j]; a->y1[2 * n + j] = a->y0[2 * n + j]; a->x2[2 * n + j] = a->x1[2 * n + j]; @@ -289,7 +303,9 @@ void SPEAK::xspeak (SPEAK *a) } } else if (a->out != a->in) + { std::copy( a->in, a->in + a->size * 2, a->out); + } } void SPEAK::setBuffers_speak (SPEAK *a, float* in, float* out) @@ -322,21 +338,21 @@ void SPEAK::SetSPCWRun (RXA& rxa, int run) a->run = run; } -void SPEAK::SetSPCWFreq (RXA& rxa, float freq) +void SPEAK::SetSPCWFreq (RXA& rxa, double freq) { SPEAK *a = rxa.speak.p; a->f = freq; calc_speak (a); } -void SPEAK::SetSPCWBandwidth (RXA& rxa, float bw) +void SPEAK::SetSPCWBandwidth (RXA& rxa, double bw) { SPEAK *a = rxa.speak.p; a->bw = bw; calc_speak (a); } -void SPEAK::SetSPCWGain (RXA& rxa, float gain) +void SPEAK::SetSPCWGain (RXA& rxa, double gain) { SPEAK *a = rxa.speak.p; a->gain = gain; @@ -380,7 +396,19 @@ void MPEAK::decalc_mpeak (MPEAK *a) delete[] (a->tmp); } -MPEAK* MPEAK::create_mpeak (int run, int size, float* in, float* out, int rate, int npeaks, int* enable, float* f, float* bw, float* gain, int nstages) +MPEAK* MPEAK::create_mpeak ( + int run, + int size, + float* in, + float* out, + int rate, + int npeaks, + int* enable, + double* f, + double* bw, + double* gain, + int nstages +) { MPEAK *a = new MPEAK; a->run = run; @@ -391,13 +419,13 @@ MPEAK* MPEAK::create_mpeak (int run, int size, float* in, float* out, int rate, a->npeaks = npeaks; a->nstages = nstages; a->enable = new int[a->npeaks]; // (int *) malloc0 (a->npeaks * sizeof (int)); - a->f = new float[a->npeaks]; // (float *) malloc0 (a->npeaks * sizeof (float)); - a->bw = new float[a->npeaks]; // (float *) malloc0 (a->npeaks * sizeof (float)); - a->gain = new float[a->npeaks]; // (float *) malloc0 (a->npeaks * sizeof (float)); + a->f = new double[a->npeaks]; // (float *) malloc0 (a->npeaks * sizeof (float)); + a->bw = new double[a->npeaks]; // (float *) malloc0 (a->npeaks * sizeof (float)); + a->gain = new double[a->npeaks]; // (float *) malloc0 (a->npeaks * sizeof (float)); memcpy (a->enable, enable, a->npeaks * sizeof (int)); - memcpy (a->f, f, a->npeaks * sizeof (float)); - memcpy (a->bw, bw, a->npeaks * sizeof (float)); - memcpy (a->gain, gain, a->npeaks * sizeof (float)); + memcpy (a->f, f, a->npeaks * sizeof (double)); + memcpy (a->bw, bw, a->npeaks * sizeof (double)); + memcpy (a->gain, gain, a->npeaks * sizeof (double)); a->pfil = new SPEAK*[a->npeaks]; // (SPEAK *) malloc0 (a->npeaks * sizeof (SPEAK)); calc_mpeak (a); return a; @@ -440,9 +468,10 @@ void MPEAK::xmpeak (MPEAK *a) std::copy(a->mix, a->mix + a->size * 2, a->out); } - else if (a->in != a->out) + { std::copy( a->in, a->in + a->size * 2, a->out); + } } void MPEAK::setBuffers_mpeak (MPEAK *a, float* in, float* out) @@ -491,7 +520,7 @@ void MPEAK::SetmpeakFilEnable (RXA& rxa, int fil, int enable) a->enable[fil] = enable; } -void MPEAK::SetmpeakFilFreq (RXA& rxa, int fil, float freq) +void MPEAK::SetmpeakFilFreq (RXA& rxa, int fil, double freq) { MPEAK *a = rxa.mpeak.p; a->f[fil] = freq; @@ -499,7 +528,7 @@ void MPEAK::SetmpeakFilFreq (RXA& rxa, int fil, float freq) SPEAK::calc_speak(a->pfil[fil]); } -void MPEAK::SetmpeakFilBw (RXA& rxa, int fil, float bw) +void MPEAK::SetmpeakFilBw (RXA& rxa, int fil, double bw) { MPEAK *a = rxa.mpeak.p; a->bw[fil] = bw; @@ -507,7 +536,7 @@ void MPEAK::SetmpeakFilBw (RXA& rxa, int fil, float bw) SPEAK::calc_speak(a->pfil[fil]); } -void MPEAK::SetmpeakFilGain (RXA& rxa, int fil, float gain) +void MPEAK::SetmpeakFilGain (RXA& rxa, int fil, double gain) { MPEAK *a = rxa.mpeak.p; a->gain[fil] = gain; @@ -524,11 +553,11 @@ void MPEAK::SetmpeakFilGain (RXA& rxa, int fil, float gain) void PHROT::calc_phrot (PHROT *a) { - float g; - a->x0 = new float[a->nstages]; // (float *) malloc0 (a->nstages * sizeof (float)); - a->x1 = new float[a->nstages]; // (float *) malloc0 (a->nstages * sizeof (float)); - a->y0 = new float[a->nstages]; // (float *) malloc0 (a->nstages * sizeof (float)); - a->y1 = new float[a->nstages]; // (float *) malloc0 (a->nstages * sizeof (float)); + double g; + a->x0 = new double[a->nstages]; // (float *) malloc0 (a->nstages * sizeof (float)); + a->x1 = new double[a->nstages]; // (float *) malloc0 (a->nstages * sizeof (float)); + a->y0 = new double[a->nstages]; // (float *) malloc0 (a->nstages * sizeof (float)); + a->y1 = new double[a->nstages]; // (float *) malloc0 (a->nstages * sizeof (float)); g = tan (PI * a->fc / (float)a->rate); a->b0 = (g - 1.0) / (g + 1.0); a->b1 = 1.0; @@ -543,7 +572,7 @@ void PHROT::decalc_phrot (PHROT *a) delete[] (a->x0); } -PHROT* PHROT::create_phrot (int run, int size, float* in, float* out, int rate, float fc, int nstages) +PHROT* PHROT::create_phrot (int run, int size, float* in, float* out, int rate, double fc, int nstages) { PHROT *a = new PHROT; a->reverse = 0; @@ -566,10 +595,10 @@ void PHROT::destroy_phrot (PHROT *a) void PHROT::flush_phrot (PHROT *a) { - memset (a->x0, 0, a->nstages * sizeof (float)); - memset (a->x1, 0, a->nstages * sizeof (float)); - memset (a->y0, 0, a->nstages * sizeof (float)); - memset (a->y1, 0, a->nstages * sizeof (float)); + memset (a->x0, 0, a->nstages * sizeof (double)); + memset (a->x1, 0, a->nstages * sizeof (double)); + memset (a->y0, 0, a->nstages * sizeof (double)); + memset (a->y1, 0, a->nstages * sizeof (double)); } void PHROT::xphrot (PHROT *a) @@ -579,6 +608,7 @@ void PHROT::xphrot (PHROT *a) for (int i = 0; i < a->size; i++) a->in[2 * i + 0] = -a->in[2 * i + 0]; } + if (a->run) { int i, n; @@ -590,9 +620,9 @@ void PHROT::xphrot (PHROT *a) for (n = 0; n < a->nstages; n++) { if (n > 0) a->x0[n] = a->y0[n - 1]; - a->y0[n] = a->b0 * a->x0[n] - + a->b1 * a->x1[n] - - a->a1 * a->y1[n]; + a->y0[n] = a->b0 * a->x0[n] + + a->b1 * a->x1[n] + - a->a1 * a->y1[n]; a->y1[n] = a->y0[n]; a->x1[n] = a->x0[n]; } @@ -601,7 +631,9 @@ void PHROT::xphrot (PHROT *a) } } else if (a->out != a->in) + { std::copy( a->in, a->in + a->size * 2, a->out); + } } void PHROT::setBuffers_phrot (PHROT *a, float* in, float* out) @@ -638,7 +670,7 @@ void PHROT::SetPHROTRun (TXA& txa, int run) flush_phrot (a); } -void PHROT::SetPHROTCorner (TXA& txa, float corner) +void PHROT::SetPHROTCorner (TXA& txa, double corner) { PHROT *a = txa.phrot.p; decalc_phrot (a); @@ -668,8 +700,8 @@ void PHROT::SetPHROTReverse (TXA& txa, int reverse) void BQLP::calc_bqlp(BQLP *a) { - float w0, cs, c, den; - w0 = TWOPI * a->fc / (float)a->rate; + double w0, cs, c, den; + w0 = TWOPI * a->fc / (double)a->rate; cs = cos(w0); c = sin(w0) / (2.0 * a->Q); den = 1.0 + c; @@ -681,7 +713,7 @@ void BQLP::calc_bqlp(BQLP *a) flush_bqlp(a); } -BQLP* BQLP::create_bqlp(int run, int size, float* in, float* out, float rate, float fc, float Q, float gain, int nstages) +BQLP* BQLP::create_bqlp(int run, int size, float* in, float* out, double rate, double fc, double Q, double gain, int nstages) { BQLP *a = new BQLP; a->run = run; @@ -693,12 +725,12 @@ BQLP* BQLP::create_bqlp(int run, int size, float* in, float* out, float rate, fl a->Q = Q; a->gain = gain; a->nstages = nstages; - a->x0 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); - a->x1 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); - a->x2 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); - a->y0 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); - a->y1 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); - a->y2 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->x0 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->x1 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->x2 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->y0 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->y1 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->y2 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); calc_bqlp(a); return a; } @@ -738,7 +770,8 @@ void BQLP::xbqlp(BQLP *a) for (n = 0; n < a->nstages; n++) { - if (n > 0) a->x0[2 * n + j] = a->y0[2 * (n - 1) + j]; + if (n > 0) + a->x0[2 * n + j] = a->y0[2 * (n - 1) + j]; a->y0[2 * n + j] = a->a0 * a->x0[2 * n + j] + a->a1 * a->x1[2 * n + j] + a->a2 * a->x2[2 * n + j] @@ -755,7 +788,9 @@ void BQLP::xbqlp(BQLP *a) } } else if (a->out != a->in) + { std::copy(a->in, a->in + a->size * 2, a->out); + } } void BQLP::setBuffers_bqlp(BQLP *a, float* in, float* out) @@ -797,7 +832,7 @@ void DBQLP::calc_dbqlp(BQLP *a) flush_dbqlp(a); } -BQLP* DBQLP::create_dbqlp(int run, int size, float* in, float* out, float rate, float fc, float Q, float gain, int nstages) +BQLP* DBQLP::create_dbqlp(int run, int size, float* in, float* out, double rate, double fc, double Q, double gain, int nstages) { BQLP *a = new BQLP; a->run = run; @@ -809,12 +844,12 @@ BQLP* DBQLP::create_dbqlp(int run, int size, float* in, float* out, float rate, a->Q = Q; a->gain = gain; a->nstages = nstages; - a->x0 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); - a->x1 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); - a->x2 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); - a->y0 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); - a->y1 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); - a->y2 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->x0 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->x1 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->x2 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->y0 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->y1 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->y2 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); calc_dbqlp(a); return a; } @@ -869,7 +904,9 @@ void DBQLP::xdbqlp(BQLP *a) } } else if (a->out != a->in) + { memcpy(a->out, a->in, a->size * sizeof(float)); + } } void DBQLP::setBuffers_dbqlp(BQLP *a, float* in, float* out) @@ -899,7 +936,7 @@ void DBQLP::setSize_dbqlp(BQLP *a, int size) void BQBP::calc_bqbp(BQBP *a) { - float f0, w0, bw, q, sn, cs, c, den; + double f0, w0, bw, q, sn, cs, c, den; bw = a->f_high - a->f_low; f0 = (a->f_high + a->f_low) / 2.0; q = f0 / bw; @@ -916,7 +953,7 @@ void BQBP::calc_bqbp(BQBP *a) flush_bqbp(a); } -BQBP* BQBP::create_bqbp(int run, int size, float* in, float* out, float rate, float f_low, float f_high, float gain, int nstages) +BQBP* BQBP::create_bqbp(int run, int size, float* in, float* out, double rate, double f_low, double f_high, double gain, int nstages) { BQBP *a = new BQBP; a->run = run; @@ -928,12 +965,12 @@ BQBP* BQBP::create_bqbp(int run, int size, float* in, float* out, float rate, fl a->f_high = f_high; a->gain = gain; a->nstages = nstages; - a->x0 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); - a->x1 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); - a->x2 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); - a->y0 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); - a->y1 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); - a->y2 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->x0 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->x1 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->x2 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->y0 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->y1 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->y2 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); calc_bqbp(a); return a; } @@ -992,7 +1029,9 @@ void BQBP::xbqbp(BQBP *a) } } else if (a->out != a->in) + { std::copy(a->in, a->in + a->size * 2, a->out); + } } void BQBP::setBuffers_bqbp(BQBP *a, float* in, float* out) @@ -1021,7 +1060,7 @@ void BQBP::setSize_bqbp(BQBP *a, int size) void BQBP::calc_dbqbp(BQBP *a) { - float f0, w0, bw, q, sn, cs, c, den; + double f0, w0, bw, q, sn, cs, c, den; bw = a->f_high - a->f_low; f0 = (a->f_high + a->f_low) / 2.0; q = f0 / bw; @@ -1038,7 +1077,7 @@ void BQBP::calc_dbqbp(BQBP *a) flush_dbqbp(a); } -BQBP* BQBP::create_dbqbp(int run, int size, float* in, float* out, float rate, float f_low, float f_high, float gain, int nstages) +BQBP* BQBP::create_dbqbp(int run, int size, float* in, float* out, double rate, double f_low, double f_high, double gain, int nstages) { BQBP *a = new BQBP; a->run = run; @@ -1050,12 +1089,12 @@ BQBP* BQBP::create_dbqbp(int run, int size, float* in, float* out, float rate, f a->f_high = f_high; a->gain = gain; a->nstages = nstages; - a->x0 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); - a->x1 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); - a->x2 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); - a->y0 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); - a->y1 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); - a->y2 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->x0 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->x1 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->x2 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->y0 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->y1 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->y2 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); calc_dbqbp(a); return a; } @@ -1110,7 +1149,9 @@ void BQBP::xdbqbp(BQBP *a) } } else if (a->out != a->in) + { memcpy(a->out, a->in, a->size * sizeof(float)); + } } void BQBP::setBuffers_dbqbp(BQBP *a, float* in, float* out) @@ -1139,18 +1180,18 @@ void BQBP::setSize_dbqbp(BQBP *a, int size) void SPHP::calc_sphp(SPHP *a) { - float g; - a->x0 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); - a->x1 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); - a->y0 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); - a->y1 = new float[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + double g; + a->x0 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->x1 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->y0 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); + a->y1 = new double[a->nstages * 2]; // (float*)malloc0(a->nstages * sizeof(complex)); g = exp(-TWOPI * a->fc / a->rate); a->b0 = +0.5 * (1.0 + g); a->b1 = -0.5 * (1.0 + g); a->a1 = -g; } -SPHP* SPHP::create_sphp(int run, int size, float* in, float* out, float rate, float fc, int nstages) +SPHP* SPHP::create_sphp(int run, int size, float* in, float* out, double rate, double fc, int nstages) { SPHP *a = new SPHP; a->run = run; @@ -1214,7 +1255,9 @@ void SPHP::xsphp(SPHP *a) } } else if (a->out != a->in) + { std::copy(a->in, a->in + a->size * 2, a->out); + } } void SPHP::setBuffers_sphp(SPHP *a, float* in, float* out) @@ -1244,18 +1287,18 @@ void SPHP::setSize_sphp(SPHP *a, int size) void SPHP::calc_dsphp(SPHP *a) { - float g; - a->x0 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); - a->x1 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); - a->y0 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); - a->y1 = new float[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + double g; + a->x0 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->x1 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->y0 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); + a->y1 = new double[a->nstages]; // (float*)malloc0(a->nstages * sizeof(float)); g = exp(-TWOPI * a->fc / a->rate); a->b0 = +0.5 * (1.0 + g); a->b1 = -0.5 * (1.0 + g); a->a1 = -g; } -SPHP* SPHP::create_dsphp(int run, int size, float* in, float* out, float rate, float fc, int nstages) +SPHP* SPHP::create_dsphp(int run, int size, float* in, float* out, double rate, double fc, int nstages) { SPHP *a = new SPHP; a->run = run; @@ -1317,7 +1360,9 @@ void SPHP::xdsphp(SPHP *a) } } else if (a->out != a->in) + { memcpy(a->out, a->in, a->size * sizeof(float)); + } } void SPHP::setBuffers_dsphp(SPHP *a, float* in, float* out) diff --git a/wdsp/iir.hpp b/wdsp/iir.hpp index be23fbc4b..d6ba5cfce 100644 --- a/wdsp/iir.hpp +++ b/wdsp/iir.hpp @@ -45,20 +45,20 @@ public: int size; float* in; float* out; - float rate; - float f; - float bw; - float a0, a1, a2, b1, b2; - float x0, x1, x2, y1, y2; + double rate; + double f; + double bw; + double a0, a1, a2, b1, b2; + double x0, x1, x2, y1, y2; - static SNOTCH* create_snotch (int run, int size, float* in, float* out, int rate, float f, float bw); + static SNOTCH* create_snotch (int run, int size, float* in, float* out, int rate, double f, double bw); static void destroy_snotch (SNOTCH *a); static void flush_snotch (SNOTCH *a); static void xsnotch (SNOTCH *a); static void setBuffers_snotch (SNOTCH *a, float* in, float* out); static void setSamplerate_snotch (SNOTCH *a, int rate); static void setSize_snotch (SNOTCH *a, int size); - static void SetSNCTCSSFreq (SNOTCH *a, float freq); + static void SetSNCTCSSFreq (SNOTCH *a, double freq); static void SetSNCTCSSRun (SNOTCH *a, int run); private: @@ -91,18 +91,29 @@ public: int size; float* in; float* out; - float rate; - float f; - float bw; - float cbw; - float gain; - float fgain; + double rate; + double f; + double bw; + double cbw; + double gain; + double fgain; int nstages; int design; - float a0, a1, a2, b1, b2; - float *x0, *x1, *x2, *y0, *y1, *y2; + double a0, a1, a2, b1, b2; + double *x0, *x1, *x2, *y0, *y1, *y2; - static SPEAK* create_speak (int run, int size, float* in, float* out, int rate, float f, float bw, float gain, int nstages, int design); + static SPEAK* create_speak ( + int run, + int size, + float* in, + float* out, + int rate, + double f, + double bw, + double gain, + int nstages, + int design + ); static void destroy_speak (SPEAK *a); static void flush_speak (SPEAK *a); static void xspeak (SPEAK *a); @@ -111,9 +122,9 @@ public: static void setSize_speak (SPEAK *a, int size); // RXA static void SetSPCWRun (RXA& rxa, int run); - static void SetSPCWFreq (RXA& rxa, float freq); - static void SetSPCWBandwidth (RXA& rxa, float bw); - static void SetSPCWGain (RXA& rxa, float gain); + static void SetSPCWFreq (RXA& rxa, double freq); + static void SetSPCWBandwidth (RXA& rxa, double bw); + static void SetSPCWGain (RXA& rxa, double gain); static void calc_speak (SPEAK *a); }; @@ -146,15 +157,27 @@ public: int rate; int npeaks; int* enable; - float* f; - float* bw; - float* gain; + double* f; + double* bw; + double* gain; int nstages; SPEAK** pfil; float* tmp; float* mix; - static MPEAK* create_mpeak (int run, int size, float* in, float* out, int rate, int npeaks, int* enable, float* f, float* bw, float* gain, int nstages); + static MPEAK* create_mpeak ( + int run, + int size, + float* in, + float* out, + int rate, + int npeaks, + int* enable, + double* f, + double* bw, + double* gain, + int nstages + ); static void destroy_mpeak (MPEAK *a); static void flush_mpeak (MPEAK *a); static void xmpeak (MPEAK *a); @@ -165,9 +188,9 @@ public: static void SetmpeakRun (RXA& rxa, int run); static void SetmpeakNpeaks (RXA& rxa, int npeaks); static void SetmpeakFilEnable (RXA& rxa, int fil, int enable); - static void SetmpeakFilFreq (RXA& rxa, int fil, float freq); - static void SetmpeakFilBw (RXA& rxa, int fil, float bw); - static void SetmpeakFilGain (RXA& rxa, int fil, float gain); + static void SetmpeakFilFreq (RXA& rxa, int fil, double freq); + static void SetmpeakFilBw (RXA& rxa, int fil, double bw); + static void SetmpeakFilGain (RXA& rxa, int fil, double gain); private: static void calc_mpeak (MPEAK *a); @@ -202,13 +225,13 @@ public: float* in; float* out; int rate; - float fc; + double fc; int nstages; // normalized such that a0 = 1 - float a1, b0, b1; - float *x0, *x1, *y0, *y1; + double a1, b0, b1; + double *x0, *x1, *y0, *y1; - static PHROT* create_phrot (int run, int size, float* in, float* out, int rate, float fc, int nstages); + static PHROT* create_phrot (int run, int size, float* in, float* out, int rate, double fc, int nstages); static void destroy_phrot (PHROT *a); static void flush_phrot (PHROT *a); static void xphrot (PHROT *a); @@ -217,7 +240,7 @@ public: static void setSize_phrot (PHROT *a, int size); // TXA Properties static void SetPHROTRun (TXA& txa, int run); - static void SetPHROTCorner (TXA& txa, float corner); + static void SetPHROTCorner (TXA& txa, double corner); static void SetPHROTNstages (TXA& txa, int nstages); static void SetPHROTReverse (TXA& txa, int reverse); @@ -250,15 +273,15 @@ public: int size; float* in; float* out; - float rate; - float fc; - float Q; - float gain; + double rate; + double fc; + double Q; + double gain; int nstages; - float a0, a1, a2, b1, b2; - float* x0, * x1, * x2, * y0, * y1, * y2; + double a0, a1, a2, b1, b2; + double* x0, * x1, * x2, * y0, * y1, * y2; - static BQLP* create_bqlp(int run, int size, float* in, float* out, float rate, float fc, float Q, float gain, int nstages); + static BQLP* create_bqlp(int run, int size, float* in, float* out, double rate, double fc, double Q, double gain, int nstages); static void destroy_bqlp(BQLP *a); static void flush_bqlp(BQLP *a); static void xbqlp(BQLP *a); @@ -290,7 +313,7 @@ namespace WDSP { class WDSP_API DBQLP { public: - static BQLP* create_dbqlp(int run, int size, float* in, float* out, float rate, float fc, float Q, float gain, int nstages); + static BQLP* create_dbqlp(int run, int size, float* in, float* out, double rate, double fc, double Q, double gain, int nstages); static void destroy_dbqlp(BQLP *a); static void flush_dbqlp(BQLP *a); static void xdbqlp(BQLP *a); @@ -326,15 +349,15 @@ public: int size; float* in; float* out; - float rate; - float f_low; - float f_high; - float gain; + double rate; + double f_low; + double f_high; + double gain; int nstages; - float a0, a1, a2, b1, b2; - float* x0, * x1, * x2, * y0, * y1, * y2; + double a0, a1, a2, b1, b2; + double* x0, * x1, * x2, * y0, * y1, * y2; - static BQBP* create_bqbp(int run, int size, float* in, float* out, float rate, float f_low, float f_high, float gain, int nstages); + static BQBP* create_bqbp(int run, int size, float* in, float* out, double rate, double f_low, double f_high, double gain, int nstages); static void destroy_bqbp(BQBP *a); static void flush_bqbp(BQBP *a); static void xbqbp(BQBP *a); @@ -343,7 +366,7 @@ public: static void setSize_bqbp(BQBP *a, int size); // Double Bi-Quad Band-Pass - static BQBP* create_dbqbp(int run, int size, float* in, float* out, float rate, float f_low, float f_high, float gain, int nstages); + static BQBP* create_dbqbp(int run, int size, float* in, float* out, double rate, double f_low, double f_high, double gain, int nstages); static void destroy_dbqbp(BQBP *a); static void flush_dbqbp(BQBP *a); static void xdbqbp(BQBP *a); @@ -380,13 +403,13 @@ public: int size; float* in; float* out; - float rate; - float fc; + double rate; + double fc; int nstages; - float a1, b0, b1; - float* x0, * x1, * y0, * y1; + double a1, b0, b1; + double* x0, * x1, * y0, * y1; - static SPHP* create_dsphp(int run, int size, float* in, float* out, float rate, float fc, int nstages); + static SPHP* create_dsphp(int run, int size, float* in, float* out, double rate, double fc, int nstages); static void destroy_dsphp(SPHP *a); static void flush_dsphp(SPHP *a); static void xdsphp(SPHP *a); @@ -395,7 +418,7 @@ public: static void setSize_dsphp(SPHP *a, int size); // Complex Single-Pole High-Pass - static SPHP* create_sphp(int run, int size, float* in, float* out, float rate, float fc, int nstages); + static SPHP* create_sphp(int run, int size, float* in, float* out, double rate, double fc, int nstages); static void destroy_sphp(SPHP *a); static void flush_sphp(SPHP *a); static void xsphp(SPHP *a); diff --git a/wdsp/patchpanel.cpp b/wdsp/patchpanel.cpp index 630a9643d..9637866ab 100644 --- a/wdsp/patchpanel.cpp +++ b/wdsp/patchpanel.cpp @@ -37,9 +37,9 @@ PANEL* PANEL::create_panel ( int size, float* in, float* out, - float gain1, - float gain2I, - float gain2Q, + double gain1, + double gain2I, + double gain2Q, int inselect, int copy ) @@ -70,9 +70,9 @@ void PANEL::flush_panel (PANEL *) void PANEL::xpanel (PANEL *a) { int i; - float I, Q; - float gainI = a->gain1 * a->gain2I; - float gainQ = a->gain1 * a->gain2Q; + double I, Q; + double gainI = a->gain1 * a->gain2I; + double gainQ = a->gain1 * a->gain2Q; // inselect is either 0(neither), 1(Q), 2(I), or 3(both) switch (a->copy) { @@ -147,20 +147,20 @@ void PANEL::SetPanelSelect (RXA& rxa, int select) rxa.panel.p->inselect = select; } -void PANEL::SetPanelGain1 (RXA& rxa, float gain) +void PANEL::SetPanelGain1 (RXA& rxa, double gain) { rxa.panel.p->gain1 = gain; } -void PANEL::SetPanelGain2 (RXA& rxa, float gainI, float gainQ) +void PANEL::SetPanelGain2 (RXA& rxa, double gainI, double gainQ) { rxa.panel.p->gain2I = gainI; rxa.panel.p->gain2Q = gainQ; } -void PANEL::SetPanelPan (RXA& rxa, float pan) +void PANEL::SetPanelPan (RXA& rxa, double pan) { - float gain1, gain2; + double gain1, gain2; if (pan <= 0.5) { @@ -198,7 +198,7 @@ void PANEL::SetPanelRun (TXA& txa, int run) txa.panel.p->run = run; } -void PANEL::SetPanelGain1 (TXA& txa, float gain) +void PANEL::SetPanelGain1 (TXA& txa, double gain) { txa.panel.p->gain1 = gain; //print_message ("micgainset.txt", "Set MIC Gain to", (int)(100.0 * gain), 0, 0); diff --git a/wdsp/patchpanel.hpp b/wdsp/patchpanel.hpp index 34b3ea712..48cbcce7b 100644 --- a/wdsp/patchpanel.hpp +++ b/wdsp/patchpanel.hpp @@ -42,9 +42,9 @@ public: int size; float* in; float* out; - float gain1; - float gain2I; - float gain2Q; + double gain1; + double gain2I; + double gain2Q; int inselect; int copy; @@ -53,9 +53,9 @@ public: int size, float* in, float* out, - float gain1, - float gain2I, - float gain2Q, + double gain1, + double gain2I, + double gain2Q, int inselect, int copy ); @@ -68,14 +68,14 @@ public: // RXA Properties static void SetPanelRun (RXA& rxa, int run); static void SetPanelSelect (RXA& rxa, int select); - static void SetPanelGain1 (RXA& rxa, float gain); - static void SetPanelGain2 (RXA& rxa, float gainI, float gainQ); - static void SetPanelPan (RXA& rxa, float pan); + static void SetPanelGain1 (RXA& rxa, double gain); + static void SetPanelGain2 (RXA& rxa, double gainI, double gainQ); + static void SetPanelPan (RXA& rxa, double pan); static void SetPanelCopy (RXA& rxa, int copy); static void SetPanelBinaural (RXA& rxa, int bin); // TXA Properties static void SetPanelRun (TXA& txa, int run); - static void SetPanelGain1 (TXA& txa, float gain); + static void SetPanelGain1 (TXA& txa, double gain); static void SetPanelSelect (TXA& txa, int select); }; diff --git a/wdsp/snba.cpp b/wdsp/snba.cpp index 28eab140f..3df71971b 100644 --- a/wdsp/snba.cpp +++ b/wdsp/snba.cpp @@ -273,9 +273,12 @@ void SNBA::ATAc0 (int n, int nr, double* A, double* r) { int i, j; memset(r, 0, n * sizeof (double)); + for (i = 0; i < n; i++) + { for (j = 0; j < nr; j++) r[i] += A[j * n + i] * A[j * n + 0]; + } } void SNBA::multA1TA2(double* a1, double* a2, int m, int n, int q, double* c) @@ -425,7 +428,7 @@ void SNBA::det(SNBA *d, int asize, double* v, int* detout) else if (d->sdet.vpwr[i] <= 2.0 * t1) t2 += 2.0 * t1 - d->sdet.vpwr[i]; } - t2 *= d->sdet.k2 / (double)(d->xsize - asize); + t2 *= d->sdet.k2 / (double) (d->xsize - asize); for (i = asize; i < d->xsize; i++) { @@ -444,8 +447,11 @@ void SNBA::det(SNBA *d, int asize, double* v, int* detout) switch (bstate) { case 0: - if (detout[i] == 1) bstate = 1; + if (detout[i] == 1) + bstate = 1; + break; + case 1: if (detout[i] == 0) { @@ -453,37 +459,51 @@ void SNBA::det(SNBA *d, int asize, double* v, int* detout) bsamp = i; bcount = 1; } + break; + case 2: ++bcount; + if (bcount > d->sdet.b) + { if (detout[i] == 1) bstate = 1; else bstate = 0; + } else if (detout[i] == 1) { for (j = bsamp; j < bsamp + bcount - 1; j++) detout[j] = 1; bstate = 1; } + break; } } + for (i = asize; i < d->xsize; i++) { if (detout[i] == 1) { for (j = i - 1; j > i - 1 - d->sdet.pre; j--) - if (j >= asize) detout[j] = 1; + { + if (j >= asize) + detout[j] = 1; + } } } + for (i = d->xsize - 1; i >= asize; i--) { if (detout[i] == 1) { for (j = i + 1; j < i + 1 + d->sdet.post; j++) - if (j < d->xsize) detout[j] = 1; + { + if (j < d->xsize) + detout[j] = 1; + } } } } @@ -510,6 +530,7 @@ int SNBA::scanFrame( int nextlist[MAXIMP]; memset (befimp, 0, MAXIMP * sizeof (int)); memset (aftimp, 0, MAXIMP * sizeof (int)); + while (i < xsize && nimp < MAXIMP) { if (det[i] == 1 && inflag == 0) @@ -530,16 +551,20 @@ int SNBA::scanFrame( if (nimp > 0) aftimp[nimp - 1]++; } + i++; } + for (i = 0; i < nimp; i++) { if (befimp[i] < aftimp[i]) p_opt[i] = befimp[i]; else p_opt[i] = aftimp[i]; + if (p_opt[i] > pval) p_opt[i] = pval; + if (p_opt[i] < (int)(pmultmin * limp[i])) p_opt[i] = -1; } @@ -549,6 +574,7 @@ int SNBA::scanFrame( merit[i] = (double)p_opt[i] / (double)limp[i]; nextlist[i] = i; } + for (j = 0; j < nimp - 1; j++) { for (k = 0; k < nimp - j - 1; k++) @@ -564,9 +590,15 @@ int SNBA::scanFrame( } } } + i = 1; + if (nimp > 0) - while (merit[i] == merit[0] && i < nimp) i++; + { + while (merit[i] == merit[0] && i < nimp) + i++; + } + for (j = 0; j < i - 1; j++) { for (k = 0; k < i - j - 1; k++) @@ -582,6 +614,7 @@ int SNBA::scanFrame( } } } + *next = nextlist[0]; return nimp; } @@ -673,7 +706,9 @@ void SNBA::xsnba (SNBA *d) RESAMPLE::xresample (d->outresamp); } else if (d->out != d->in) + { std::copy(d->in, d->in + d->bsize * 2, d->out); + } } /******************************************************************************************************** @@ -685,6 +720,7 @@ void SNBA::xsnba (SNBA *d) void SNBA::SetSNBARun (RXA& rxa, int run) { SNBA *a = rxa.snba.p; + if (a->run != run) { RXA::bpsnbaCheck (rxa, rxa.mode, rxa.ndb.p->master_run); diff --git a/wdsp/wcpAGC.cpp b/wdsp/wcpAGC.cpp index 824a73477..80ffddb9e 100644 --- a/wdsp/wcpAGC.cpp +++ b/wdsp/wcpAGC.cpp @@ -98,7 +98,7 @@ WCPAGC* WCPAGC::create_wcpagc ( a->in = in; a->out = out; a->io_buffsize = io_buffsize; - a->sample_rate = (float)sample_rate; + a->sample_rate = (double) sample_rate; a->tau_attack = tau_attack; a->tau_decay = tau_decay; a->n_tau = n_tau; @@ -121,7 +121,7 @@ WCPAGC* WCPAGC::create_wcpagc ( void WCPAGC::loadWcpAGC (WCPAGC *a) { - float tmp; + double tmp; //calculate internal parameters a->attack_buffsize = (int)ceil(a->sample_rate * a->n_tau * a->tau_attack); a->in_index = a->attack_buffsize + a->out_index; @@ -131,24 +131,22 @@ void WCPAGC::loadWcpAGC (WCPAGC *a) a->fast_backmult = 1.0 - exp(-1.0 / (a->sample_rate * a->tau_fast_backaverage)); a->onemfast_backmult = 1.0 - a->fast_backmult; - a->out_target = a->out_targ * (1.0 - exp(-(float)a->n_tau)) * 0.9999; + a->out_target = a->out_targ * (1.0 - exp(-(double)a->n_tau)) * 0.9999; a->min_volts = a->out_target / (a->var_gain * a->max_gain); a->inv_out_target = 1.0 / a->out_target; tmp = log10(a->out_target / (a->max_input * a->var_gain * a->max_gain)); + if (tmp == 0.0) tmp = 1e-16; + a->slope_constant = (a->out_target * (1.0 - 1.0 / a->var_gain)) / tmp; - a->inv_max_input = 1.0 / a->max_input; - tmp = pow (10.0, (a->hang_thresh - 1.0) / 0.125); a->hang_level = (a->max_input * tmp + (a->out_target / (a->var_gain * a->max_gain)) * (1.0 - tmp)) * 0.637; - a->hang_backmult = 1.0 - exp(-1.0 / (a->sample_rate * a->tau_hang_backmult)); a->onemhang_backmult = 1.0 - a->hang_backmult; - a->hang_decay_mult = 1.0 - exp(-1.0 / (a->sample_rate * a->tau_hang_decay)); } @@ -160,15 +158,16 @@ void WCPAGC::destroy_wcpagc (WCPAGC *a) void WCPAGC::flush_wcpagc (WCPAGC *a) { - memset ((void *)a->ring, 0, sizeof(float) * RB_SIZE * 2); + memset ((void *)a->ring, 0, sizeof(double) * RB_SIZE * 2); a->ring_max = 0.0; - memset ((void *)a->abs_ring, 0, sizeof(float)* RB_SIZE); + memset ((void *)a->abs_ring, 0, sizeof(double)* RB_SIZE); } void WCPAGC::xwcpagc (WCPAGC *a) { int i, j, k; - float mult; + double mult; + if (a->run) { if (a->mode == 0) @@ -178,6 +177,7 @@ void WCPAGC::xwcpagc (WCPAGC *a) a->out[2 * i + 0] = a->fixed_gain * a->in[2 * i + 0]; a->out[2 * i + 1] = a->fixed_gain * a->in[2 * i + 1]; } + return; } @@ -185,18 +185,20 @@ void WCPAGC::xwcpagc (WCPAGC *a) { if (++a->out_index >= a->ring_buffsize) a->out_index -= a->ring_buffsize; + if (++a->in_index >= a->ring_buffsize) a->in_index -= a->ring_buffsize; a->out_sample[0] = a->ring[2 * a->out_index + 0]; a->out_sample[1] = a->ring[2 * a->out_index + 1]; a->abs_out_sample = a->abs_ring[a->out_index]; - a->ring[2 * a->in_index + 0] = a->in[2 * i + 0]; - a->ring[2 * a->in_index + 1] = a->in[2 * i + 1]; + double xr = a->ring[2 * a->in_index + 0] = a->in[2 * i + 0]; + double xi = a->ring[2 * a->in_index + 1] = a->in[2 * i + 1]; + if (a->pmode == 0) - a->abs_ring[a->in_index] = std::max(fabs(a->ring[2 * a->in_index + 0]), fabs(a->ring[2 * a->in_index + 1])); + a->abs_ring[a->in_index] = std::max(fabs(xr), fabs(xi)); else - a->abs_ring[a->in_index] = sqrt(a->ring[2 * a->in_index + 0] * a->ring[2 * a->in_index + 0] + a->ring[2 * a->in_index + 1] * a->ring[2 * a->in_index + 1]); + a->abs_ring[a->in_index] = sqrt(xr*xr + xi*xi); a->fast_backaverage = a->fast_backmult * a->abs_out_sample + a->onemfast_backmult * a->fast_backaverage; a->hang_backaverage = a->hang_backmult * a->abs_out_sample + a->onemhang_backmult * a->hang_backaverage; @@ -205,6 +207,7 @@ void WCPAGC::xwcpagc (WCPAGC *a) { a->ring_max = 0.0; k = a->out_index; + for (j = 0; j < a->attack_buffsize; j++) { if (++k == a->ring_buffsize) @@ -213,6 +216,7 @@ void WCPAGC::xwcpagc (WCPAGC *a) a->ring_max = a->abs_ring[k]; } } + if (a->abs_ring[a->in_index] > a->ring_max) a->ring_max = a->abs_ring[a->in_index]; @@ -252,6 +256,7 @@ void WCPAGC::xwcpagc (WCPAGC *a) } break; } + case 1: { if (a->ring_max >= a->volts) @@ -288,6 +293,7 @@ void WCPAGC::xwcpagc (WCPAGC *a) } break; } + case 2: { if (a->ring_max >= a->volts) @@ -306,6 +312,7 @@ void WCPAGC::xwcpagc (WCPAGC *a) } break; } + case 3: { if (a->ring_max >= a->volts) @@ -320,6 +327,7 @@ void WCPAGC::xwcpagc (WCPAGC *a) } break; } + case 4: { if (a->ring_max >= a->volts) @@ -338,6 +346,7 @@ void WCPAGC::xwcpagc (WCPAGC *a) if (a->volts < a->min_volts) a->volts = a->min_volts; + a->gain = a->volts * a->inv_out_target; mult = (a->out_target - a->slope_constant * std::min (0.0, log10(a->inv_max_input * a->volts))) / a->volts; a->out[2 * i + 0] = a->out_sample[0] * mult; @@ -345,7 +354,9 @@ void WCPAGC::xwcpagc (WCPAGC *a) } } else if (a->out != a->in) + { std::copy(a->in, a->in + a->io_buffsize * 2, a->out); + } } void WCPAGC::setBuffers_wcpagc (WCPAGC *a, float* in, float* out) @@ -432,16 +443,16 @@ void WCPAGC::SetAGCHang (RXA& rxa, int hang) loadWcpAGC ( rxa.agc.p ); } -void WCPAGC::GetAGCHangLevel(RXA& rxa, float *hangLevel) +void WCPAGC::GetAGCHangLevel(RXA& rxa, double *hangLevel) //for line on bandscope { *hangLevel = 20.0 * log10( rxa.agc.p->hang_level / 0.637 ); } -void WCPAGC::SetAGCHangLevel(RXA& rxa, float hangLevel) +void WCPAGC::SetAGCHangLevel(RXA& rxa, double hangLevel) //for line on bandscope { - float convert, tmp; + double convert, tmp; if (rxa.agc.p->max_input > rxa.agc.p->min_volts) { @@ -458,59 +469,59 @@ void WCPAGC::SetAGCHangLevel(RXA& rxa, float hangLevel) void WCPAGC::GetAGCHangThreshold(RXA& rxa, int *hangthreshold) //for slider in setup { - *hangthreshold = (int)(100.0 * rxa.agc.p->hang_thresh); + *hangthreshold = (int) (100.0 * rxa.agc.p->hang_thresh); } void WCPAGC::SetAGCHangThreshold (RXA& rxa, int hangthreshold) //For slider in setup { - rxa.agc.p->hang_thresh = (float)hangthreshold / 100.0; + rxa.agc.p->hang_thresh = (double) hangthreshold / 100.0; loadWcpAGC ( rxa.agc.p ); } -void WCPAGC::GetAGCThresh(RXA& rxa, float *thresh, float size, float rate) +void WCPAGC::GetAGCThresh(RXA& rxa, double *thresh, double size, double rate) //for line on bandscope. { - float noise_offset; + double noise_offset; noise_offset = 10.0 * log10((rxa.nbp0.p->fhigh - rxa.nbp0.p->flow) * size / rate); *thresh = 20.0 * log10( rxa.agc.p->min_volts ) - noise_offset; } -void WCPAGC::SetAGCThresh(RXA& rxa, float thresh, float size, float rate) +void WCPAGC::SetAGCThresh(RXA& rxa, double thresh, double size, double rate) //for line on bandscope { - float noise_offset; + double noise_offset; noise_offset = 10.0 * log10((rxa.nbp0.p->fhigh - rxa.nbp0.p->flow) * size / rate); rxa.agc.p->max_gain = rxa.agc.p->out_target / (rxa.agc.p->var_gain * pow (10.0, (thresh + noise_offset) / 20.0)); loadWcpAGC ( rxa.agc.p ); } -void WCPAGC::GetAGCTop(RXA& rxa, float *max_agc) +void WCPAGC::GetAGCTop(RXA& rxa, double *max_agc) //for AGC Max Gain in setup { *max_agc = 20 * log10 (rxa.agc.p->max_gain); } -void WCPAGC::SetAGCTop (RXA& rxa, float max_agc) +void WCPAGC::SetAGCTop (RXA& rxa, double max_agc) //for AGC Max Gain in setup { - rxa.agc.p->max_gain = pow (10.0, (float)max_agc / 20.0); + rxa.agc.p->max_gain = pow (10.0, (double) max_agc / 20.0); loadWcpAGC ( rxa.agc.p ); } void WCPAGC::SetAGCSlope (RXA& rxa, int slope) { - rxa.agc.p->var_gain = pow (10.0, (float)slope / 20.0 / 10.0); + rxa.agc.p->var_gain = pow (10.0, (double) slope / 20.0 / 10.0); loadWcpAGC ( rxa.agc.p ); } -void WCPAGC::SetAGCFixed (RXA& rxa, float fixed_agc) +void WCPAGC::SetAGCFixed (RXA& rxa, double fixed_agc) { - rxa.agc.p->fixed_gain = pow (10.0, (float)fixed_agc / 20.0); + rxa.agc.p->fixed_gain = pow (10.0, (double) fixed_agc / 20.0); loadWcpAGC ( rxa.agc.p ); } -void WCPAGC::SetAGCMaxInputLevel (RXA& rxa, float level) +void WCPAGC::SetAGCMaxInputLevel (RXA& rxa, double level) { rxa.agc.p->max_input = level; loadWcpAGC ( rxa.agc.p ); @@ -529,25 +540,25 @@ void WCPAGC::SetALCSt (TXA& txa, int state) void WCPAGC::SetALCAttack (TXA& txa, int attack) { - txa.alc.p->tau_attack = (float)attack / 1000.0; + txa.alc.p->tau_attack = (double) attack / 1000.0; loadWcpAGC(txa.alc.p); } void WCPAGC::SetALCDecay (TXA& txa, int decay) { - txa.alc.p->tau_decay = (float)decay / 1000.0; + txa.alc.p->tau_decay = (double) decay / 1000.0; loadWcpAGC(txa.alc.p); } void WCPAGC::SetALCHang (TXA& txa, int hang) { - txa.alc.p->hangtime = (float)hang / 1000.0; + txa.alc.p->hangtime = (double) hang / 1000.0; loadWcpAGC(txa.alc.p); } -void WCPAGC::SetALCMaxGain (TXA& txa, float maxgain) +void WCPAGC::SetALCMaxGain (TXA& txa, double maxgain) { - txa.alc.p->max_gain = pow (10.0,(float)maxgain / 20.0); + txa.alc.p->max_gain = pow (10.0,(double) maxgain / 20.0); loadWcpAGC(txa.alc.p); } @@ -558,25 +569,25 @@ void WCPAGC::SetLevelerSt (TXA& txa, int state) void WCPAGC::SetLevelerAttack (TXA& txa, int attack) { - txa.leveler.p->tau_attack = (float)attack / 1000.0; + txa.leveler.p->tau_attack = (double) attack / 1000.0; loadWcpAGC(txa.leveler.p); } void WCPAGC::SetLevelerDecay (TXA& txa, int decay) { - txa.leveler.p->tau_decay = (float)decay / 1000.0; + txa.leveler.p->tau_decay = (double) decay / 1000.0; loadWcpAGC(txa.leveler.p); } void WCPAGC::SetLevelerHang (TXA& txa, int hang) { - txa.leveler.p->hangtime = (float)hang / 1000.0; + txa.leveler.p->hangtime = (double) hang / 1000.0; loadWcpAGC(txa.leveler.p); } -void WCPAGC::SetLevelerTop (TXA& txa, float maxgain) +void WCPAGC::SetLevelerTop (TXA& txa, double maxgain) { - txa.leveler.p->max_gain = pow (10.0,(float)maxgain / 20.0); + txa.leveler.p->max_gain = pow (10.0,(double) maxgain / 20.0); loadWcpAGC(txa.leveler.p); } diff --git a/wdsp/wcpAGC.hpp b/wdsp/wcpAGC.hpp index 8ef4e539d..267595d24 100644 --- a/wdsp/wcpAGC.hpp +++ b/wdsp/wcpAGC.hpp @@ -139,20 +139,20 @@ public: static void setSize_wcpagc (WCPAGC *a, int size); // RXA Properties static void SetAGCMode (RXA& rxa, int mode); - static void SetAGCFixed (RXA& rxa, float fixed_agc); + static void SetAGCFixed (RXA& rxa, double fixed_agc); static void SetAGCAttack (RXA& rxa, int attack); static void SetAGCDecay (RXA& rxa, int decay); static void SetAGCHang (RXA& rxa, int hang); - static void GetAGCHangLevel(RXA& rxa, float *hangLevel); - static void SetAGCHangLevel(RXA& rxa, float hangLevel); + static void GetAGCHangLevel(RXA& rxa, double *hangLevel); + static void SetAGCHangLevel(RXA& rxa, double hangLevel); static void GetAGCHangThreshold(RXA& rxa, int *hangthreshold); static void SetAGCHangThreshold (RXA& rxa, int hangthreshold); - static void GetAGCTop(RXA& rxa, float *max_agc); - static void SetAGCTop (RXA& rxa, float max_agc); + static void GetAGCTop(RXA& rxa, double *max_agc); + static void SetAGCTop (RXA& rxa, double max_agc); static void SetAGCSlope (RXA& rxa, int slope); - static void SetAGCThresh(RXA& rxa, float thresh, float size, float rate); - static void GetAGCThresh(RXA& rxa, float *thresh, float size, float rate); - static void SetAGCMaxInputLevel (RXA& rxa, float level); + static void SetAGCThresh(RXA& rxa, double thresh, double size, double rate); + static void GetAGCThresh(RXA& rxa, double *thresh, double size, double rate); + static void SetAGCMaxInputLevel (RXA& rxa, double level); // TXA Properties static void SetALCSt (TXA& txa, int state); static void SetALCAttack (TXA& txa, int attack); @@ -162,8 +162,8 @@ public: static void SetLevelerAttack (TXA& txa, int attack); static void SetLevelerDecay (TXA& txa, int decay); static void SetLevelerHang (TXA& txa, int hang); - static void SetLevelerTop (TXA& txa, float maxgain); - static void SetALCMaxGain (TXA& txa, float maxgain); + static void SetLevelerTop (TXA& txa, double maxgain); + static void SetALCMaxGain (TXA& txa, double maxgain); private: static void loadWcpAGC (WCPAGC *a);