From 52a2198ad7ebc5f0b44eeff27f05d36a45d21629 Mon Sep 17 00:00:00 2001 From: David Date: Sun, 10 Mar 2019 09:23:29 +1030 Subject: [PATCH] added small vec test feature to quant_feat (didn't work well), and random bit error simulation feature to lpcnet_dec --- README.md | 6 +++++- src/lpcnet_dec.c | 37 +++++++++++++++++++++++++++++++------ src/quant_feat.c | 24 ++++++++++++++++++------ 3 files changed, 54 insertions(+), 13 deletions(-) diff --git a/README.md b/README.md index 6abaef5..8d6f38f 100644 --- a/README.md +++ b/README.md @@ -142,7 +142,11 @@ Same thing with everything integrated into stand alone encoder and decoder progr ```cat ~/Downloads/speech_orig_16k.s16 | ./lpcnet_enc | ./lpcnet_dec | aplay -f S16_LE -r 16000``` -The bit stream interface is 1 bit/char, as I find that convenient for my digital voice over radio experiments. The decimation rate, number of VQ stages, and a few other parameters can be set as command line options. You'll need the same set of parameters for the encoder as decoder. +The bit stream interface is 1 bit/char, as I find that convenient for my digital voice over radio experiments. The decimation rate, number of VQ stages, and a few other parameters can be set as command line options, for example 20ms frame rate, 3 stage VQ (2050 bits/s): + +```cat ~/Downloads/speech_orig_16k.s16 | ./lpcnet_enc -d 2 -n 3 | ./lpcnet_dec -d 2 -n 3 | aplay -f S16_LE -r 16000``` + +You'll need the same set of parameters for the encoder as decoder. Useful additions would be: diff --git a/src/lpcnet_dec.c b/src/lpcnet_dec.c index ab11e96..0ffae51 100644 --- a/src/lpcnet_dec.c +++ b/src/lpcnet_dec.c @@ -58,10 +58,12 @@ int main(int argc, char **argv) { int mbest_survivors = 5; float weight = 1.0/sqrt(NB_BANDS); int pitch_bits = 6; - + float ber = 0.0; + /* quantiser options */ static struct option long_options[] = { + {"ber", required_argument, 0, 'b'}, {"decimate", required_argument, 0, 'd'}, {"numstages", required_argument, 0, 'n'}, {"pitchquant", required_argument, 0, 'o'}, @@ -73,8 +75,12 @@ int main(int argc, char **argv) { int c; int opt_index = 0; - while ((c = getopt_long (argc, argv, "d:n:o:p:v", long_options, &opt_index)) != -1) { + while ((c = getopt_long (argc, argv, "b:d:n:o:p:v", long_options, &opt_index)) != -1) { switch (c) { + case 'b': + ber = atof(optarg); + fprintf(stderr, "BER = %f\n", ber); + break; case 'd': dec = atoi(optarg); fprintf(stderr, "dec = %d\n", dec); @@ -94,8 +100,10 @@ int main(int argc, char **argv) { case 'v': lpcnet_verbose = 1; break; - default: - fprintf(stderr,"usage: %s [Options]:\n [-d --decimation 1/2/3...]\n", argv[0]); + default: + fprintf(stderr,"usage: %s [Options]:\n", argv[0]); + fprintf(stderr," [-b --ber BER]\n"); + fprintf(stderr," [-d --decimation 1/2/3...]\n"); fprintf(stderr," [-n --numstages]\n [-o --pitchbits nBits]\n"); fprintf(stderr," [-p --pred predCoff]\n"); fprintf(stderr," [-v --verbose]\n"); @@ -120,13 +128,27 @@ int main(int argc, char **argv) { fin = stdin; fout = stdout; - + int nbits = 0, nerrs = 0; + do { float in_features[NB_TOTAL_FEATURES]; float features[NB_TOTAL_FEATURES]; short pcm[FRAME_SIZE]; - if ((q->f % q->dec) == 0) + if ((q->f % q->dec) == 0) { bits_read = fread(frame, sizeof(char), q->bits_per_frame, fin); + nbits += bits_read; + if (ber != 0.0) { + int i; + for(i=0; ibits_per_frame; i++) { + float r = (float)rand()/RAND_MAX; + if (r < ber) { + frame[i] = (frame[i] ^ 1) & 0x1; + nerrs++; + } + } + } + + } lpcnet_frame_to_features(q, frame, in_features); RNN_COPY(features, in_features, NB_TOTAL_FEATURES); @@ -139,5 +161,8 @@ int main(int argc, char **argv) { fclose(fin); fclose(fout); lpcnet_destroy(net); lpcnet_quant_destroy(q); + + if (ber != 0.0) + fprintf(stderr, "nbits: %d nerr: %d BER: %4.3f\n", nbits, nerrs, (float)nerrs/nbits); return 0; } diff --git a/src/quant_feat.c b/src/quant_feat.c index 1ba4fd8..5a0cff2 100644 --- a/src/quant_feat.c +++ b/src/quant_feat.c @@ -61,10 +61,12 @@ int main(int argc, char *argv[]) { float weight = 1.0; float pitch_gain_bias = 0.0; int pitch_bits = 0; - + int small_vec = 0; + for(i=0; i