public SideInfo() { TT = new GrInfo[2, 2]; for (int i1 = 0; i1 < 2; i1++) { for (int i2 = 0; i2 < 2; i2++) { TT[i1, i2] = new GrInfo(); } } Scfsi = new int[2, 4]; }
int InnerLoop(double[] abs_xr, int[] abs_ix, int max_bits, ref GrInfo cod_info) { int bits; cod_info.QuantizerStepSize -= 1.0; do { do { cod_info.QuantizerStepSize += 1.0; tjBitOverflow2 = false; QuantizeTj(abs_xr, abs_ix, ref cod_info); }while (tjBitOverflow2); bits = CountBits(abs_ix, ref cod_info); }while (bits > max_bits); return(bits); }
void CalcNoise(double[] xr, int[] ix, ref GrInfo cod_info, double[,] xfsf) { int start, end, l, i; int sfb; double sum, step, bw; step = Math.Pow(2.0, (cod_info.QuantizerStepSize) * 0.25); for (sfb = 0; sfb < cod_info.SfbLmax; sfb++) { start = scalefac_band_long[sfb]; end = scalefac_band_long[sfb + 1]; bw = end - start; for (sum = 0.0, l = start; l < end; l++) { double temp; temp = xr[l] - noisePowTab[ix[l]] * step; sum += temp * temp; } xfsf[0, sfb] = sum / bw; } for (i = 0; i < 3; i++) { for (sfb = cod_info.SfbSmax; sfb < 12; sfb++) { start = scalefac_band_short[sfb]; end = scalefac_band_short[sfb + 1]; bw = end - start; for (sum = 0.0, l = start; l < end; l++) { double temp; temp = xr[l * 3 + i] - noisePowTab[ix[l * 3 + i]] * step; sum += temp * temp; } xfsf[i + 1, sfb] = sum / bw; } } }
private bool LoopBreak(int[][][] scalefact_l, int[][][][] scalefact_s, ref GrInfo cod_info, int gr, int ch) { int i, sfb; for (sfb = 0; sfb < cod_info.SfbLmax; sfb++) { if (scalefact_l[ch][gr][sfb] == 0) { return(false); } } for (sfb = cod_info.SfbSmax; sfb < 12; sfb++) { for (i = 0; i < 3; i++) { if (scalefact_s[ch][gr][sfb][i] == 0) { return(false); } } } return(true); }
public void ResvAdjust(ref FrameParams fr_ps, ref GrInfo gi, ref SideInfo l3_side, int mean_bits) { ResvSize += (mean_bits / fr_ps.Chn) - gi.Part23Length; }
private int CountBits(int[] abs_ix, ref GrInfo cod_info) { int zero_region = 576; int bigv_region = 576; int bits = 0; int sum0 = 0; int sum1 = 0; if (cod_info.WindowSwitchingFlag == 0 || (cod_info.BlockType != 2)) { int p; for (; zero_region > 1; zero_region -= 2) { if (abs_ix[zero_region - 1] != 0) { break; } else if (abs_ix[zero_region - 2] != 0) { break; } } for (bigv_region = zero_region; bigv_region > 3; bigv_region -= 4) { if (abs_ix[bigv_region - 1] > 1) { break; } else if (abs_ix[bigv_region - 2] > 1) { break; } else if (abs_ix[bigv_region - 3] > 1) { break; } else if (abs_ix[bigv_region - 4] > 1) { break; } p = 0; if (abs_ix[bigv_region - 1] != 0) { bits++; p |= 8; } if (abs_ix[bigv_region - 2] != 0) { bits++; p |= 4; } if (abs_ix[bigv_region - 3] != 0) { bits++; p |= 2; } if (abs_ix[bigv_region - 4] != 0) { bits++; p |= 1; } sum0 += huf.HT[32].Hlen[p]; sum1 += huf.HT[33].Hlen[p]; } } cod_info.Count1 = (zero_region - bigv_region) / 4; cod_info.BigValues = bigv_region / 2; if (sum0 < sum1) { bits += sum0; cod_info.Count1tableSelect = 0; } else { bits += sum1; cod_info.Count1tableSelect = 1; } if (bigv_region != 0) { if (cod_info.WindowSwitchingFlag != 0) { if (cod_info.MixedBlockFlag != 0 || (cod_info.BlockType != 2)) { cod_info.Region0Count = 7; cod_info.Region1Count = 13; cod_info.Address1 = scalefac_band_long[cod_info.Region0Count + 1]; } else { cod_info.Region0Count = 8; cod_info.Region1Count = 36; cod_info.Address1 = 36; } cod_info.Address2 = bigv_region; cod_info.Address3 = 0; } else { int index0, index1; int scfb_anz = 0; while (scalefac_band_long[scfb_anz] < bigv_region) { scfb_anz++; } index0 = (cod_info.Region0Count = subdv_table[scfb_anz][0]) + 1; index1 = (cod_info.Region1Count = subdv_table[scfb_anz][1]) + 1; cod_info.Address1 = scalefac_band_long[index0]; cod_info.Address2 = scalefac_band_long[index0 + index1]; cod_info.Address3 = bigv_region; } } else { cod_info.Region0Count = 0; cod_info.Region1Count = 0; } cod_info.TableSelect[0] = 0; cod_info.TableSelect[1] = 0; cod_info.TableSelect[2] = 0; if (cod_info.WindowSwitchingFlag != 0 && (cod_info.BlockType == 2)) { int sfb, window, line, start, end; int max1, max2, pmax, tMax; int x, y; max1 = max2 = 0; for (sfb = 0; sfb < 13; sfb++) { start = scalefac_band_short[sfb]; end = scalefac_band_short[sfb + 1]; if (start < 12) { pmax = max1; } else { pmax = max2; } tMax = pmax; for (window = 0; window < 3; window++) { for (line = start; line < end; line += 2) { x = abs_ix[window + line * 3]; y = abs_ix[window + (line + 1) * 3]; if (x > tMax) { tMax = x; } if (y > tMax) { tMax = y; } } } if (start < 12) { max1 = tMax; } else { max2 = tMax; } } cod_info.TableSelect[0] = ChooseTable(max1); cod_info.TableSelect[1] = ChooseTable(max2); if (cod_info.MixedBlockFlag != 0) { if (cod_info.TableSelect[0] != 0) { bits += CountBitTj(abs_ix, 0, cod_info.Address1, cod_info.TableSelect[0]); } sfb = 2; } else { sfb = 0; } for (; sfb < 13; sfb++) { int tableindex; int idx; start = scalefac_band_short[sfb]; end = scalefac_band_short[sfb + 1]; if (start < 12) { tableindex = cod_info.TableSelect[0]; } else { tableindex = cod_info.TableSelect[1]; } if (tableindex != 0) { for (window = 0; window < 3; window++) { for (line = start; line < end; line += 2) { int x1 = abs_ix[window + line * 3]; int y1 = abs_ix[window + (line + 1) * 3]; if (tableindex > 15) { if (x1 > 14) { x1 = 15; bits += huf.HT[tableindex].LinBits; } if (y1 > 14) { y1 = 15; bits += huf.HT[tableindex].LinBits; } } idx = (x1 * huf.HT[tableindex].Ylen) + y1; bits += huf.HT[tableindex].Hlen[idx]; if (x1 != 0) { bits++; } if (y1 != 0) { bits++; } } } } } } else { if (cod_info.Address1 > 0) { if ((cod_info.TableSelect[0] = NewChooseTableTj(abs_ix, 0, cod_info.Address1)) > 0) { bits += CountBitTj(abs_ix, 0, cod_info.Address1, cod_info.TableSelect[0]); } } if (cod_info.Address2 > cod_info.Address1) { if ((cod_info.TableSelect[1] = NewChooseTableTj(abs_ix, cod_info.Address1, cod_info.Address2)) > 0) { bits += CountBitTj(abs_ix, cod_info.Address1, cod_info.Address2, cod_info.TableSelect[1]); } } if (cod_info.BigValues * 2 > cod_info.Address2) { if ((cod_info.TableSelect[2] = NewChooseTableTj(abs_ix, cod_info.Address2, cod_info.BigValues * 2)) > 0) { bits += CountBitTj(abs_ix, cod_info.Address2, cod_info.Address3, cod_info.TableSelect[2]); } } } return(bits); }
private int BinSearchStepSize(int desired_rate, double start, int[] abs_ix, double[] abs_xr, ref GrInfo cod_info) { double top, bot, next, last; int bit; top = start; bot = 200; next = start; do { last = next; next = (int)((top + bot) / 2.0); cod_info.QuantizerStepSize = next; tjBitOverflow1 = false; QuantizeTj(abs_xr, abs_ix, ref cod_info); if (tjBitOverflow1) { bit = 100000; } else { bit = CountBits(abs_ix, ref cod_info); } if (bit > desired_rate) { top = next; } else { bot = next; } }while ((bit != desired_rate) && (Math.Abs(last - next) > 1.0)); return((int)next); }
private int ScaleBitcount(int[][][] scalefact_l, int[][][][] scalefact_s, ref GrInfo cod_info, int gr, int ch) { int i, k, sfb, max_slen1 = 0, max_slen2 = 0, ep = 2; int[] slen1 = { 0, 0, 0, 0, 3, 1, 1, 1, 2, 2, 2, 3, 3, 3, 4, 4 }; int[] slen2 = { 0, 1, 2, 3, 0, 1, 2, 3, 1, 2, 3, 1, 2, 3, 2, 3 }; int[] pow2 = { 1, 2, 4, 8, 16 }; if (cod_info.WindowSwitchingFlag != 0 && cod_info.BlockType == 2) { if (cod_info.MixedBlockFlag == 0) { for (i = 0; i < 3; i++) { for (sfb = 0; sfb < 6; sfb++) { if (scalefact_s[ch][gr][sfb][i] > max_slen1) { max_slen1 = scalefact_s[ch][gr][sfb][i]; } } for (sfb = 6; sfb < 12; sfb++) { if (scalefact_s[ch][gr][sfb][i] > max_slen2) { max_slen2 = scalefact_s[ch][gr][sfb][i]; } } } } else { for (sfb = 0; sfb < 8; sfb++) { if (scalefact_l[ch][gr][sfb] > max_slen1) { max_slen1 = scalefact_l[ch][gr][sfb]; } } for (i = 0; i < 3; i++) { for (sfb = 3; sfb < 6; sfb++) { if (scalefact_s[ch][gr][sfb][i] > max_slen1) { max_slen1 = scalefact_s[ch][gr][sfb][i]; } } for (sfb = 6; sfb < 12; sfb++) { if (scalefact_s[ch][gr][sfb][i] > max_slen2) { max_slen2 = scalefact_s[ch][gr][sfb][i]; } } } } } else { for (sfb = 0; sfb < 11; sfb++) { if (scalefact_l[ch][gr][sfb] > max_slen1) { max_slen1 = scalefact_l[ch][gr][sfb]; } } for (sfb = 11; sfb < 21; sfb++) { if (scalefact_l[ch][gr][sfb] > max_slen2) { max_slen2 = scalefact_l[ch][gr][sfb]; } } } for (k = 0; k < 16; k++) { if ((max_slen1 < pow2[slen1[k]]) && (max_slen2 < pow2[slen2[k]])) { ep = 0; break; } } if (ep == 0) { cod_info.ScalefacCompress = k; } return(ep); }
private void QuantizeTj(double[] abs_xr, int[] abs_ix, ref GrInfo cod_info) { int i, b, l_end, s_start; double expo, mulVal; expo = -cod_info.QuantizerStepSize * 0.25; mulVal = Math.Pow(2, expo); if (cod_info.WindowSwitchingFlag != 0 && (cod_info.BlockType == 2)) { if (cod_info.MixedBlockFlag != 0) { l_end = 18 * 2; s_start = 6 * 2; } else { l_end = 0; s_start = 0; } for (int bi = l_end; bi < (576 - l_end); bi++) { abs_ix[bi] = 0; } } else { l_end = 576; s_start = 192; } for (i = 0; i < l_end; i++) { abs_ix[i] = Nint(Math.Pow(abs_xr[i] * mulVal, 0.75) - 0.0946); if (abs_ix[i] > 8192) { tjBitOverflow1 = true; if (abs_ix[i] > 8191 + 14) { tjBitOverflow2 = true; } } } if (s_start < 192) { for (b = 0; b < 3; b++) { mulVal = Math.Pow(2.0, expo - (double)(cod_info.SubblockGain[b] * 2)); for (i = s_start; i < 192; i++) { abs_ix[i * 3 + b] = Nint(Math.Pow(abs_xr[i * 3 + b] * mulVal, 0.75) - 0.0946); if (abs_ix[i * 3 + b] > 8192) { tjBitOverflow1 = true; if (abs_ix[i * 3 + b] > 8191 + 14) { tjBitOverflow2 = true; } } } } } }
private void HuffmanCodeBits(int ch, int gr, int[] ix, ref GrInfo gi, ref FrameParams fr_ps) { int region1Start; int region2Start; int bigvalues, count1End; int v, w, x, y, bits, stuffingBits; HuffCodeTab ht; int bvbits, c1bits, cbits = 0, xbits = 0, code = 0, ext = 0, tablezeros = 0, r0 = 0, r1 = 0, r2 = 0, rt, pr; int bitsWritten = 0; bigvalues = gi.BigValues * 2; if (bigvalues != 0) { if (gi.MixedBlockFlag == 0 && gi.WindowSwitchingFlag != 0 && gi.BlockType == 2) { int sfb, window, line, start, end; region1Start = 12; region2Start = 576; for (sfb = 0; sfb < 13; sfb++) { int tableindex = 100; start = Tables.SfBandIndex[fr_ps.Header.SamplingFrequency][1][sfb]; //scalefac[sfb]; end = Tables.SfBandIndex[fr_ps.Header.SamplingFrequency][1][sfb + 1]; if (start < region1Start) { tableindex = gi.TableSelect[0]; } else { tableindex = gi.TableSelect[1]; } for (window = 0; window < 3; window++) { for (line = start; line < end; line += 2) { x = ix[line * 3 + window]; y = ix[(line + 1) * 3 + window]; bits = HuffmanCode(tableindex, x, y, ref code, ref ext, ref cbits, ref xbits); codedDataPH[ch, gr].Add(code, cbits); codedDataPH[ch, gr].Add(ext, xbits); bitsWritten += bits; } } } } else if (gi.MixedBlockFlag != 0 && gi.BlockType == 2) { int sfb, window, line, start, end, tableindex; tableindex = gi.TableSelect[0]; if (tableindex != 0) { for (int i = 0; i < 36; i += 2) { x = ix[i]; y = ix[i + 1]; bits = HuffmanCode(tableindex, x, y, ref code, ref ext, ref cbits, ref xbits); codedDataPH[ch, gr].Add(code, cbits); codedDataPH[ch, gr].Add(ext, xbits); bitsWritten += bits; } } tableindex = gi.TableSelect[1]; for (sfb = 3; sfb < 13; sfb++) { start = Tables.SfBandIndex[fr_ps.Header.SamplingFrequency][1][sfb]; end = Tables.SfBandIndex[fr_ps.Header.SamplingFrequency][1][sfb + 1]; for (window = 0; window < 3; window++) { for (line = start; line < end; line += 2) { x = ix[line * 3 + window]; y = ix[(line + 1) * 3 + window]; bits = HuffmanCode(tableindex, x, y, ref code, ref ext, ref cbits, ref xbits); codedDataPH[ch, gr].Add(code, cbits); codedDataPH[ch, gr].Add(ext, xbits); bitsWritten += bits; } } } } else { int scalefac_index = 100; if (gi.MixedBlockFlag != 0) { region1Start = 36; region2Start = 576; } else { scalefac_index = gi.Region0Count + 1; region1Start = Tables.SfBandIndex[fr_ps.Header.SamplingFrequency][0][scalefac_index]; scalefac_index += gi.Region1Count + 1; region2Start = Tables.SfBandIndex[fr_ps.Header.SamplingFrequency][0][scalefac_index]; } for (int i = 0; i < bigvalues; i += 2) { int tableindex = 100; if (i < region1Start) { tableindex = gi.TableSelect[0]; pr = 0; } else if (i < region2Start) { tableindex = gi.TableSelect[1]; pr = 1; } else { tableindex = gi.TableSelect[2]; pr = 2; } ht = huf.HT[tableindex]; x = ix[i]; y = ix[i + 1]; if (tableindex != 0) { bits = HuffmanCode(tableindex, x, y, ref code, ref ext, ref cbits, ref xbits); codedDataPH[ch, gr].Add(code, cbits); codedDataPH[ch, gr].Add(ext, xbits); rt = bits; bitsWritten += rt; switch (pr) { case 0: r0 += rt; break; case 1: r1 += rt; break; case 2: r2 += rt; break; } } else { tablezeros += 1; switch (pr) { case 0: r0 = 0; break; case 1: r1 = 0; break; case 2: r2 = 0; break; } } } } } bvbits = bitsWritten; ht = huf.HT[gi.Count1tableSelect + 32]; count1End = bigvalues + (gi.Count1 * 4); for (int i = bigvalues; i < count1End; i += 4) { v = ix[i]; w = ix[i + 1]; x = ix[i + 2]; y = ix[i + 3]; bitsWritten += HuffmanCoderCount1(ch, gr, ht, v, w, x, y); } c1bits = bitsWritten - bvbits; stuffingBits = gi.Part23Length - gi.Part2Length - bitsWritten; if (stuffingBits != 0) { int stuffingWords = stuffingBits / 32; int remainingBits = stuffingBits % 32; for (; stuffingWords > 0; stuffingWords--) { codedDataPH[ch, gr].Add(-1, 32); } if (remainingBits != 0) { codedDataPH[ch, gr].Add(-1, remainingBits); } bitsWritten += stuffingBits; } }