From 859bc548ce04bf27d07e922f66743c05ef4bad2e Mon Sep 17 00:00:00 2001 From: Josh Coalson Date: Tue, 27 Mar 2001 22:22:27 +0000 Subject: [PATCH] add support for new "wasted bits" field --- src/libFLAC/encoder.c | 71 +++++++++++++++++++++------ src/libFLAC/encoder_framing.c | 26 +++++++--- src/libFLAC/include/private/encoder_framing.h | 8 +-- src/libFLAC/stream_decoder.c | 15 ++++-- 4 files changed, 89 insertions(+), 31 deletions(-) diff --git a/src/libFLAC/encoder.c b/src/libFLAC/encoder.c index 37f01f5..b59f778 100644 --- a/src/libFLAC/encoder.c +++ b/src/libFLAC/encoder.c @@ -45,6 +45,8 @@ typedef struct FLAC__EncoderPrivate { int32 *integer_signal_mid_side[2]; /* the integer version of the mid-side input signal (stereo only) */ real *real_signal[FLAC__MAX_CHANNELS]; /* the floating-point version of the input signal */ real *real_signal_mid_side[2]; /* the floating-point version of the mid-side input signal (stereo only) */ + unsigned wasted_bits[FLAC__MAX_CHANNELS]; /* 'wasted_bits' value of each independent channel */ + unsigned wasted_bits_mid_side[2]; /* 'wasted_bits' value of the mid-side input signal (stereo only) */ int32 *residual_workspace[FLAC__MAX_CHANNELS][2]; /* each channel has a candidate and best workspace where the subframe residual signals will be stored */ int32 *residual_workspace_mid_side[2][2]; FLAC__Subframe subframe_workspace[FLAC__MAX_CHANNELS][2]; @@ -75,13 +77,14 @@ static bool encoder_resize_buffers_(FLAC__Encoder *encoder, unsigned new_size); static bool encoder_process_frame_(FLAC__Encoder *encoder, bool is_last_frame); static bool encoder_process_subframes_(FLAC__Encoder *encoder, bool is_last_frame); static bool encoder_process_subframe_(FLAC__Encoder *encoder, unsigned max_partition_order, bool verbatim_only, const FLAC__FrameHeader *frame_header, unsigned bits_per_sample, const int32 integer_signal[], const real real_signal[], FLAC__Subframe *subframe[2], int32 *residual[2], unsigned *best_subframe, unsigned *best_bits); -static bool encoder_add_subframe_(FLAC__Encoder *encoder, const FLAC__FrameHeader *frame_header, unsigned bits_per_sample, const FLAC__Subframe *subframe, FLAC__BitBuffer *frame); +static bool encoder_add_subframe_(FLAC__Encoder *encoder, const FLAC__FrameHeader *frame_header, unsigned bits_per_sample, unsigned wasted_bits, const FLAC__Subframe *subframe, FLAC__BitBuffer *frame); static unsigned encoder_evaluate_constant_subframe_(const int32 signal, unsigned bits_per_sample, FLAC__Subframe *subframe); static unsigned encoder_evaluate_fixed_subframe_(const int32 signal[], int32 residual[], uint32 abs_residual[], unsigned blocksize, unsigned bits_per_sample, unsigned order, unsigned rice_parameter, unsigned max_partition_order, FLAC__Subframe *subframe); static unsigned encoder_evaluate_lpc_subframe_(const int32 signal[], int32 residual[], uint32 abs_residual[], const real lp_coeff[], unsigned blocksize, unsigned bits_per_sample, unsigned order, unsigned qlp_coeff_precision, unsigned rice_parameter, unsigned max_partition_order, FLAC__Subframe *subframe); static unsigned encoder_evaluate_verbatim_subframe_(const int32 signal[], unsigned blocksize, unsigned bits_per_sample, FLAC__Subframe *subframe); static unsigned encoder_find_best_partition_order_(const int32 residual[], uint32 abs_residual[], unsigned residual_samples, unsigned predictor_order, unsigned rice_parameter, unsigned max_partition_order, unsigned *best_partition_order, unsigned best_parameters[]); static bool encoder_set_partitioned_rice_(const uint32 abs_residual[], const unsigned residual_samples, const unsigned predictor_order, const unsigned rice_parameter, const unsigned partition_order, unsigned parameters[], unsigned *bits); +static unsigned encoder_get_wasted_bits_(int32 signal[], unsigned samples); const char *FLAC__EncoderWriteStatusString[] = { "FLAC__ENCODER_WRITE_OK", @@ -689,6 +692,20 @@ bool encoder_process_subframes_(FLAC__Encoder *encoder, bool is_last_frame) assert(do_independent || do_mid_side); /* + * Check for wasted bits + */ + if(do_independent) { + for(channel = 0; channel < encoder->channels; channel++) + encoder->guts->wasted_bits[channel] = encoder_get_wasted_bits_(encoder->guts->integer_signal[channel], encoder->blocksize); + } + if(do_mid_side) { + assert(encoder->channels == 2); + + for(channel = 0; channel < 2; channel++) + encoder->guts->wasted_bits_mid_side[channel] = encoder_get_wasted_bits_(encoder->guts->integer_signal_mid_side[channel], encoder->blocksize); + } + + /* * First do a normal encoding pass of each independent channel */ if(do_independent) { @@ -752,27 +769,27 @@ bool encoder_process_subframes_(FLAC__Encoder *encoder, bool is_last_frame) switch(channel_assignment) { /* note that encoder_add_subframe_ sets the state for us in case of an error */ case FLAC__CHANNEL_ASSIGNMENT_INDEPENDENT: - if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample , &encoder->guts->subframe_workspace [0][encoder->guts->best_subframe [0]], &encoder->guts->frame)) + if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample -encoder->guts->wasted_bits [0], encoder->guts->wasted_bits [0], &encoder->guts->subframe_workspace [0][encoder->guts->best_subframe [0]], &encoder->guts->frame)) return false; - if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample , &encoder->guts->subframe_workspace [1][encoder->guts->best_subframe [1]], &encoder->guts->frame)) + if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample -encoder->guts->wasted_bits [1], encoder->guts->wasted_bits [1], &encoder->guts->subframe_workspace [1][encoder->guts->best_subframe [1]], &encoder->guts->frame)) return false; break; case FLAC__CHANNEL_ASSIGNMENT_LEFT_SIDE: - if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample , &encoder->guts->subframe_workspace [0][encoder->guts->best_subframe [0]], &encoder->guts->frame)) + if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample -encoder->guts->wasted_bits [0], encoder->guts->wasted_bits [0], &encoder->guts->subframe_workspace [0][encoder->guts->best_subframe [0]], &encoder->guts->frame)) return false; - if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample+1, &encoder->guts->subframe_workspace_mid_side[1][encoder->guts->best_subframe_mid_side[1]], &encoder->guts->frame)) + if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample+1-encoder->guts->wasted_bits_mid_side[1], encoder->guts->wasted_bits_mid_side[1], &encoder->guts->subframe_workspace_mid_side[1][encoder->guts->best_subframe_mid_side[1]], &encoder->guts->frame)) return false; break; case FLAC__CHANNEL_ASSIGNMENT_RIGHT_SIDE: - if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample+1, &encoder->guts->subframe_workspace_mid_side[1][encoder->guts->best_subframe_mid_side[1]], &encoder->guts->frame)) + if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample+1-encoder->guts->wasted_bits_mid_side[1], encoder->guts->wasted_bits_mid_side[1], &encoder->guts->subframe_workspace_mid_side[1][encoder->guts->best_subframe_mid_side[1]], &encoder->guts->frame)) return false; - if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample , &encoder->guts->subframe_workspace [1][encoder->guts->best_subframe [1]], &encoder->guts->frame)) + if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample -encoder->guts->wasted_bits [1], encoder->guts->wasted_bits [1], &encoder->guts->subframe_workspace [1][encoder->guts->best_subframe [1]], &encoder->guts->frame)) return false; break; case FLAC__CHANNEL_ASSIGNMENT_MID_SIDE: - if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample , &encoder->guts->subframe_workspace_mid_side[0][encoder->guts->best_subframe_mid_side[0]], &encoder->guts->frame)) + if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample -encoder->guts->wasted_bits_mid_side[0], encoder->guts->wasted_bits_mid_side[0], &encoder->guts->subframe_workspace_mid_side[0][encoder->guts->best_subframe_mid_side[0]], &encoder->guts->frame)) return false; - if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample+1, &encoder->guts->subframe_workspace_mid_side[1][encoder->guts->best_subframe_mid_side[1]], &encoder->guts->frame)) + if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample+1-encoder->guts->wasted_bits_mid_side[1], encoder->guts->wasted_bits_mid_side[1], &encoder->guts->subframe_workspace_mid_side[1][encoder->guts->best_subframe_mid_side[1]], &encoder->guts->frame)) return false; break; default: @@ -786,7 +803,7 @@ bool encoder_process_subframes_(FLAC__Encoder *encoder, bool is_last_frame) } for(channel = 0; channel < encoder->channels; channel++) { - if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample, &encoder->guts->subframe_workspace[channel][encoder->guts->best_subframe[channel]], &encoder->guts->frame)) { + if(!encoder_add_subframe_(encoder, &frame_header, encoder->bits_per_sample-encoder->guts->wasted_bits[channel], encoder->guts->wasted_bits[channel], &encoder->guts->subframe_workspace[channel][encoder->guts->best_subframe[channel]], &encoder->guts->frame)) { /* the above function sets the state for us in case of an error */ return false; } @@ -924,29 +941,29 @@ bool encoder_process_subframe_(FLAC__Encoder *encoder, unsigned max_partition_or return true; } -bool encoder_add_subframe_(FLAC__Encoder *encoder, const FLAC__FrameHeader *frame_header, unsigned bits_per_sample, const FLAC__Subframe *subframe, FLAC__BitBuffer *frame) +bool encoder_add_subframe_(FLAC__Encoder *encoder, const FLAC__FrameHeader *frame_header, unsigned bits_per_sample, unsigned wasted_bits, const FLAC__Subframe *subframe, FLAC__BitBuffer *frame) { switch(subframe->type) { case FLAC__SUBFRAME_TYPE_CONSTANT: - if(!FLAC__subframe_add_constant(&(subframe->data.constant), bits_per_sample, frame)) { + if(!FLAC__subframe_add_constant(&(subframe->data.constant), bits_per_sample, wasted_bits, frame)) { encoder->state = FLAC__ENCODER_FATAL_ERROR_WHILE_ENCODING; return false; } break; case FLAC__SUBFRAME_TYPE_FIXED: - if(!FLAC__subframe_add_fixed(&(subframe->data.fixed), frame_header->blocksize - subframe->data.fixed.order, bits_per_sample, frame)) { + if(!FLAC__subframe_add_fixed(&(subframe->data.fixed), frame_header->blocksize - subframe->data.fixed.order, bits_per_sample, wasted_bits, frame)) { encoder->state = FLAC__ENCODER_FATAL_ERROR_WHILE_ENCODING; return false; } break; case FLAC__SUBFRAME_TYPE_LPC: - if(!FLAC__subframe_add_lpc(&(subframe->data.lpc), frame_header->blocksize - subframe->data.lpc.order, bits_per_sample, frame)) { + if(!FLAC__subframe_add_lpc(&(subframe->data.lpc), frame_header->blocksize - subframe->data.lpc.order, bits_per_sample, wasted_bits, frame)) { encoder->state = FLAC__ENCODER_FATAL_ERROR_WHILE_ENCODING; return false; } break; case FLAC__SUBFRAME_TYPE_VERBATIM: - if(!FLAC__subframe_add_verbatim(&(subframe->data.verbatim), frame_header->blocksize, bits_per_sample, frame)) { + if(!FLAC__subframe_add_verbatim(&(subframe->data.verbatim), frame_header->blocksize, bits_per_sample, wasted_bits, frame)) { encoder->state = FLAC__ENCODER_FATAL_ERROR_WHILE_ENCODING; return false; } @@ -1152,3 +1169,27 @@ mean>>=1; *bits = bits_; return true; } + +static unsigned encoder_get_wasted_bits_(int32 signal[], unsigned samples) +{ + unsigned i, shift; + int32 x = 0; + + for(i = 0; i < samples && !(x&1); i++) + x |= signal[i]; + + if(x == 0) { + shift = 0; + } + else { + for(shift = 0; !(x&1); shift++) + x >>= 1; + } + + if(shift > 0) { + for(i = 0; i < samples; i++) + signal[i] >>= shift; + } + + return shift; +} diff --git a/src/libFLAC/encoder_framing.c b/src/libFLAC/encoder_framing.c index ec194b4..8d6b5db 100644 --- a/src/libFLAC/encoder_framing.c +++ b/src/libFLAC/encoder_framing.c @@ -230,24 +230,28 @@ bool FLAC__frame_add_header(const FLAC__FrameHeader *header, bool streamable_sub return true; } -bool FLAC__subframe_add_constant(const FLAC__Subframe_Constant *subframe, unsigned bits_per_sample, FLAC__BitBuffer *bb) +bool FLAC__subframe_add_constant(const FLAC__Subframe_Constant *subframe, unsigned bits_per_sample, unsigned wasted_bits, FLAC__BitBuffer *bb) { bool ok; ok = - FLAC__bitbuffer_write_raw_uint32(bb, FLAC__SUBFRAME_TYPE_CONSTANT_BYTE_ALIGNED_MASK, FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN) && + FLAC__bitbuffer_write_raw_uint32(bb, FLAC__SUBFRAME_TYPE_CONSTANT_BYTE_ALIGNED_MASK | (wasted_bits? 1:0), FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN) && + (wasted_bits? FLAC__bitbuffer_write_unary_unsigned(bb, wasted_bits-1) : true) && FLAC__bitbuffer_write_raw_int32(bb, subframe->value, bits_per_sample) ; return ok; } -bool FLAC__subframe_add_fixed(const FLAC__Subframe_Fixed *subframe, unsigned residual_samples, unsigned bits_per_sample, FLAC__BitBuffer *bb) +bool FLAC__subframe_add_fixed(const FLAC__Subframe_Fixed *subframe, unsigned residual_samples, unsigned bits_per_sample, unsigned wasted_bits, FLAC__BitBuffer *bb) { unsigned i; - if(!FLAC__bitbuffer_write_raw_uint32(bb, FLAC__SUBFRAME_TYPE_FIXED_BYTE_ALIGNED_MASK | (subframe->order<<1), FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN)) + if(!FLAC__bitbuffer_write_raw_uint32(bb, (FLAC__SUBFRAME_TYPE_FIXED_BYTE_ALIGNED_MASK | (subframe->order<<1)) | (wasted_bits? 1:0), FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN)) return false; + if(wasted_bits) + if(!FLAC__bitbuffer_write_unary_unsigned(bb, wasted_bits-1)) + return false; for(i = 0; i < subframe->order; i++) if(!FLAC__bitbuffer_write_raw_int32(bb, subframe->warmup[i], bits_per_sample)) @@ -267,12 +271,15 @@ bool FLAC__subframe_add_fixed(const FLAC__Subframe_Fixed *subframe, unsigned res return true; } -bool FLAC__subframe_add_lpc(const FLAC__Subframe_LPC *subframe, unsigned residual_samples, unsigned bits_per_sample, FLAC__BitBuffer *bb) +bool FLAC__subframe_add_lpc(const FLAC__Subframe_LPC *subframe, unsigned residual_samples, unsigned bits_per_sample, unsigned wasted_bits, FLAC__BitBuffer *bb) { unsigned i; - if(!FLAC__bitbuffer_write_raw_uint32(bb, FLAC__SUBFRAME_TYPE_LPC_BYTE_ALIGNED_MASK | ((subframe->order-1)<<1), FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN)) + if(!FLAC__bitbuffer_write_raw_uint32(bb, (FLAC__SUBFRAME_TYPE_LPC_BYTE_ALIGNED_MASK | ((subframe->order-1)<<1)) | (wasted_bits? 1:0), FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN)) return false; + if(wasted_bits) + if(!FLAC__bitbuffer_write_unary_unsigned(bb, wasted_bits-1)) + return false; for(i = 0; i < subframe->order; i++) if(!FLAC__bitbuffer_write_raw_int32(bb, subframe->warmup[i], bits_per_sample)) @@ -300,13 +307,16 @@ bool FLAC__subframe_add_lpc(const FLAC__Subframe_LPC *subframe, unsigned residua return true; } -bool FLAC__subframe_add_verbatim(const FLAC__Subframe_Verbatim *subframe, unsigned samples, unsigned bits_per_sample, FLAC__BitBuffer *bb) +bool FLAC__subframe_add_verbatim(const FLAC__Subframe_Verbatim *subframe, unsigned samples, unsigned bits_per_sample, unsigned wasted_bits, FLAC__BitBuffer *bb) { unsigned i; const int32 *signal = subframe->data; - if(!FLAC__bitbuffer_write_raw_uint32(bb, FLAC__SUBFRAME_TYPE_VERBATIM_BYTE_ALIGNED_MASK, FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN)) + if(!FLAC__bitbuffer_write_raw_uint32(bb, FLAC__SUBFRAME_TYPE_VERBATIM_BYTE_ALIGNED_MASK | (wasted_bits? 1:0), FLAC__SUBFRAME_ZERO_PAD_LEN + FLAC__SUBFRAME_TYPE_LEN + FLAC__SUBFRAME_WASTED_BITS_FLAG_LEN)) return false; + if(wasted_bits) + if(!FLAC__bitbuffer_write_unary_unsigned(bb, wasted_bits-1)) + return false; for(i = 0; i < samples; i++) if(!FLAC__bitbuffer_write_raw_int32(bb, signal[i], bits_per_sample)) diff --git a/src/libFLAC/include/private/encoder_framing.h b/src/libFLAC/include/private/encoder_framing.h index d9180f0..e56e693 100644 --- a/src/libFLAC/include/private/encoder_framing.h +++ b/src/libFLAC/include/private/encoder_framing.h @@ -25,9 +25,9 @@ bool FLAC__add_metadata_block(const FLAC__StreamMetaData *metadata, FLAC__BitBuffer *bb); bool FLAC__frame_add_header(const FLAC__FrameHeader *header, bool streamable_subset, bool is_last_block, FLAC__BitBuffer *bb); -bool FLAC__subframe_add_constant(const FLAC__Subframe_Constant *subframe, unsigned bits_per_sample, FLAC__BitBuffer *bb); -bool FLAC__subframe_add_fixed(const FLAC__Subframe_Fixed *subframe, unsigned residual_samples, unsigned bits_per_sample, FLAC__BitBuffer *bb); -bool FLAC__subframe_add_lpc(const FLAC__Subframe_LPC *subframe, unsigned residual_samples, unsigned bits_per_sample, FLAC__BitBuffer *bb); -bool FLAC__subframe_add_verbatim(const FLAC__Subframe_Verbatim *subframe, unsigned samples, unsigned bits_per_sample, FLAC__BitBuffer *bb); +bool FLAC__subframe_add_constant(const FLAC__Subframe_Constant *subframe, unsigned bits_per_sample, unsigned wasted_bits, FLAC__BitBuffer *bb); +bool FLAC__subframe_add_fixed(const FLAC__Subframe_Fixed *subframe, unsigned residual_samples, unsigned bits_per_sample, unsigned wasted_bits, FLAC__BitBuffer *bb); +bool FLAC__subframe_add_lpc(const FLAC__Subframe_LPC *subframe, unsigned residual_samples, unsigned bits_per_sample, unsigned wasted_bits, FLAC__BitBuffer *bb); +bool FLAC__subframe_add_verbatim(const FLAC__Subframe_Verbatim *subframe, unsigned samples, unsigned bits_per_sample, unsigned wasted_bits, FLAC__BitBuffer *bb); #endif diff --git a/src/libFLAC/stream_decoder.c b/src/libFLAC/stream_decoder.c index 84fbd64..137936d 100644 --- a/src/libFLAC/stream_decoder.c +++ b/src/libFLAC/stream_decoder.c @@ -511,7 +511,7 @@ bool stream_decoder_read_metadata_(FLAC__StreamDecoder *decoder) return false; /* the read_callback_ sets the state for us */ decoder->guts->stream_header.data.stream_info.md5sum[i] = (byte)x; } - used_bits += 128; + used_bits += i*8; /* skip the rest of the block */ assert(used_bits % 8 == 0); @@ -1040,6 +1040,9 @@ bool stream_decoder_read_subframe_(FLAC__StreamDecoder *decoder, unsigned channe else decoder->guts->frame.subframes[channel].wasted_bits = 0; + /* + * Lots of magic numbers here + */ if(x & 0x80) { decoder->guts->error_callback(decoder, FLAC__STREAM_DECODER_ERROR_LOST_SYNC, decoder->guts->client_data); decoder->state = FLAC__STREAM_DECODER_SEARCH_FOR_FRAME_SYNC; @@ -1071,8 +1074,12 @@ bool stream_decoder_read_subframe_(FLAC__StreamDecoder *decoder, unsigned channe } if(wasted_bits) { - fprintf(stderr,"@@@ CAN'T DEAL WITH WASTED BITS YET!!!\n"); + unsigned i; + x = decoder->guts->frame.subframes[channel].wasted_bits; + for(i = 0; i < decoder->guts->frame.header.blocksize; i++) + decoder->guts->output[channel][i] <<= x; } + return true; } @@ -1111,7 +1118,7 @@ bool stream_decoder_read_subframe_fixed_(FLAC__StreamDecoder *decoder, unsigned /* read warm-up samples */ for(u = 0; u < order; u++) { - if(!FLAC__bitbuffer_read_raw_int32(&decoder->guts->input, &i32, bps, read_callback_, decoder)) + if(!FLAC__bitbuffer_read_raw_int32(&decoder->guts->input, &i32, bps - decoder->guts->frame.subframes[channel].wasted_bits, read_callback_, decoder)) return false; /* the read_callback_ sets the state for us */ subframe->warmup[u] = i32; } @@ -1162,7 +1169,7 @@ bool stream_decoder_read_subframe_lpc_(FLAC__StreamDecoder *decoder, unsigned ch /* read warm-up samples */ for(u = 0; u < order; u++) { - if(!FLAC__bitbuffer_read_raw_int32(&decoder->guts->input, &i32, bps, read_callback_, decoder)) + if(!FLAC__bitbuffer_read_raw_int32(&decoder->guts->input, &i32, bps - decoder->guts->frame.subframes[channel].wasted_bits, read_callback_, decoder)) return false; /* the read_callback_ sets the state for us */ subframe->warmup[u] = i32; } -- 2.7.4