minimodem: --limit (2.3) sets fsk_confidence_search_limit
Significant performance enhancements from fsk_confidence_search_limit: runs far fewer FFT's when --limit (default 2.3) is less than INFINITY.
This commit is contained in:
parent
e1b055cf4f
commit
f81f069d95
27
src/fsk.c
27
src/fsk.c
|
@ -409,8 +409,10 @@ fsk_frame_analyze( fsk_plan *fskp, float *samples, float samples_per_bit,
|
|||
/* returns confidence value [0.0 to 1.0] */
|
||||
float
|
||||
fsk_find_frame( fsk_plan *fskp, float *samples, unsigned int frame_nsamples,
|
||||
unsigned int try_first_sample,
|
||||
unsigned int try_max_nsamples,
|
||||
unsigned int try_step_nsamples,
|
||||
float try_confidence_search_limit,
|
||||
unsigned int *bits_outp,
|
||||
unsigned int *frame_start_outp
|
||||
)
|
||||
|
@ -419,25 +421,34 @@ fsk_find_frame( fsk_plan *fskp, float *samples, unsigned int frame_nsamples,
|
|||
|
||||
// try_step_nsamples = 1; // pedantic TEST
|
||||
|
||||
unsigned int t;
|
||||
unsigned int best_t = 0;
|
||||
float best_c = 0.0;
|
||||
unsigned int best_bits = 0;
|
||||
for ( t=0; t+try_step_nsamples<=try_max_nsamples; t+=try_step_nsamples )
|
||||
|
||||
// Scan the frame positions starting with the one try_first_sample,
|
||||
// alternating between a step above that, a step below that, above, below,
|
||||
// and so on, until we've scanned the whole try_max_nsamples range.
|
||||
int j;
|
||||
for ( j=0; ; j++ )
|
||||
{
|
||||
int up = j%2 ? 1 : -1;
|
||||
int t = try_first_sample + up*((j+1)/2)*try_step_nsamples;
|
||||
if ( t >= (int)try_max_nsamples )
|
||||
break;
|
||||
if ( t < 0 )
|
||||
continue;
|
||||
|
||||
float c;
|
||||
unsigned int bits_out = 0;
|
||||
debug_log("try fsk_frame_analyze(skip=%+d)\n", t);
|
||||
debug_log("try fsk_frame_analyze at t=%d\n", t);
|
||||
c = fsk_frame_analyze(fskp, samples+t, samples_per_bit, &bits_out);
|
||||
if ( best_c < c ) {
|
||||
best_t = t;
|
||||
best_c = c;
|
||||
best_bits = bits_out;
|
||||
// TEST
|
||||
// if ( best_c > 100.0f )
|
||||
// break;
|
||||
// if we find a perfect frame, stop scanning for a better one
|
||||
if ( best_c == INFINITY )
|
||||
// If we find a frame with confidence > try_confidence_search_limit
|
||||
// quit searching.
|
||||
if ( best_c >= try_confidence_search_limit )
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -63,8 +63,10 @@ fsk_plan_destroy( fsk_plan *fskp );
|
|||
/* returns confidence value [0.0 to 1.0] */
|
||||
float
|
||||
fsk_find_frame( fsk_plan *fskp, float *samples, unsigned int frame_nsamples,
|
||||
unsigned int try_first_sample,
|
||||
unsigned int try_max_nsamples,
|
||||
unsigned int try_step_nsamples,
|
||||
float try_confidence_search_limit,
|
||||
unsigned int *bits_outp,
|
||||
unsigned int *frame_start_outp
|
||||
);
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
.\" First parameter, NAME, should be all caps
|
||||
.\" Second parameter, SECTION, should be 1-8, maybe w/ subsection
|
||||
.\" other parameters are allowed: see man(7), man(1)
|
||||
.TH MINIMODEM 1 "August 12, 2011"
|
||||
.TH MINIMODEM 1 "August 19, 2012"
|
||||
.\" Please adjust this date whenever revising the manpage.
|
||||
.\"
|
||||
.\" Some roff macros, for reference:
|
||||
|
@ -48,8 +48,19 @@ receive mode: decode audio tones
|
|||
.B \-a, \-\-auto-carrier
|
||||
automatically detect mark and space frequences from carrier
|
||||
.TP
|
||||
.B \-c, \-\-confidence threshold
|
||||
set receive confidence (minimum SNR) threshold (default 2.0)
|
||||
.B \-c, \-\-confidence min-snr-threshold
|
||||
Set receive confidence minimum SNR threshold (default 2.0).
|
||||
This value acts as an FSK decoder "squelch" control.
|
||||
Increase to accept only very clean signals (up to INFINITY, but
|
||||
a value around 5.0 is more practical). Decrease to accept partial
|
||||
decoding of noisy signals (down to 1.0).
|
||||
.TP
|
||||
.B \-l, \-\-limit max-snr-search-limit
|
||||
Set receive confidence maximum SNR search limit (default 2.3).
|
||||
This value acts as a performance vs. analysis quality control.
|
||||
Increase (up to INFINITY) for a more pedantic analysis
|
||||
and higher CPU usage. Decrease (down to the min-snr-threshold)
|
||||
for a sloppier analysis, with lower CPU usage.
|
||||
.TP
|
||||
.B \-8, \-\-ascii
|
||||
ASCII 8\-N\-1
|
||||
|
@ -143,7 +154,7 @@ The latest version is available at <http://www.whence.com/minimodem>.
|
|||
.B minimodem
|
||||
was written by Kamal Mostafa <kamal@whence.com>.
|
||||
.SH COPYRIGHT
|
||||
Copyright \(co 2011 by Kamal Mostafa <kamal@whence.com>.
|
||||
Copyright \(co 2011-2012 by Kamal Mostafa <kamal@whence.com>.
|
||||
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>.
|
||||
.br
|
||||
This is free software: you are free to change and redistribute it.
|
||||
|
|
|
@ -322,6 +322,7 @@ usage()
|
|||
" [options]\n"
|
||||
" -a, --auto-carrier\n"
|
||||
" -c, --confidence {min-snr-threshold}\n"
|
||||
" -l, --limit {max-snr-search-limit}\n"
|
||||
" -8, --ascii ASCII 8-N-1\n"
|
||||
" -5, --baudot Baudot 5-N-1\n"
|
||||
" -f, --file {filename.flac}\n"
|
||||
|
@ -360,7 +361,20 @@ main( int argc, char*argv[] )
|
|||
char *filename = NULL;
|
||||
|
||||
float carrier_autodetect_threshold = 0.0;
|
||||
float bfsk_confidence_threshold = 2.0;
|
||||
|
||||
// fsk_confidence_threshold : signal-to-noise squelch control
|
||||
//
|
||||
// The minimum SNR confidence level seen as "a signal".
|
||||
float fsk_confidence_threshold = 2.0;
|
||||
|
||||
// fsk_confidence_search_limit : performance vs. quality
|
||||
//
|
||||
// If we find a frame with SNR confidence > confidence_search_limit,
|
||||
// quit searching for a better frame. confidence_search_limit has a
|
||||
// dramatic effect on peformance (high value yields low performance, but
|
||||
// higher decode quality, for noisy or hard-to-discern signals (Bell 103).
|
||||
float fsk_confidence_search_limit = 2.3f;
|
||||
// float fsk_confidence_search_limit = INFINITY; /* for test */
|
||||
|
||||
sa_backend_t sa_backend = SA_BACKEND_SYSDEFAULT;
|
||||
sa_format_t sample_format = SA_SAMPLE_FORMAT_S16;
|
||||
|
@ -403,6 +417,7 @@ main( int argc, char*argv[] )
|
|||
{ "receive", 0, 0, 'r' },
|
||||
{ "read", 0, 0, 'r' },
|
||||
{ "confidence", 1, 0, 'c' },
|
||||
{ "limit", 1, 0, 'l' },
|
||||
{ "auto-carrier", 0, 0, 'a' },
|
||||
{ "ascii", 0, 0, '8' },
|
||||
{ "baudot", 0, 0, '5' },
|
||||
|
@ -438,7 +453,10 @@ main( int argc, char*argv[] )
|
|||
TX_mode = 0;
|
||||
break;
|
||||
case 'c':
|
||||
bfsk_confidence_threshold = atof(optarg);
|
||||
fsk_confidence_threshold = atof(optarg);
|
||||
break;
|
||||
case 'l':
|
||||
fsk_confidence_search_limit = atof(optarg);
|
||||
break;
|
||||
case 'a':
|
||||
carrier_autodetect_threshold = 0.001;
|
||||
|
@ -607,6 +625,9 @@ main( int argc, char*argv[] )
|
|||
if ( band_width > bfsk_data_rate )
|
||||
band_width = bfsk_data_rate;
|
||||
|
||||
// sanitize confidence search limit
|
||||
if ( fsk_confidence_search_limit < fsk_confidence_threshold )
|
||||
fsk_confidence_search_limit = fsk_confidence_threshold;
|
||||
|
||||
char *stream_name = NULL;;
|
||||
|
||||
|
@ -842,9 +863,25 @@ main( int argc, char*argv[] )
|
|||
* prev_stop bit begins (since the "frame" includes the prev_stop). */
|
||||
unsigned int frame_start_sample = 0;
|
||||
|
||||
// If we don't have carrier, then set this try_confidence_search_limit
|
||||
// to infinity (search for best possible frame) so to get the decoder
|
||||
// into phase with the signal, so the next try_first_sample will match
|
||||
// up with where the next frame should be.
|
||||
unsigned int try_first_sample;
|
||||
float try_confidence_search_limit;
|
||||
if ( carrier ) {
|
||||
try_first_sample = nsamples_overscan;
|
||||
try_confidence_search_limit = fsk_confidence_search_limit;
|
||||
} else {
|
||||
try_first_sample = 0;
|
||||
try_confidence_search_limit = INFINITY;
|
||||
}
|
||||
|
||||
confidence = fsk_find_frame(fskp, samplebuf, frame_nsamples,
|
||||
try_first_sample,
|
||||
try_max_nsamples,
|
||||
try_step_nsamples,
|
||||
try_confidence_search_limit,
|
||||
&bits,
|
||||
&frame_start_sample
|
||||
);
|
||||
|
@ -857,7 +894,7 @@ main( int argc, char*argv[] )
|
|||
|
||||
#define FSK_MAX_NOCONFIDENCE_BITS 20
|
||||
|
||||
if ( confidence <= bfsk_confidence_threshold ) {
|
||||
if ( confidence <= fsk_confidence_threshold ) {
|
||||
|
||||
// FIXME: explain
|
||||
if ( ++noconfidence > FSK_MAX_NOCONFIDENCE_BITS )
|
||||
|
|
Loading…
Reference in New Issue