diff options
author | Marcus Müller <mmueller@gnuradio.org> | 2019-08-07 21:45:12 +0200 |
---|---|---|
committer | Marcus Müller <marcus@hostalia.de> | 2019-08-09 23:04:28 +0200 |
commit | f7bbf2c1d8d780294f3e016aff239ca35eb6516e (patch) | |
tree | e09ab6112e02b2215b2d59ac24d3d6ea2edac745 /gr-fec/lib/cc_decoder_impl.cc | |
parent | 78431dc6941e3acc67c858277dfe4a0ed583643c (diff) |
Tree: clang-format without the include sorting
Diffstat (limited to 'gr-fec/lib/cc_decoder_impl.cc')
-rw-r--r-- | gr-fec/lib/cc_decoder_impl.cc | 888 |
1 files changed, 435 insertions, 453 deletions
diff --git a/gr-fec/lib/cc_decoder_impl.cc b/gr-fec/lib/cc_decoder_impl.cc index c65e67706b..abe5ca59bc 100644 --- a/gr-fec/lib/cc_decoder_impl.cc +++ b/gr-fec/lib/cc_decoder_impl.cc @@ -33,473 +33,455 @@ #include <vector> namespace gr { - namespace fec { - namespace code { - - generic_decoder::sptr - cc_decoder::make(int frame_size, int k, - int rate, std::vector<int> polys, - int start_state, int end_state, - cc_mode_t mode, bool padded) - { - return generic_decoder::sptr - (new cc_decoder_impl(frame_size, k, rate, polys, - start_state, end_state, mode, padded)); - } - - cc_decoder_impl::cc_decoder_impl(int frame_size, int k, - int rate, std::vector<int> polys, - int start_state, int end_state, - cc_mode_t mode, bool padded) - : generic_decoder("cc_decoder"), - d_k(k), - d_rate(rate), - d_polys(polys), - d_mode(mode), - d_padding(0), - d_start_state_chaining(start_state), - d_start_state_nonchaining(start_state), - d_end_state_nonchaining(end_state) - { - // Set max frame size here; all buffers and settings will be - // based on this value. - d_max_frame_size = frame_size; - d_frame_size = frame_size; - - // set up a padding factor. If padding, the encoded frame was exteded - // by this many bits to fit into a full byte. - if(padded && (mode == CC_TERMINATED)) { - d_padding = static_cast<int>(8.0f*ceilf(d_rate*(d_k-1)/8.0f) - (d_rate*(d_k-1))); - } - - d_vp = new struct v; - - d_numstates = 1 << (d_k - 1); - - d_decision_t_size = d_numstates/8; //packed bit array - - d_managed_in_size = 0; - switch(d_mode) { - case(CC_TAILBITING): - d_end_state = &d_end_state_chaining; - d_veclen = d_frame_size + (6 * (d_k - 1)); - d_managed_in = (unsigned char*)volk_malloc(d_veclen*d_rate*sizeof(unsigned char), - volk_get_alignment()); - d_managed_in_size = d_veclen * d_rate; - if(d_managed_in == NULL) { +namespace fec { +namespace code { + +generic_decoder::sptr cc_decoder::make(int frame_size, + int k, + int rate, + std::vector<int> polys, + int start_state, + int end_state, + cc_mode_t mode, + bool padded) +{ + return generic_decoder::sptr(new cc_decoder_impl( + frame_size, k, rate, polys, start_state, end_state, mode, padded)); +} + +cc_decoder_impl::cc_decoder_impl(int frame_size, + int k, + int rate, + std::vector<int> polys, + int start_state, + int end_state, + cc_mode_t mode, + bool padded) + : generic_decoder("cc_decoder"), + d_k(k), + d_rate(rate), + d_polys(polys), + d_mode(mode), + d_padding(0), + d_start_state_chaining(start_state), + d_start_state_nonchaining(start_state), + d_end_state_nonchaining(end_state) +{ + // Set max frame size here; all buffers and settings will be + // based on this value. + d_max_frame_size = frame_size; + d_frame_size = frame_size; + + // set up a padding factor. If padding, the encoded frame was exteded + // by this many bits to fit into a full byte. + if (padded && (mode == CC_TERMINATED)) { + d_padding = static_cast<int>(8.0f * ceilf(d_rate * (d_k - 1) / 8.0f) - + (d_rate * (d_k - 1))); + } + + d_vp = new struct v; + + d_numstates = 1 << (d_k - 1); + + d_decision_t_size = d_numstates / 8; // packed bit array + + d_managed_in_size = 0; + switch (d_mode) { + case (CC_TAILBITING): + d_end_state = &d_end_state_chaining; + d_veclen = d_frame_size + (6 * (d_k - 1)); + d_managed_in = (unsigned char*)volk_malloc( + d_veclen * d_rate * sizeof(unsigned char), volk_get_alignment()); + d_managed_in_size = d_veclen * d_rate; + if (d_managed_in == NULL) { throw std::runtime_error("cc_decoder: bad alloc for d_managed_in\n"); - } - break; - - case(CC_TRUNCATED): - d_veclen = d_frame_size; - d_end_state = &d_end_state_chaining; - break; - - case(CC_TERMINATED): - d_veclen = d_frame_size + d_k - 1; - d_end_state = (end_state == -1) ? &d_end_state_chaining : &d_end_state_nonchaining; - break; - - case(CC_STREAMING): - d_veclen = d_frame_size + d_k - 1; - d_end_state = &d_end_state_chaining; - break; - - default: - throw std::runtime_error("cc_decoder: mode not recognized"); - } - - d_vp->metrics = (unsigned char*)volk_malloc(2*sizeof(unsigned char)*d_numstates, - volk_get_alignment()); - if(d_vp->metrics == NULL) { - throw std::runtime_error("bad alloc for d_vp->metrics!\n"); } + break; - d_vp->metrics1.t = d_vp->metrics; - d_vp->metrics2.t = d_vp->metrics + d_numstates; + case (CC_TRUNCATED): + d_veclen = d_frame_size; + d_end_state = &d_end_state_chaining; + break; - d_vp->decisions = (unsigned char*)volk_malloc(sizeof(unsigned char)*d_veclen*d_decision_t_size, - volk_get_alignment()); - if(d_vp->decisions == NULL) { - throw std::runtime_error("bad alloc for d_vp->decisions!\n"); - } + case (CC_TERMINATED): + d_veclen = d_frame_size + d_k - 1; + d_end_state = + (end_state == -1) ? &d_end_state_chaining : &d_end_state_nonchaining; + break; - Branchtab = (unsigned char*)volk_malloc(sizeof(unsigned char)*d_numstates/2*rate, - volk_get_alignment()); - if(Branchtab == NULL) { - throw std::runtime_error("bad alloc for d_vp->decisions!\n"); - } - - create_viterbi(); - - if(d_k-1<8) { - d_ADDSHIFT = (8-(d_k-1)); - d_SUBSHIFT = 0; - } - else if(d_k-1>8) { - d_ADDSHIFT = 0; - d_SUBSHIFT = ((d_k-1)-8); - } - else { - d_ADDSHIFT = 0; - d_SUBSHIFT = 0; - } + case (CC_STREAMING): + d_veclen = d_frame_size + d_k - 1; + d_end_state = &d_end_state_chaining; + break; - std::map<std::string, conv_kernel> yp_kernel = boost::assign::map_list_of("k=7r=2", volk_8u_x4_conv_k7_r2_8u); + default: + throw std::runtime_error("cc_decoder: mode not recognized"); + } - std::string k_ = "k="; - std::string r_ = "r="; - - std::ostringstream kerneltype; - kerneltype << k_ << d_k << r_ << d_rate; - - d_kernel = yp_kernel[kerneltype.str()]; - if (d_kernel == NULL) { - throw std::runtime_error("cc_decoder: parameters not supported"); - } - } - - cc_decoder_impl::~cc_decoder_impl() - { - volk_free(d_vp->decisions); - volk_free(Branchtab); - volk_free(d_vp->metrics); - - delete d_vp; - - if(d_mode == CC_TAILBITING) { - volk_free(d_managed_in); - } - } - - int - cc_decoder_impl::get_output_size() - { - //unpacked bits - return d_frame_size; - } - - int - cc_decoder_impl::get_input_size() - { - if(d_mode == CC_TERMINATED) { - return d_rate * (d_frame_size + d_k - 1) + d_padding; - } - else { - return d_rate * d_frame_size; - } - } - - int - cc_decoder_impl::get_input_item_size() - { - return 1; - } - - int - cc_decoder_impl::get_history() - { - if(d_mode == CC_STREAMING) { - return d_rate * (d_k - 1); - } - else { - return 0; - } - } - - float - cc_decoder_impl::get_shift() - { - return 128.0; - } - - const char* - cc_decoder_impl::get_input_conversion() - { - return "uchar"; - } - - void - cc_decoder_impl::create_viterbi() - { - int state; - unsigned int i; - partab_init(); - for(state = 0; state < d_numstates/2; state++) { - for(i = 0; i < d_rate; i++) { - Branchtab[i*d_numstates/2+state] = (d_polys[i] < 0) ^ parity((2*state) & abs(d_polys[i])) ? 255 : 0; - } - } - - switch(d_mode) { - case(CC_STREAMING): - d_start_state = &d_start_state_chaining; - init_viterbi_unbiased(d_vp); - break; - - case(CC_TAILBITING): - d_start_state = &d_start_state_nonchaining; - init_viterbi_unbiased(d_vp); - break; - - case(CC_TRUNCATED): - case(CC_TERMINATED): - d_start_state = &d_start_state_nonchaining; - init_viterbi(d_vp, *d_start_state); - break; - - default: - throw std::runtime_error("cc_decoder: mode not recognized"); + d_vp->metrics = (unsigned char*)volk_malloc(2 * sizeof(unsigned char) * d_numstates, + volk_get_alignment()); + if (d_vp->metrics == NULL) { + throw std::runtime_error("bad alloc for d_vp->metrics!\n"); + } + + d_vp->metrics1.t = d_vp->metrics; + d_vp->metrics2.t = d_vp->metrics + d_numstates; + + d_vp->decisions = (unsigned char*)volk_malloc( + sizeof(unsigned char) * d_veclen * d_decision_t_size, volk_get_alignment()); + if (d_vp->decisions == NULL) { + throw std::runtime_error("bad alloc for d_vp->decisions!\n"); + } + + Branchtab = (unsigned char*)volk_malloc( + sizeof(unsigned char) * d_numstates / 2 * rate, volk_get_alignment()); + if (Branchtab == NULL) { + throw std::runtime_error("bad alloc for d_vp->decisions!\n"); + } + + create_viterbi(); + + if (d_k - 1 < 8) { + d_ADDSHIFT = (8 - (d_k - 1)); + d_SUBSHIFT = 0; + } else if (d_k - 1 > 8) { + d_ADDSHIFT = 0; + d_SUBSHIFT = ((d_k - 1) - 8); + } else { + d_ADDSHIFT = 0; + d_SUBSHIFT = 0; + } + + std::map<std::string, conv_kernel> yp_kernel = + boost::assign::map_list_of("k=7r=2", volk_8u_x4_conv_k7_r2_8u); + + std::string k_ = "k="; + std::string r_ = "r="; + + std::ostringstream kerneltype; + kerneltype << k_ << d_k << r_ << d_rate; + + d_kernel = yp_kernel[kerneltype.str()]; + if (d_kernel == NULL) { + throw std::runtime_error("cc_decoder: parameters not supported"); + } +} + +cc_decoder_impl::~cc_decoder_impl() +{ + volk_free(d_vp->decisions); + volk_free(Branchtab); + volk_free(d_vp->metrics); + + delete d_vp; + + if (d_mode == CC_TAILBITING) { + volk_free(d_managed_in); + } +} + +int cc_decoder_impl::get_output_size() +{ + // unpacked bits + return d_frame_size; +} + +int cc_decoder_impl::get_input_size() +{ + if (d_mode == CC_TERMINATED) { + return d_rate * (d_frame_size + d_k - 1) + d_padding; + } else { + return d_rate * d_frame_size; + } +} + +int cc_decoder_impl::get_input_item_size() { return 1; } + +int cc_decoder_impl::get_history() +{ + if (d_mode == CC_STREAMING) { + return d_rate * (d_k - 1); + } else { + return 0; + } +} + +float cc_decoder_impl::get_shift() { return 128.0; } + +const char* cc_decoder_impl::get_input_conversion() { return "uchar"; } + +void cc_decoder_impl::create_viterbi() +{ + int state; + unsigned int i; + partab_init(); + for (state = 0; state < d_numstates / 2; state++) { + for (i = 0; i < d_rate; i++) { + Branchtab[i * d_numstates / 2 + state] = + (d_polys[i] < 0) ^ parity((2 * state) & abs(d_polys[i])) ? 255 : 0; } - - return; - } - - int - cc_decoder_impl::parity(int x) - { - x ^= (x >> 16); - x ^= (x >> 8); - return parityb(x); - } - - int - cc_decoder_impl::parityb(unsigned char x) - { - return Partab[x]; - } - - void - cc_decoder_impl::partab_init(void) - { - int i,cnt,ti; - - /* Initialize parity lookup table */ - for(i=0;i<256;i++){ - cnt = 0; - ti = i; - while(ti){ - if(ti & 1) - cnt++; + } + + switch (d_mode) { + case (CC_STREAMING): + d_start_state = &d_start_state_chaining; + init_viterbi_unbiased(d_vp); + break; + + case (CC_TAILBITING): + d_start_state = &d_start_state_nonchaining; + init_viterbi_unbiased(d_vp); + break; + + case (CC_TRUNCATED): + case (CC_TERMINATED): + d_start_state = &d_start_state_nonchaining; + init_viterbi(d_vp, *d_start_state); + break; + + default: + throw std::runtime_error("cc_decoder: mode not recognized"); + } + + return; +} + +int cc_decoder_impl::parity(int x) +{ + x ^= (x >> 16); + x ^= (x >> 8); + return parityb(x); +} + +int cc_decoder_impl::parityb(unsigned char x) { return Partab[x]; } + +void cc_decoder_impl::partab_init(void) +{ + int i, cnt, ti; + + /* Initialize parity lookup table */ + for (i = 0; i < 256; i++) { + cnt = 0; + ti = i; + while (ti) { + if (ti & 1) + cnt++; ti >>= 1; - } - Partab[i] = cnt & 1; } - } - - int - cc_decoder_impl::init_viterbi(struct v* vp, int starting_state) - { - int i; - - if(vp == NULL) - return -1; - for(i = 0; i < d_numstates; i++) { - vp->metrics1.t[i] = 63; - } - - vp->old_metrics = vp->metrics1; - vp->new_metrics = vp->metrics2; - vp->old_metrics.t[starting_state & (d_numstates-1)] = 0; /* Bias known start state */ - return 0; - } - - int - cc_decoder_impl::init_viterbi_unbiased(struct v* vp) - { - int i; - - if(vp == NULL) - return -1; - for(i=0;i<d_numstates;i++) - vp->metrics1.t[i] = 31; - - vp->old_metrics = vp->metrics1; - vp->new_metrics = vp->metrics2; - //no bias step - return 0; - } - - int - cc_decoder_impl::find_endstate() - { - unsigned char* met = ((d_k + d_veclen)%2 == 0)? d_vp->new_metrics.t : d_vp->old_metrics.t; - - unsigned char min = met[0]; - int state = 0; - for(int i = 1; i < d_numstates; ++i) { - if(met[i] < min) { + Partab[i] = cnt & 1; + } +} + +int cc_decoder_impl::init_viterbi(struct v* vp, int starting_state) +{ + int i; + + if (vp == NULL) + return -1; + for (i = 0; i < d_numstates; i++) { + vp->metrics1.t[i] = 63; + } + + vp->old_metrics = vp->metrics1; + vp->new_metrics = vp->metrics2; + vp->old_metrics.t[starting_state & (d_numstates - 1)] = + 0; /* Bias known start state */ + return 0; +} + +int cc_decoder_impl::init_viterbi_unbiased(struct v* vp) +{ + int i; + + if (vp == NULL) + return -1; + for (i = 0; i < d_numstates; i++) + vp->metrics1.t[i] = 31; + + vp->old_metrics = vp->metrics1; + vp->new_metrics = vp->metrics2; + // no bias step + return 0; +} + +int cc_decoder_impl::find_endstate() +{ + unsigned char* met = + ((d_k + d_veclen) % 2 == 0) ? d_vp->new_metrics.t : d_vp->old_metrics.t; + + unsigned char min = met[0]; + int state = 0; + for (int i = 1; i < d_numstates; ++i) { + if (met[i] < min) { min = met[i]; state = i; - } - - - } - //printf("min %d\n", state); - return state; - } - - int - cc_decoder_impl::update_viterbi_blk(unsigned char* syms, int nbits) - { - unsigned char *d; - - d = d_vp->decisions; - - memset(d,0,d_decision_t_size * nbits); - - d_kernel(d_vp->new_metrics.t, d_vp->old_metrics.t, syms, - d, nbits - (d_k - 1), d_k - 1, Branchtab); - - return 0; - } - - int - cc_decoder_impl::chainback_viterbi(unsigned char* data, - unsigned int nbits, - unsigned int endstate, - unsigned int tailsize) - { - unsigned char *d; - - /* ADDSHIFT and SUBSHIFT make sure that the thing returned is a byte. */ - d = d_vp->decisions; - /* Make room beyond the end of the encoder register so we can - * accumulate a full byte of decoded data - */ - - endstate = (endstate%d_numstates) << d_ADDSHIFT; - - /* The store into data[] only needs to be done every 8 bits. - * But this avoids a conditional branch, and the writes will - * combine in the cache anyway - */ - - d += tailsize * d_decision_t_size ; /* Look past tail */ - int retval; - int dif = tailsize - (d_k - 1); - decision_t dec; - while(nbits-- > d_frame_size - (d_k - 1)) { - int k; - dec.t = &d[nbits * d_decision_t_size]; - k = (dec.w[(endstate>>d_ADDSHIFT)/32] >> ((endstate>>d_ADDSHIFT)%32)) & 1; - - endstate = (endstate >> 1) | (k << (d_k-2+d_ADDSHIFT)); - data[((nbits+dif)%d_frame_size)] = k; - - retval = endstate; - } - nbits += 1; - - while(nbits-- != 0) { - int k; - - dec.t = &d[nbits * d_decision_t_size]; - - k = (dec.w[(endstate>>d_ADDSHIFT)/32] >> ((endstate>>d_ADDSHIFT)%32)) & 1; - - endstate = (endstate >> 1) | (k << (d_k-2+d_ADDSHIFT)); - data[((nbits+dif)%d_frame_size)] = k; } - - return retval >> d_ADDSHIFT; - } - - bool - cc_decoder_impl::set_frame_size(unsigned int frame_size) - { - bool ret = true; - if(frame_size > d_max_frame_size) { - GR_LOG_INFO(d_logger, boost::format("cc_decoder: tried to set frame to %1%; max possible is %2%") \ - % frame_size % d_max_frame_size); - frame_size = d_max_frame_size; - ret = false; + } + // printf("min %d\n", state); + return state; +} + +int cc_decoder_impl::update_viterbi_blk(unsigned char* syms, int nbits) +{ + unsigned char* d; + + d = d_vp->decisions; + + memset(d, 0, d_decision_t_size * nbits); + + d_kernel(d_vp->new_metrics.t, + d_vp->old_metrics.t, + syms, + d, + nbits - (d_k - 1), + d_k - 1, + Branchtab); + + return 0; +} + +int cc_decoder_impl::chainback_viterbi(unsigned char* data, + unsigned int nbits, + unsigned int endstate, + unsigned int tailsize) +{ + unsigned char* d; + + /* ADDSHIFT and SUBSHIFT make sure that the thing returned is a byte. */ + d = d_vp->decisions; + /* Make room beyond the end of the encoder register so we can + * accumulate a full byte of decoded data + */ + + endstate = (endstate % d_numstates) << d_ADDSHIFT; + + /* The store into data[] only needs to be done every 8 bits. + * But this avoids a conditional branch, and the writes will + * combine in the cache anyway + */ + + d += tailsize * d_decision_t_size; /* Look past tail */ + int retval; + int dif = tailsize - (d_k - 1); + decision_t dec; + while (nbits-- > d_frame_size - (d_k - 1)) { + int k; + dec.t = &d[nbits * d_decision_t_size]; + k = (dec.w[(endstate >> d_ADDSHIFT) / 32] >> ((endstate >> d_ADDSHIFT) % 32)) & 1; + + endstate = (endstate >> 1) | (k << (d_k - 2 + d_ADDSHIFT)); + data[((nbits + dif) % d_frame_size)] = k; + + retval = endstate; + } + nbits += 1; + + while (nbits-- != 0) { + int k; + + dec.t = &d[nbits * d_decision_t_size]; + + k = (dec.w[(endstate >> d_ADDSHIFT) / 32] >> ((endstate >> d_ADDSHIFT) % 32)) & 1; + + endstate = (endstate >> 1) | (k << (d_k - 2 + d_ADDSHIFT)); + data[((nbits + dif) % d_frame_size)] = k; + } + + return retval >> d_ADDSHIFT; +} + +bool cc_decoder_impl::set_frame_size(unsigned int frame_size) +{ + bool ret = true; + if (frame_size > d_max_frame_size) { + GR_LOG_INFO( + d_logger, + boost::format("cc_decoder: tried to set frame to %1%; max possible is %2%") % + frame_size % d_max_frame_size); + frame_size = d_max_frame_size; + ret = false; + } + + d_frame_size = frame_size; + + switch (d_mode) { + case (CC_TAILBITING): + d_veclen = d_frame_size + (6 * (d_k - 1)); + if (d_veclen * d_rate > d_managed_in_size) { + throw std::runtime_error( + "cc_decoder: attempt to resize beyond d_managed_in buffer size!\n"); } - - d_frame_size = frame_size; - - switch(d_mode) { - case(CC_TAILBITING): - d_veclen = d_frame_size + (6 * (d_k - 1)); - if(d_veclen * d_rate > d_managed_in_size) { - throw std::runtime_error("cc_decoder: attempt to resize beyond d_managed_in buffer size!\n"); - } - break; - - case(CC_TRUNCATED): - d_veclen = d_frame_size; - break; - - case(CC_STREAMING): - d_veclen = d_frame_size + d_k - 1; - break; - - case(CC_TERMINATED): - // If the input is being padded out to a byte, we know the - // real frame size is without the padding. - d_frame_size -= d_padding * d_rate; - d_veclen = d_frame_size + d_k - 1; - break; - - default: - throw std::runtime_error("cc_decoder: mode not recognized"); - } - - return ret; - } - - double - cc_decoder_impl::rate() - { - return 1.0/static_cast<double>(d_rate); - } - - void - cc_decoder_impl::generic_work(void *inbuffer, void *outbuffer) - { - const unsigned char *in = (const unsigned char *) inbuffer; - unsigned char *out = (unsigned char *) outbuffer; - - switch(d_mode) { - - case(CC_TAILBITING): - memcpy(d_managed_in, in, d_frame_size * d_rate * sizeof(unsigned char)); - memcpy(d_managed_in + d_frame_size * d_rate * sizeof(unsigned char), in, - (d_veclen - d_frame_size) * d_rate * sizeof(unsigned char)); - update_viterbi_blk(d_managed_in, d_veclen); - d_end_state_chaining = find_endstate(); - chainback_viterbi(&out[0], d_frame_size, *d_end_state, d_veclen - d_frame_size); - init_viterbi_unbiased(d_vp); - break; - - - case(CC_TRUNCATED): - update_viterbi_blk((unsigned char*)(&in[0]), d_veclen); - d_end_state_chaining = find_endstate(); - for(unsigned int i = 0; i < d_k-1; ++i) { + break; + + case (CC_TRUNCATED): + d_veclen = d_frame_size; + break; + + case (CC_STREAMING): + d_veclen = d_frame_size + d_k - 1; + break; + + case (CC_TERMINATED): + // If the input is being padded out to a byte, we know the + // real frame size is without the padding. + d_frame_size -= d_padding * d_rate; + d_veclen = d_frame_size + d_k - 1; + break; + + default: + throw std::runtime_error("cc_decoder: mode not recognized"); + } + + return ret; +} + +double cc_decoder_impl::rate() { return 1.0 / static_cast<double>(d_rate); } + +void cc_decoder_impl::generic_work(void* inbuffer, void* outbuffer) +{ + const unsigned char* in = (const unsigned char*)inbuffer; + unsigned char* out = (unsigned char*)outbuffer; + + switch (d_mode) { + + case (CC_TAILBITING): + memcpy(d_managed_in, in, d_frame_size * d_rate * sizeof(unsigned char)); + memcpy(d_managed_in + d_frame_size * d_rate * sizeof(unsigned char), + in, + (d_veclen - d_frame_size) * d_rate * sizeof(unsigned char)); + update_viterbi_blk(d_managed_in, d_veclen); + d_end_state_chaining = find_endstate(); + chainback_viterbi(&out[0], d_frame_size, *d_end_state, d_veclen - d_frame_size); + init_viterbi_unbiased(d_vp); + break; + + + case (CC_TRUNCATED): + update_viterbi_blk((unsigned char*)(&in[0]), d_veclen); + d_end_state_chaining = find_endstate(); + for (unsigned int i = 0; i < d_k - 1; ++i) { out[d_veclen - 1 - i] = ((*d_end_state) >> i) & 1; - } - d_start_state_chaining = chainback_viterbi(&out[0], d_frame_size - (d_k - 1), - *d_end_state, d_k - 1); - init_viterbi(d_vp, *d_start_state); - break; - - case(CC_STREAMING): - case(CC_TERMINATED): - update_viterbi_blk((unsigned char*)(&in[0]), d_veclen); - d_end_state_chaining = find_endstate(); - d_start_state_chaining = chainback_viterbi(&out[0], d_frame_size, *d_end_state, - d_veclen - d_frame_size); - - init_viterbi(d_vp, *d_start_state); - break; - - default: - throw std::runtime_error("cc_decoder: mode not recognized"); } - } - - } /* namespace code */ - } /* namespace fec */ + d_start_state_chaining = + chainback_viterbi(&out[0], d_frame_size - (d_k - 1), *d_end_state, d_k - 1); + init_viterbi(d_vp, *d_start_state); + break; + + case (CC_STREAMING): + case (CC_TERMINATED): + update_viterbi_blk((unsigned char*)(&in[0]), d_veclen); + d_end_state_chaining = find_endstate(); + d_start_state_chaining = chainback_viterbi( + &out[0], d_frame_size, *d_end_state, d_veclen - d_frame_size); + + init_viterbi(d_vp, *d_start_state); + break; + + default: + throw std::runtime_error("cc_decoder: mode not recognized"); + } +} + +} /* namespace code */ +} /* namespace fec */ } /* namespace gr */ |