/* (c) Copyright 1998-2000 - Tord Jansson ====================================== This file is part of the BladeEnc MP3 Encoder, based on ISO's reference code for MPEG Layer 3 compression, and might contain smaller or larger sections that are directly taken from ISO's reference code. All changes to the ISO reference code herein are either copyrighted by Tord Jansson (tord.jansson@swipnet.se) or sublicensed to Tord Jansson by a third party. BladeEnc is free software; you can redistribute this file and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. ------------ Changes ------------ 2000-12-11 Andre Piotrowski - reformatted */ #include #include #include #include #include "common.h" #include "l3side.h" #include "loop.h" #include "huffman.h" #include "l3bitstream.h" #include "reservoir.h" /* Layer3 bit reservoir: Described in C.1.5.4.2.2 of the IS */ static int ResvSize = 0; /* in bits */ static int ResvMax = 0; /* in bits */ void fixStatic_reservoir (void) { ResvSize = 0; ResvMax = 0; } /* ResvFrameBegin: Called at the beginning of a frame. Updates the maximum size of the reservoir, and checks to make sure main_data_begin was set properly by the formatter */ void ResvFrameBegin ( frame_params *fr_ps, III_side_info_t *l3_side, int mean_bits, int frameLength ) { layer *info; int fullFrameBits, mode_gr; int expectedResvSize, resvLimit; info = fr_ps->header; mode_gr = 2; resvLimit = 4088; /* main_data_begin has 9 bits in MPEG 1 */ /* main_data_begin was set by the formatter to the expected value for the next call -- this should agree with our reservoir size */ expectedResvSize = l3_side->main_data_begin * 8; /* assert (expectedResvSize == ResvSize); */ fullFrameBits = mean_bits * mode_gr; /* determine maximum size of reservoir: ResvMax + frameLength <= 7680; limit max size to resvLimit bits because main_data_begin cannot indicate a larger value */ ResvMax = MIN(MAX (0, 7680-frameLength), resvLimit); } /* ResvMaxBits: Called at the beginning of each granule to get the max bit allowance for the current granule based on reservoir size and perceptual entropy. */ int ResvMaxBits ( frame_params *fr_ps, III_side_info_t *l3_side, double *pe, int mean_bits ) { int more_bits, max_bits, add_bits, over_bits; mean_bits /= fr_ps->stereo; max_bits = mean_bits; if (ResvMax != 0) { more_bits = (int) (*pe * 3.1 - mean_bits); if (more_bits > 100) { int frac = (ResvSize * 6) / 10; add_bits = MIN(frac, more_bits); } else add_bits = 0; over_bits = ResvSize - ((ResvMax * 8) / 10) - add_bits; if (over_bits > 0) add_bits += over_bits; max_bits += add_bits; } if (max_bits > 4095) max_bits = 4095; return max_bits; } /* ResvAdjust: Called after a granule's bit allocation. Readjusts the size of the reservoir to reflect the granule's usage. */ void ResvAdjust ( frame_params *fr_ps, gr_info *cod_info, III_side_info_t *l3_side, int mean_bits ) { ResvSize += (mean_bits / fr_ps->stereo) - cod_info->part2_3_length; } /* ResvFrameEnd: Called after all granules in a frame have been allocated. Makes sure that the reservoir size is within limits, possibly by adding stuffing bits. Note that stuffing bits are added by increasing a granule's part2_3_length. The bitstream formatter will detect this and write the appropriate stuffing bits to the bitstream. */ void ResvFrameEnd ( frame_params *fr_ps, III_side_info_t *l3_side, int mean_bits ) { layer *info; gr_info *cod_info; int mode_gr, gr, ch, stereo, ancillary_pad, stuffingBits; int over_bits; info = fr_ps->header; stereo = fr_ps->stereo; mode_gr = 2; ancillary_pad = 0; /* just in case mean_bits is odd, this is necessary... */ if ((stereo == 2) && (mean_bits & 1)) ResvSize ++; stuffingBits = ancillary_pad; if ((over_bits = ResvSize - ResvMax) > 0) { stuffingBits += over_bits; ResvSize -= over_bits; } /* we must be byte aligned */ if ((over_bits = ResvSize % 8) != 0) { stuffingBits += over_bits; ResvSize -= over_bits; } if (stuffingBits) { /* plan a: put all into the first granule This was preferred by someone designing a real-time decoder... */ cod_info = &l3_side->gr[0].ch[0].tt; if (cod_info->part2_3_length + stuffingBits < 4095) cod_info->part2_3_length += stuffingBits; else { /* plan b: distribute throughout the granules */ for (gr = 0; gr < mode_gr; gr++) { for (ch = 0; ch < stereo; ch++) { int extraBits, bitsThisGr; gr_info *cod_info = &l3_side->gr[gr].ch[ch].tt; if (stuffingBits == 0) break; extraBits = 4095 - cod_info->part2_3_length; bitsThisGr = (extraBits < stuffingBits) ? extraBits : stuffingBits; cod_info->part2_3_length += bitsThisGr; stuffingBits -= bitsThisGr; } } /* If any stuffing bits remain, we elect to spill them into ancillary data. The bitstream formatter will do this if l3side->resvDrain is set */ l3_side->resvDrain = stuffingBits; } } }