From: drowe67 Date: Mon, 18 Mar 2013 04:19:47 +0000 (+0000) Subject: new 1300 bit/s mode X-Git-Url: http://git.whiteaudio.com/gitweb/?a=commitdiff_plain;h=4e4e9b26c06be8d6679380eb01cabd36f039401e;p=freetel-svn-tracking.git new 1300 bit/s mode git-svn-id: https://svn.code.sf.net/p/freetel/code@1206 01035d8c-6547-0410-b346-abe4f91aad63 --- diff --git a/codec2-dev/src/c2dec.c b/codec2-dev/src/c2dec.c index c1e1f467..c39193a2 100644 --- a/codec2-dev/src/c2dec.c +++ b/codec2-dev/src/c2dec.c @@ -46,16 +46,17 @@ int main(int argc, char *argv[]) FILE *fout; short *buf; unsigned char *bits; - int nsam, nbit, nbyte, i, byte, frames, bit_errors, error_mode; + int nsam, nbit, nbyte, i, byte, frames, bits_proc, bit_errors, error_mode; int nstart_bit, nend_bit, bit_rate; int state, next_state; float ber, r, burst_length, burst_period, burst_timer; + unsigned char mask; - if (argc < 4) { - printf("basic usage.................: c2dec 3200|2400|1600|1400|1200 InputBitFile OutputRawSpeechFile\n"); - printf("uniform errors usage........: c2dec 3200|2400|1600|1400|1200 InputBitFile OutputRawSpeechFile uniformBER startBit endBit\n"); - printf("uniform error on range usage: c2dec 3200|2400|1600|1400|1200 InputBitFile OutputRawSpeechFile uniformBER\n"); - printf("two state fading usage......: c2dec 3200|2400|1600|1400|1200 InputBitFile OutputRawSpeechFile burstLength burstPeriod\n"); + if ((argc != 4) && (argc != 5) && (argc != 6) && (argc != 7)) { + printf("basic usage.................: c2dec 3200|2400|1600|1400|1300|1200 InputBitFile OutputRawSpeechFile\n"); + printf("uniform errors usage........: c2dec 3200|2400|1600|1400|1300|1200 InputBitFile OutputRawSpeechFile uniformBER startBit endBit smoothingFlag\n"); + printf("uniform error on range usage: c2dec 3200|2400|1600|1400|1300|1200 InputBitFile OutputRawSpeechFile uniformBER\n"); + printf("two state fading usage......: c2dec 3200|2400|1600|1400|1300|1200 InputBitFile OutputRawSpeechFile burstLength burstPeriod\n"); printf("e.g c2dec 1400 hts1a.c2 hts1a_1400.raw\n"); printf("e.g c2dec 1400 hts1a.c2 hts1a_1400.raw 0.9\n"); printf("e.g c2dec 1400 hts1a.c2 hts1a_1400.raw 0.99 0.9\n"); @@ -70,10 +71,12 @@ int main(int argc, char *argv[]) mode = CODEC2_MODE_1600; else if (strcmp(argv[1],"1400") == 0) mode = CODEC2_MODE_1400; + else if (strcmp(argv[1],"1300") == 0) + mode = CODEC2_MODE_1300; else if (strcmp(argv[1],"1200") == 0) mode = CODEC2_MODE_1200; else { - fprintf(stderr, "Error in mode: %s. Must be 3200, 2400, 1600, 1400 or 1200\n", argv[1]); + fprintf(stderr, "Error in mode: %s. Must be 3200, 2400, 1600, 1400, 1300 or 1200\n", argv[1]); exit(1); } bit_rate = atoi(argv[1]); @@ -103,7 +106,7 @@ int main(int argc, char *argv[]) buf = (short*)malloc(nsam*sizeof(short)); nbyte = (nbit + 7) / 8; bits = (unsigned char*)malloc(nbyte*sizeof(char)); - frames = bit_errors = 0; + frames = bit_errors = bits_proc = 0; nstart_bit = 0; nend_bit = nbit-1; @@ -120,7 +123,7 @@ int main(int argc, char *argv[]) nend_bit = 2; state = 0; } - + if (argc == 7) { error_mode = UNIFORM_RANGE; ber = atof(argv[4]); @@ -142,10 +145,13 @@ int main(int argc, char *argv[]) r = (float)rand()/RAND_MAX; if (r < ber) { byte = i/8; - //printf("nbyte %d nbit %d i %d byte %d\n", nbyte, nbit, i, byte); - bits[byte] ^= 1 << (7 - i - byte*8); + //printf("nbyte %d nbit %d i %d byte %d bits[%d] 0x%0x ", nbyte, nbit, i, byte, byte, bits[byte]); + mask = 1 << (7 - i + byte*8); + bits[byte] ^= mask; + //printf("shift: %d mask: 0x%0x bits[%d] 0x%0x\n", 7 - i + byte*8, mask, byte, bits[byte] ); bit_errors++; - } + } + bits_proc++; } } @@ -171,9 +177,10 @@ int main(int argc, char *argv[]) r = (float)rand()/RAND_MAX; if (r < 0.5) { byte = i/8; - bits[byte] ^= 1 << (7 - i - byte*8); + bits[byte] ^= 1 << (7 - i + byte*8); bit_errors++; } + bits_proc++; } if (burst_timer > burst_period) { @@ -196,7 +203,7 @@ int main(int argc, char *argv[]) } if (error_mode) - fprintf(stderr, "actual BER: %1.3f\n", (float)bit_errors/(frames*nbit)); + fprintf(stderr, "actual BER: %1.3f\n", (float)bit_errors/bits_proc); codec2_destroy(codec2); diff --git a/codec2-dev/src/c2enc.c b/codec2-dev/src/c2enc.c index 88c20864..027f617b 100644 --- a/codec2-dev/src/c2enc.c +++ b/codec2-dev/src/c2enc.c @@ -44,7 +44,7 @@ int main(int argc, char *argv[]) int nsam, nbit, nbyte; if (argc != 4) { - printf("usage: c2enc 3200|2400|1600|1400|1200 InputRawspeechFile OutputBitFile\n"); + printf("usage: c2enc 3200|2400|1600|1400|1300|1200 InputRawspeechFile OutputBitFile\n"); printf("e.g c2enc 1400 ../raw/hts1a.raw hts1a.c2\n"); exit(1); } @@ -57,10 +57,12 @@ int main(int argc, char *argv[]) mode = CODEC2_MODE_1600; else if (strcmp(argv[1],"1400") == 0) mode = CODEC2_MODE_1400; + else if (strcmp(argv[1],"1300") == 0) + mode = CODEC2_MODE_1300; else if (strcmp(argv[1],"1200") == 0) mode = CODEC2_MODE_1200; else { - fprintf(stderr, "Error in mode: %s. Must be 3200, 2400, 1600, 1400 or 1200\n", argv[1]); + fprintf(stderr, "Error in mode: %s. Must be 3200, 2400, 1600, 1400, 1300 or 1200\n", argv[1]); exit(1); } diff --git a/codec2-dev/src/codec2.c b/codec2-dev/src/codec2.c index 156e6fdc..bad11110 100644 --- a/codec2-dev/src/codec2.c +++ b/codec2-dev/src/codec2.c @@ -62,6 +62,8 @@ void codec2_encode_1600(struct CODEC2 *c2, unsigned char * bits, short speech[]) void codec2_decode_1600(struct CODEC2 *c2, short speech[], const unsigned char * bits); void codec2_encode_1400(struct CODEC2 *c2, unsigned char * bits, short speech[]); void codec2_decode_1400(struct CODEC2 *c2, short speech[], const unsigned char * bits); +void codec2_encode_1300(struct CODEC2 *c2, unsigned char * bits, short speech[]); +void codec2_decode_1300(struct CODEC2 *c2, short speech[], const unsigned char * bits); void codec2_encode_1200(struct CODEC2 *c2, unsigned char * bits, short speech[]); void codec2_decode_1200(struct CODEC2 *c2, short speech[], const unsigned char * bits); static void ear_protection(float in_out[], int n); @@ -100,6 +102,7 @@ struct CODEC2 * CODEC2_WIN32SUPPORT codec2_create(int mode) (mode == CODEC2_MODE_2400) || (mode == CODEC2_MODE_1600) || (mode == CODEC2_MODE_1400) || + (mode == CODEC2_MODE_1300) || (mode == CODEC2_MODE_1200) ); c2->mode = mode; @@ -139,6 +142,8 @@ struct CODEC2 * CODEC2_WIN32SUPPORT codec2_create(int mode) c2->xq_enc[0] = c2->xq_enc[1] = 0.0; c2->xq_dec[0] = c2->xq_dec[1] = 0.0; + c2->smoothing = 0; + return c2; } @@ -180,6 +185,8 @@ int CODEC2_WIN32SUPPORT codec2_bits_per_frame(struct CODEC2 *c2) { return 64; if (c2->mode == CODEC2_MODE_1400) return 56; + if (c2->mode == CODEC2_MODE_1300) + return 52; if (c2->mode == CODEC2_MODE_1200) return 48; @@ -206,6 +213,8 @@ int CODEC2_WIN32SUPPORT codec2_samples_per_frame(struct CODEC2 *c2) { return 320; if (c2->mode == CODEC2_MODE_1400) return 320; + if (c2->mode == CODEC2_MODE_1300) + return 320; if (c2->mode == CODEC2_MODE_1200) return 320; @@ -220,6 +229,7 @@ void CODEC2_WIN32SUPPORT codec2_encode(struct CODEC2 *c2, unsigned char *bits, s (c2->mode == CODEC2_MODE_2400) || (c2->mode == CODEC2_MODE_1600) || (c2->mode == CODEC2_MODE_1400) || + (c2->mode == CODEC2_MODE_1300) || (c2->mode == CODEC2_MODE_1200) ); @@ -231,6 +241,8 @@ void CODEC2_WIN32SUPPORT codec2_encode(struct CODEC2 *c2, unsigned char *bits, s codec2_encode_1600(c2, bits, speech); if (c2->mode == CODEC2_MODE_1400) codec2_encode_1400(c2, bits, speech); + if (c2->mode == CODEC2_MODE_1300) + codec2_encode_1300(c2, bits, speech); if (c2->mode == CODEC2_MODE_1200) codec2_encode_1200(c2, bits, speech); } @@ -243,6 +255,7 @@ void CODEC2_WIN32SUPPORT codec2_decode(struct CODEC2 *c2, short speech[], const (c2->mode == CODEC2_MODE_2400) || (c2->mode == CODEC2_MODE_1600) || (c2->mode == CODEC2_MODE_1400) || + (c2->mode == CODEC2_MODE_1300) || (c2->mode == CODEC2_MODE_1200) ); @@ -254,6 +267,8 @@ void CODEC2_WIN32SUPPORT codec2_decode(struct CODEC2 *c2, short speech[], const codec2_decode_1600(c2, speech, bits); if (c2->mode == CODEC2_MODE_1400) codec2_decode_1400(c2, speech, bits); + if (c2->mode == CODEC2_MODE_1300) + codec2_decode_1300(c2, speech, bits); if (c2->mode == CODEC2_MODE_1200) codec2_decode_1200(c2, speech, bits); } @@ -713,7 +728,7 @@ void codec2_decode_1600(struct CODEC2 *c2, short speech[], const unsigned char * e[0] = interp_energy(c2->prev_e_dec, e[1]); interp_Wo(&model[2], &model[1], &model[3]); e[2] = interp_energy(e[1], e[3]); - + /* LSPs are sampled every 40ms so we interpolate the 3 frames in between, then recover spectral amplitudes */ @@ -914,6 +929,174 @@ void codec2_decode_1400(struct CODEC2 *c2, short speech[], const unsigned char * } +/*---------------------------------------------------------------------------*\ + + FUNCTION....: codec2_encode_1300 + AUTHOR......: David Rowe + DATE CREATED: March 14 2013 + + Encodes 320 speech samples (40ms of speech) into 52 bits. + + The codec2 algorithm actually operates internally on 10ms (80 + sample) frames, so we run the encoding algorithm 4 times: + + frame 0: voicing bit + frame 1: voicing bit, + frame 2: voicing bit + frame 3: voicing bit, Wo and E, scalar LSPs + + The bit allocation is: + + Parameter frame 2 frame 4 Total + ------------------------------------------------------- + Harmonic magnitudes (LSPs) 0 36 36 + Pitch (Wo) 0 7 7 + Energy 0 5 5 + Voicing (10ms update) 2 2 4 + TOTAL 2 50 52 + +\*---------------------------------------------------------------------------*/ + +void codec2_encode_1300(struct CODEC2 *c2, unsigned char * bits, short speech[]) +{ + MODEL model; + float lsps[LPC_ORD]; + float ak[LPC_ORD+1]; + float e; + int lsp_indexes[LPC_ORD]; + int Wo_index, e_index; + int i; + unsigned int nbit = 0; + + assert(c2 != NULL); + + memset(bits, '\0', ((codec2_bits_per_frame(c2) + 7) / 8)); + + /* frame 1: - voicing ---------------------------------------------*/ + + analyse_one_frame(c2, &model, speech); + pack(bits, &nbit, model.voiced, 1); + + /* frame 2: - voicing ---------------------------------------------*/ + + analyse_one_frame(c2, &model, &speech[N]); + pack(bits, &nbit, model.voiced, 1); + + /* frame 3: - voicing ---------------------------------------------*/ + + analyse_one_frame(c2, &model, &speech[2*N]); + pack(bits, &nbit, model.voiced, 1); + + /* frame 4: - voicing, scalar Wo & E, scalar LSPs ------------------*/ + + analyse_one_frame(c2, &model, &speech[3*N]); + pack(bits, &nbit, model.voiced, 1); + + Wo_index = encode_Wo(model.Wo); + pack(bits, &nbit, Wo_index, WO_BITS); + + e = speech_to_uq_lsps(lsps, ak, c2->Sn, c2->w, LPC_ORD); + e_index = encode_energy(e); + pack(bits, &nbit, e_index, E_BITS); + + encode_lsps_scalar(lsp_indexes, lsps, LPC_ORD); + for(i=0; iprev_lsps_dec, &lsps[3][0], weight); + interp_Wo2(&model[i], &c2->prev_model_dec, &model[3], weight); + e[i] = interp_energy2(c2->prev_e_dec, e[3],weight); + } + + /* then recover spectral amplitudes */ + + for(i=0; i<4; i++) { + lsp_to_lpc(&lsps[i][0], &ak[i][0], LPC_ORD); + aks_to_M2(c2->fft_fwd_cfg, &ak[i][0], LPC_ORD, &model[i], e[i], &snr, 0, 0, + c2->lpc_pf, c2->bass_boost, c2->beta, c2->gamma); + apply_lpc_correction(&model[i]); + } + + /* synthesise ------------------------------------------------*/ + + for(i=0; i<4; i++) + synthesise_one_frame(c2, &speech[N*i], &model[i], &ak[i][0]); + + /* update memories for next frame ----------------------------*/ + + c2->prev_model_dec = model[3]; + c2->prev_e_dec = e[3]; + for(i=0; iprev_lsps_dec[i] = lsps[3][i]; + +} + /*---------------------------------------------------------------------------*\ @@ -1277,5 +1460,3 @@ int CODEC2_WIN32SUPPORT codec2_rebuild_spare_bit(struct CODEC2 *c2, int unpacked return -1; } - - diff --git a/codec2-dev/src/codec2.h b/codec2-dev/src/codec2.h index 2c25f661..e871b71e 100644 --- a/codec2-dev/src/codec2.h +++ b/codec2-dev/src/codec2.h @@ -50,7 +50,8 @@ #define CODEC2_MODE_2400 1 #define CODEC2_MODE_1600 2 #define CODEC2_MODE_1400 3 -#define CODEC2_MODE_1200 4 +#define CODEC2_MODE_1300 4 +#define CODEC2_MODE_1200 5 struct CODEC2;