Example #1
0
        private void ReadSamples(MpegFrame frame)
        {
            // load in all the data for this frame (1152 samples in this case)
            // NB: we flatten these into output order
            for (int ss = 0, idx = 0; ss < SSLIMIT; ss++, idx += SBLIMIT * (_granuleCount - 1))
            {
                for (int sb = 0; sb < SBLIMIT; sb++, idx++)
                {
                    for (int ch = 0; ch < _channels; ch++)
                    {
                        if (ch == 0 || sb < _jsbound)
                        {
                            int[] samples = _samples[ch];
                            int   alloc   = _allocation[ch][sb];
                            if (alloc != 0)
                            {
                                if (alloc < 0)
                                {
                                    // grouping (Layer II only, so we don't have to play with the granule count)
                                    int val    = frame.ReadBits(-alloc);
                                    int levels = (1 << (-alloc / 2 + -alloc % 2 - 1)) + 1;

                                    samples[idx]               = val % levels;
                                    val                       /= levels;
                                    samples[idx + SBLIMIT]     = val % levels;
                                    samples[idx + SBLIMIT * 2] = val / levels;
                                }
                                else
                                {
                                    // non-grouping
                                    for (int gr = 0; gr < _granuleCount; gr++)
                                    {
                                        samples[idx + SBLIMIT * gr] = frame.ReadBits(alloc);
                                    }
                                }
                            }
                            else
                            {
                                // no energy...  zero out the samples
                                for (int gr = 0; gr < _granuleCount; gr++)
                                {
                                    samples[idx + SBLIMIT * gr] = 0;
                                }
                            }
                        }
                        else
                        {
                            int[] samples0 = _samples[0];
                            int[] samples1 = _samples[1];

                            // copy chan 0 to chan 1
                            for (int gr = 0; gr < _granuleCount; gr++)
                            {
                                samples1[idx + SBLIMIT * gr] = samples0[idx + SBLIMIT * gr];
                            }
                        }
                    }
                }
            }
        }
Example #2
0
        private void ReadAllocation(MpegFrame frame, int[] rateTable)
        {
            var _subBandCount = rateTable.Length;

            if (_jsbound > _subBandCount)
            {
                _jsbound = _subBandCount;
            }

            Array.Clear(_allocation[0], 0, SBLIMIT);
            Array.Clear(_allocation[1], 0, SBLIMIT);

            int sb = 0;

            for (; sb < _jsbound; sb++)
            {
                int[] table = _allocLookupTable[rateTable[sb]];
                int   bits  = table[0];

                for (int ch = 0; ch < _channels; ch++)
                {
                    _allocation[ch][sb] = table[frame.ReadBits(bits) + 1];
                }
            }
            for (; sb < _subBandCount; sb++)
            {
                int[] table = _allocLookupTable[rateTable[sb]];
                _allocation[0][sb] = _allocation[1][sb] = table[frame.ReadBits(table[0]) + 1];
            }
        }
Example #3
0
        private void ReadScaleFactors(MpegFrame frame)
        {
            for (int sb = 0; sb < SBLIMIT; sb++)
            {
                for (int ch = 0; ch < _channels; ch++)
                {
                    int[][] scalefac = _scalefac[ch];
                    switch (_scfsi[ch][sb])
                    {
                    case 0:
                        // all three
                        scalefac[0][sb] = frame.ReadBits(6);
                        scalefac[1][sb] = frame.ReadBits(6);
                        scalefac[2][sb] = frame.ReadBits(6);
                        break;

                    case 1:
                        // only two (2 = 1)
                        scalefac[0][sb]     =
                            scalefac[1][sb] = frame.ReadBits(6);
                        scalefac[2][sb]     = frame.ReadBits(6);
                        break;

                    case 2:
                        // only one (3 = 2 = 1)
                        scalefac[0][sb]         =
                            scalefac[1][sb]     =
                                scalefac[2][sb] = frame.ReadBits(6);
                        break;

                    case 3:
                        // only two (3 = 2)
                        scalefac[0][sb]     = frame.ReadBits(6);
                        scalefac[1][sb]     =
                            scalefac[2][sb] = frame.ReadBits(6);
                        break;

                    default:
                        // none
                        scalefac[0][sb] = 63;
                        scalefac[1][sb] = 63;
                        scalefac[2][sb] = 63;
                        break;
                    }
                }
            }
        }
        public bool AddBits(MpegFrame frame, int overlap)
        {
            int originalEnd = _end;

            int slots = GetSlots(frame);

            while (--slots >= 0)
            {
                int tmp = frame.ReadBits(8);
                if (tmp == -1)
                {
                    ThrowFrameNotEnoughBytes();
                }

                _buf[++_end] = (byte)tmp;
                if (_end == BufferSize - 1)
                {
                    _end = -1;
                }
            }

            _bitsLeft = 8;
            if (originalEnd == -1)
            {
                // it's either the start of the stream or we've reset...
                // only return true if overlap says this frame is enough
                return(overlap == 0);
            }
            else
            {
                // it's not the start of the stream so calculate _start based on whether we have enough bytes left

                // if we have enough bytes, reset start to match overlap
                if ((originalEnd + 1 - _start + BufferSize) % BufferSize >= overlap)
                {
                    _start = (originalEnd + 1 - overlap + BufferSize) % BufferSize;
                    return(true);
                }
                // otherwise, just set start to match the start of the frame (we probably skipped a frame)
                else
                {
                    _start = originalEnd;
                    return(false);
                }
            }
        }
Example #5
0
        protected static bool GetCRC(
            MpegFrame frame, int[] rateTable, int[][] allocLookupTable, bool readScfsiBits, ref uint crc)
        {
            // ugh...  we basically have to re-implement the allocation logic here.

            // keep up with how many active subbands we need to read selection info for
            var scfsiBits = 0;

            // only read as many subbands as we actually need; pay attention to the intensity stereo subbands
            var subbandCount = rateTable.Length;
            var jsbound      = subbandCount;

            if (frame.ChannelMode == MpegChannelMode.JointStereo)
            {
                jsbound = frame.ChannelModeExtension * 4 + 4;
            }

            // read the full stereo subbands
            var channels = frame.ChannelMode == MpegChannelMode.Mono ? 1 : 2;
            var sb       = 0;

            for (; sb < jsbound; sb++)
            {
                var bits = allocLookupTable[rateTable[sb]][0];
                for (int ch = 0; ch < channels; ch++)
                {
                    var alloc = frame.ReadBits(bits);
                    if (alloc > 0)
                    {
                        scfsiBits += 2;
                    }

                    MpegFrame.UpdateCRC(alloc, bits, ref crc);
                }
            }

            // read the intensity stereo subbands
            for (; sb < subbandCount; sb++)
            {
                var bits = allocLookupTable[rateTable[sb]][0];

                var alloc = frame.ReadBits(bits);
                if (alloc > 0)
                {
                    scfsiBits += channels * 2;
                }

                MpegFrame.UpdateCRC(alloc, bits, ref crc);
            }

            // finally, read the scalefac selection bits
            if (readScfsiBits)
            {
                while (scfsiBits >= 2)
                {
                    MpegFrame.UpdateCRC(frame.ReadBits(2), 2, ref crc);
                    scfsiBits -= 2;
                }
            }

            return(true);
        }
 static internal bool GetCRC(MpegFrame frame, ref uint crc)
 {
     var cnt = frame.GetSideDataSize();
     while (--cnt >= 0)
     {
         MpegFrame.UpdateCRC(frame.ReadBits(8), 8, ref crc);
     }
     return true;
 }