/// Reads the Huffman coded spectral samples for a given channel in a granule from a `BitStream`
/// into a provided sample buffer. Returns the number of decoded samples (the starting index of the
/// rzero partition).
///
/// Note, each spectral sample is raised to the (4/3)-rd power. This is not actually part of the
/// Huffman decoding process, but, by converting the integer sample to floating point here we don't
/// need to do pointless casting or use an extra buffer.
Reads the Huffman coded spectral samples for a given channel in a granule from a `BitStream`
into a provided sample buffer. Returns the number of decoded samples (the starting index of the
rzero partition).

Note, each spectral sample is raised to the (4/3)-rd power. This is not actually part of the
Huffman decoding process, but, by converting the integer sample to floating point here we don't
need to do pointless casting or use an extra buffer.
Reads the Huffman coded spectral samples for a given channel in a granule from a ` BitStream ` into a provided sample buffer . Returns the number of decoded samples ( the starting index of the rzero partition ) . Note each spectral sample is raised to the ( 4 / 3 ) - rd power . This is not actually part of the Huffman decoding process but by converting the integer sample to floating point here we don ' t need to do pointless casting or use an extra buffer .
pub(super) fn read_huffman_samples<B: BitStream>(
    bs: &mut B,
    channel: &GranuleChannel,
    part3_bits: u32,
    buf: &mut [f32; 576],
) -> Result<usize> {
    // If there are no Huffman code bits, zero all samples and return immediately.
    if part3_bits == 0 {
        for sample in buf.iter_mut() {
            *sample = 0.0;
        }
        return Ok(0);
    }
    // Dereference the POW43 table once per granule since there is a tiny overhead each time a
    // lazy_static is dereferenced that should be amortized over as many samples as possible.
    let pow43_table: &[f32; 8207] = &REQUANTIZE_POW43;
    let mut bits_read = 0;
    let mut i = 0;
    // There are two samples per big_value, therefore multiply big_values by 2 to get number of
    // samples in the big_value partition.
    let big_values_len = 2 * channel.big_values as usize;
    // There are up-to 3 regions in the big_value partition. Determine the sample index denoting the
    // end of each region (non-inclusive). Clamp to the end of the big_values partition.
    let regions: [usize; 3] = [
        min(channel.region1_start as usize, big_values_len),
        min(channel.region2_start as usize, big_values_len),
        min(                           576, big_values_len),
    ];
    // Iterate over each region in big_values.
    for (region_idx, region_end) in regions.iter().enumerate() {
        // Select the Huffman table based on the region's table select value.
        let table = &HUFFMAN_TABLES[channel.table_select[region_idx] as usize];
        // If the table for a region is empty, fill the region with zeros and move on to the next
        // region.
        if table.huff_table.data.is_empty() {
            while i < *region_end {
                buf[i] = 0.0;
                i += 1;
                buf[i] = 0.0;
                i += 1;
            }
            continue;
        }
        // Otherwise, read the big_values.
        while i < *region_end && bits_read < part3_bits {
            // Decode the next Huffman code.
            let (value, code_len) = bs.read_huffman(&table.huff_table, part3_bits - bits_read)?;
            bits_read += code_len;
            // In the big_values partition, each Huffman code decodes to two sample, x and y. Each
            // sample being 4-bits long.
            let mut x = (value >> 4) as usize;
            let mut y = (value & 0xf) as usize;
            // If the first sample, x, is not 0, further process it.
            if x > 0 {
                // If x is saturated (it is at the maximum possible value), and the table specifies
                // linbits, then read linbits more bits and add it to the sample.
                if x == 15 && table.linbits > 0 {
                    x += bs.read_bits_leq32(table.linbits)? as usize;
                    bits_read += table.linbits;
                }
                // The next bit is the sign bit. The value of the sample is raised to the (4/3)
                // power.
                buf[i] = if bs.read_bit()? { -pow43_table[x] } else { pow43_table[x] };
                bits_read += 1;
            }
            else {
                buf[i] = 0.0;
            }
            i += 1;
            // Likewise, repeat the previous two steps for the second sample, y.
            if y > 0 {
                if y == 15 && table.linbits > 0 {
                    y += bs.read_bits_leq32(table.linbits)? as usize;
                    bits_read += table.linbits;
                }
                buf[i] = if bs.read_bit()? { -pow43_table[y] } else { pow43_table[y] };
                bits_read += 1;
            }
            else {
                buf[i] = 0.0;
            }
            i += 1;
        }
    }
    // Select the Huffman table for the count1 partition.
    let count1_table = if channel.count1table_select {
        QUADS_HUFFMAN_TABLE_B
    }
    else {
        QUADS_HUFFMAN_TABLE_A
    };
    // Read the count1 partition.
    while i <= 572 && bits_read < part3_bits {
        // Decode the next Huffman code. Note that we allow the Huffman decoder a few extra bits in
        // case of a count1 overrun (see below for more details).
        let (value, code_len) = bs.read_huffman(
            &count1_table,
            part3_bits + count1_table.n_table_bits - bits_read
        )?;
        bits_read += code_len;
        // In the count1 partition, each Huffman code decodes to 4 samples: v, w, x, and y.
        // Each sample is 1-bit long (1 or 0).
        //
        // For each 1-bit sample, if it is 0, then then dequantized sample value is 0 as well. If
        // the 1-bit sample is 1, then read the sign bit (the next bit). The dequantized sample is
        // then either +/-1.0 depending on the sign bit.
        if value & 0x8 != 0 {
            buf[i] = if bs.read_bit()? { -1.0 } else { 1.0 };
            bits_read += 1;
        }
        else {
            buf[i] = 0.0;
        }
        i += 1;
        if value & 0x4 != 0 {
            buf[i] = if bs.read_bit()? { -1.0 } else { 1.0 };
            bits_read += 1;
        }
        else {
            buf[i] = 0.0;
        }
        i += 1;
        if value & 0x2 != 0 {
            buf[i] = if bs.read_bit()? { -1.0 } else { 1.0 };
            bits_read += 1;
        }
        else {
            buf[i] = 0.0;
        }
        i += 1;
        if value & 0x1 != 0 {
            buf[i] = if bs.read_bit()? { -1.0 } else { 1.0 };
            bits_read += 1;
        }
        else {
            buf[i] = 0.0;
        }
        i += 1;
    }
    // Ignore any extra "stuffing" bits.
    if bits_read < part3_bits {
        bs.ignore_bits(part3_bits - bits_read)?;
    }
    // Word on the street is that some encoders are poor at "stuffing" bits, resulting in part3_len
    // being ever so slightly too large. This causes the Huffman decode loop to decode the next few
    // bits as a sample. However, these bits are random data and not a real sample, so erase it!
    // The caller will be reponsible for re-aligning the bitstream reader. Candy Pop confirms this.
    else if bits_read > part3_bits {
        info!("count1 overrun, malformed bitstream");
        i -= 4;
    }
    // The final partition after the count1 partition is the rzero partition. Samples in this
    // partition are all 0.
    for j in (i..576).step_by(2) {
        buf[j+0] = 0.0;
        buf[j+1] = 0.0;
    }
    Ok(i)
}
pub ( super ) fn read_huffman_samples < B : BitStream > ( bs : & mut B , channel : & GranuleChannel , part3_bits : u32 , buf : & mut [ f32 ; 576 ] , ) -> Result < usize > { // If there are no Huffman code bits, zero all samples and return immediately. if part3_bits == 0 { for sample in buf . iter_mut ( ) { * sample = 0.0 ; } return Ok ( 0 ) ; } // Dereference the POW43 table once per granule since there is a tiny overhead each time a // lazy_static is dereferenced that should be amortized over as many samples as possible. let pow43_table : & [ f32 ; 8207 ] = & REQUANTIZE_POW43 ; let mut bits_read = 0 ; let mut i = 0 ; // There are two samples per big_value, therefore multiply big_values by 2 to get number of // samples in the big_value partition. let big_values_len = 2 * channel . big_values as usize ; // There are up-to 3 regions in the big_value partition. Determine the sample index denoting the // end of each region (non-inclusive). Clamp to the end of the big_values partition. let regions : [ usize ; 3 ] = [ min ( channel . region1_start as usize , big_values_len ) , min ( channel . region2_start as usize , big_values_len ) , min ( 576 , big_values_len ) , ] ; // Iterate over each region in big_values. for ( region_idx , region_end ) in regions . iter ( ) . enumerate ( ) { // Select the Huffman table based on the region's table select value. let table = & HUFFMAN_TABLES [ channel . table_select [ region_idx ] as usize ] ; // If the table for a region is empty, fill the region with zeros and move on to the next // region. if table . huff_table . data . is_empty ( ) { while i < * region_end { buf [ i ] = 0.0 ; i += 1 ; buf [ i ] = 0.0 ; i += 1 ; } continue ; } // Otherwise, read the big_values. while i < * region_end && bits_read < part3_bits { // Decode the next Huffman code. let ( value , code_len ) = bs . read_huffman ( & table . huff_table , part3_bits - bits_read ) ? ; bits_read += code_len ; // In the big_values partition, each Huffman code decodes to two sample, x and y. Each // sample being 4-bits long. let mut x = ( value >> 4 ) as usize ; let mut y = ( value & 0xf ) as usize ; // If the first sample, x, is not 0, further process it. if x > 0 { // If x is saturated (it is at the maximum possible value), and the table specifies // linbits, then read linbits more bits and add it to the sample. if x == 15 && table . linbits > 0 { x += bs . read_bits_leq32 ( table . linbits ) ? as usize ; bits_read += table . linbits ; } // The next bit is the sign bit. The value of the sample is raised to the (4/3) // power. buf [ i ] = if bs . read_bit ( ) ? { - pow43_table [ x ] } else { pow43_table [ x ] } ; bits_read += 1 ; } else { buf [ i ] = 0.0 ; } i += 1 ; // Likewise, repeat the previous two steps for the second sample, y. if y > 0 { if y == 15 && table . linbits > 0 { y += bs . read_bits_leq32 ( table . linbits ) ? as usize ; bits_read += table . linbits ; } buf [ i ] = if bs . read_bit ( ) ? { - pow43_table [ y ] } else { pow43_table [ y ] } ; bits_read += 1 ; } else { buf [ i ] = 0.0 ; } i += 1 ; } } // Select the Huffman table for the count1 partition. let count1_table = if channel . count1table_select { QUADS_HUFFMAN_TABLE_B } else { QUADS_HUFFMAN_TABLE_A } ; // Read the count1 partition. while i <= 572 && bits_read < part3_bits { // Decode the next Huffman code. Note that we allow the Huffman decoder a few extra bits in // case of a count1 overrun (see below for more details). let ( value , code_len ) = bs . read_huffman ( & count1_table , part3_bits + count1_table . n_table_bits - bits_read ) ? ; bits_read += code_len ; // In the count1 partition, each Huffman code decodes to 4 samples: v, w, x, and y. // Each sample is 1-bit long (1 or 0). // // For each 1-bit sample, if it is 0, then then dequantized sample value is 0 as well. If // the 1-bit sample is 1, then read the sign bit (the next bit). The dequantized sample is // then either +/-1.0 depending on the sign bit. if value & 0x8 != 0 { buf [ i ] = if bs . read_bit ( ) ? { - 1.0 } else { 1.0 } ; bits_read += 1 ; } else { buf [ i ] = 0.0 ; } i += 1 ; if value & 0x4 != 0 { buf [ i ] = if bs . read_bit ( ) ? { - 1.0 } else { 1.0 } ; bits_read += 1 ; } else { buf [ i ] = 0.0 ; } i += 1 ; if value & 0x2 != 0 { buf [ i ] = if bs . read_bit ( ) ? { - 1.0 } else { 1.0 } ; bits_read += 1 ; } else { buf [ i ] = 0.0 ; } i += 1 ; if value & 0x1 != 0 { buf [ i ] = if bs . read_bit ( ) ? { - 1.0 } else { 1.0 } ; bits_read += 1 ; } else { buf [ i ] = 0.0 ; } i += 1 ; } // Ignore any extra "stuffing" bits. if bits_read < part3_bits { bs . ignore_bits ( part3_bits - bits_read ) ? ; } // Word on the street is that some encoders are poor at "stuffing" bits, resulting in part3_len // being ever so slightly too large. This causes the Huffman decode loop to decode the next few // bits as a sample. However, these bits are random data and not a real sample, so erase it! // The caller will be reponsible for re-aligning the bitstream reader. Candy Pop confirms this. else if bits_read > part3_bits { info ! ( " " ) ; i -= 4 ; } // The final partition after the count1 partition is the rzero partition. Samples in this // partition are all 0. for j in ( i .. 576 ) . step_by ( 2 ) { buf [ j + 0 ] = 0.0 ; buf [ j + 1 ] = 0.0 ; } Ok ( i ) }
Reads the Huffman coded spectral samples for a given channel in a granule from a `BitStream`
into a provided sample buffer.
Reads the Huffman coded spectral samples for a given channel in a granule from a ` BitStream ` into a provided sample buffer .
bs
&mut B
channel
&GranuleChannel
part3_bits
u32
buf
&mut [f32; 576]