Michael Jacobson
2007-Jul-23 14:39 UTC
[Speex-dev] Shoehorning speex is confusing a newbie
This is going to take some explaining and I apologize in advance if any of this is found in the manual or sample code but I couldn't find it. I just graduated last may and this is my first experience with vocoders and dissecting a professional's code. I work for a company that is currently using a G729A vocoder from a 3rd party software company and is looking into speex so they no longer have to pay royalties. The product we are trying to force speex into is based on a TI C5416 DSP that did narrowband 8-bit, 8kbs. The product was fairly full as it is so some modifications had to be made in order to fit speex into the project just to allow it to link. The modifications are based off assumptions that I made when looking over the code so I may have been absolutely wrong. The main assumption was about the exc tables. In looking through modes.c it appeared that only one table was required for 8kbs so I commented out the portions of the code that referenced the other tables and modified "static const SpeexNBMode nb_mode" structure so that the pointers to the other structures that referenced the tables were NULL. We did not have enough data memory to store all the tables. I thought this would work with my initialization but when I stepped through the code in nb_celp for encode it would put it in mode 6 (instead of mode 3), which I believe is 18.2kbs (table 8.2). My set up code is: st = speex_encoder_init(&speex_nb_mode); speex_bits_set_bit_buffer(&bits, &G729_tx, COMPRESS_LENGTH); tmp=TESTENC_QUALITY; //=4 speex_encoder_ctl(st, SPEEX_SET_QUALITY, &tmp); speex_encode_int(st, (spx_int16_t *)samples_in, &bits); which I thought would put it in 8kbs narrowband. I tried to use SPEEX_SET_MODE in there too but it just got overwritten by the set mode in the encode function. So I thought I'd try to force it into mode 3 and see what happens, and I got A result, but when I try to decode it my decode stage gets stuck in an infinite loop: while (st->voc_offset<st->subframeSize) { if (st->voc_offset>=0) exc[st->voc_offset]=sqrt(1.0*ol_pitch); st->voc_offset+=ol_pitch; } because both voc_offset and ol_pitch is = 0 because this code is never entered: if (SUBMODE(lbr_pitch)!=-1) { ol_pitch = st->min_pitch+speex_bits_unpack_unsigned(bits, 7); } This is how I set up the decoder: dec = speex_decoder_init(&speex_nb_mode); speex_bits_set_bit_buffer(&bits, &Speex_enc_buffer[0 + COMPRESS_LENGTH*Speex_player_frame], COMPRESS_LENGTH); tmp=0; speex_decoder_ctl(dec, SPEEX_SET_ENH, &tmp); speex_decode_int(dec, &bits, (spx_int16_t *)samples_out); There are some things I am sure will be asked. Yes I set flags for the TI_54X part, disable wideband, manual allocation, and fixed point in a config file and defined the #define value needed to include that config file. I do have a heap for the setup of the state structure for encode and decode and yes I made sure it was big enough to allocate enough to both. Yes I destroy the structures after I am done en/decoding them. If there is anything you need to help you help me then I am defiantly willing to share. I am thoroughly confused and could use some help. Thanks. -Mike Jacobson michael.jacobson@ultratec.com -------------- next part -------------- An HTML attachment was scrubbed... URL: http://lists.xiph.org/pipermail/speex-dev/attachments/20070723/9dd3aba4/attachment.html
Hi Michael,> The main assumption was about the exc tables. In looking through > modes.c it appeared that only one table was required for 8kbsThe assumption is correct.> so I > commented out the portions of the code that referenced the other tables > and modified "static const SpeexNBMode nb_mode" structure so that the > pointers to the other structures that referenced the tables were NULL. > We did not have enough data memory to store all the tables. I thought > this would work with my initialization but when I stepped through the > code in nb_celp for encode it would put it in mode 6 (instead of mode > 3), which I believe is 18.2kbs (table 8.2). My set up code is: > > st = speex_encoder_init(&speex_nb_mode); > speex_bits_set_bit_buffer(&bits, &G729_tx, COMPRESS_LENGTH); > tmp=TESTENC_QUALITY; //=4 > speex_encoder_ctl(st, SPEEX_SET_QUALITY, &tmp); > speex_encode_int(st, (spx_int16_t *)samples_in, &bits);That appears correct -- assuming tmp is a 32-bit int (spx_int32_t) and its value is really 4. In general, make sure that you use 32-bit integers since it's a common cause of errors on the TI 5xxx. Also make sure you're using 1.2beta2 (or current git/svn).> which I thought would put it in 8kbs narrowband. I tried to use > SPEEX_SET_MODE in there too but it just got overwritten by the set mode > in the encode function. So I thought I'd try to force it into mode 3 > and see what happens, and I got A result, but when I try to decode it my > decode stage gets stuck in an infinite loop: > > while (st->voc_offset<st->subframeSize) > { > if (st->voc_offset>=0) > exc[st->voc_offset]=sqrt(1.0*ol_pitch); > st->voc_offset+=ol_pitch; > }Things should never go there at all. This code is only for mode 1.> because both voc_offset and ol_pitch is = 0 because this code is never > entered: > > if (SUBMODE(lbr_pitch)!=-1) > { > ol_pitch = st->min_pitch+speex_bits_unpack_unsigned(bits, 7); > } > > This is how I set up the decoder: > > dec = speex_decoder_init(&speex_nb_mode); > speex_bits_set_bit_buffer(&bits, &Speex_enc_buffer[0 + > COMPRESS_LENGTH*Speex_player_frame], COMPRESS_LENGTH);doesn't this read all the bits that are *after* the ones you want?> tmp=0; > speex_decoder_ctl(dec, SPEEX_SET_ENH, &tmp); > speex_decode_int(dec, &bits, (spx_int16_t *)samples_out); > > There are some things I am sure will be asked. Yes I set flags for the > TI_54X part, disable wideband, manual allocation,You sure you don't allocate the same memory for the encoder and the decoder or something like that?> and fixed point in a > config file and defined the #define value needed to include that config > file. I do have a heap for the setup of the state structure for encode > and decode and yes I made sure it was big enough to allocate enough to > both. Yes I destroy the structures after I am done en/decoding them. > If there is anything you need to help you help me then I am defiantly > willing to share. I am thoroughly confused and could use some help.Not clear what the problem is, but I suspect it's some kind of memory management and/or 16-bit vs. 32-bit problem. Can you try and work directly with testenc and sampleenc first to see if things work. That's an easier way to start. Jean-Marc
Skipped content of type multipart/alternative-------------- next part -------------- A non-text attachment was scrubbed... Name: modes-shrink.patch Type: application/octet-stream Size: 2897 bytes Desc: not available Url : http://lists.xiph.org/pipermail/speex-dev/attachments/20070724/4a72e960/modes-shrink-0001.obj -------------- next part -------------- A non-text attachment was scrubbed... Name: nb_celp-shrink.patch Type: application/octet-stream Size: 2821 bytes Desc: not available Url : http://lists.xiph.org/pipermail/speex-dev/attachments/20070724/4a72e960/nb_celp-shrink-0001.obj -------------- next part -------------- A non-text attachment was scrubbed... Name: c55-pjt-shrink.patch Type: application/octet-stream Size: 1211 bytes Desc: not available Url : http://lists.xiph.org/pipermail/speex-dev/attachments/20070724/4a72e960/c55-pjt-shrink-0001.obj -------------- next part -------------- A non-text attachment was scrubbed... Name: stack_alloc.h.debug Type: application/octet-stream Size: 3953 bytes Desc: not available Url : http://lists.xiph.org/pipermail/speex-dev/attachments/20070724/4a72e960/stack_alloc.h-0001.obj