Beispiel #1
0
        internal bool TryInit()
        {
            // try to process the stream header...
            if (!ProcessStreamHeader(_packetProvider.PeekNextPacket()))
            {
                return(false);
            }

            // seek past the stream header packet
            _packetProvider.GetNextPacket().Done();

            // load the comments header...
            var packet = _packetProvider.GetNextPacket();

            if (!LoadComments(packet))
            {
                throw new InvalidDataException("Comment header was not readable!");
            }
            packet.Done();

            // load the book header...
            packet = _packetProvider.GetNextPacket();
            if (!LoadBooks(packet))
            {
                throw new InvalidDataException("Book header was not readable!");
            }
            packet.Done();

            // get the decoding logic bootstrapped
            InitDecoder();

            return(true);
        }
Beispiel #2
0
        internal bool TryInit()
        {
            var initialPacket = _packetProvider.GetNextPacket();

            // make sure it's a vorbis stream...
            if (!initialPacket.ReadBytes(7).SequenceEqual(new byte[] { 0x01, 0x76, 0x6f, 0x72, 0x62, 0x69, 0x73 }))
            {
                _glueBits += initialPacket.Length * 8;
                return(false);
            }

            _glueBits += 56;

            // now load the initial header
            ProcessStreamHeader(initialPacket);

            // finally, load the comment and book headers...
            DataPacket commentsPacket = null, booksPacket = null;

            while (commentsPacket == null || booksPacket == null)
            {
                var packet = _packetProvider.GetNextPacket();
                if (packet.IsResync)
                {
                    throw new InvalidDataException("Missing header packets!");
                }

                if (!_pagesSeen.Contains(packet.PageSequenceNumber))
                {
                    _pagesSeen.Add(packet.PageSequenceNumber);
                }

                switch (packet.PeekByte())
                {
                case 1: throw new InvalidDataException("Found second init header!");

                case 3: LoadComments(packet); commentsPacket = packet; break;

                case 5: LoadBooks(packet); booksPacket = packet; break;
                }
            }

            // tell the packets that we're done with them
            initialPacket.Done();
            commentsPacket.Done();
            booksPacket.Done();

            // get the decoding logic bootstrapped
            InitDecoder();

            return(true);
        }
Beispiel #3
0
        /// <summary>
        /// Looks for the next opus data packet in the Ogg stream and queues it up.
        /// If the end of stream has been reached, this does nothing.
        /// </summary>
        private void QueueNextPacket()
        {
            if (_endOfStream)
            {
                return;
            }

            DataPacket packet = _packetProvider.GetNextPacket();

            if (packet == null || packet.IsEndOfStream)
            {
                _endOfStream    = true;
                _nextDataPacket = null;
                return;
            }

            byte[] buf = new byte[packet.Length];
            packet.Read(buf, 0, packet.Length);
            packet.Done();

            if (buf.Length > 8 && "OpusHead".Equals(Encoding.UTF8.GetString(buf, 0, 8)))
            {
                _header = OpusHeader.ParsePacket(buf, buf.Length);
                QueueNextPacket();
            }
            else if (buf.Length > 8 && "OpusTags".Equals(Encoding.UTF8.GetString(buf, 0, 8)))
            {
                _tags = OpusTags.ParsePacket(buf, buf.Length);
                QueueNextPacket();
            }
            else
            {
                _nextDataPacket = buf;
            }
        }
Beispiel #4
0
        private void SkipOpusTags(IPacketProvider packetProvider)
        {
            DataPacket packet = packetProvider.PeekNextPacket();
            byte[] buffer = GetPacketData(packet);

            if (Encoding.UTF8.GetString(buffer, 0, 8) == "OpusTags")
            {
                packetProvider.GetNextPacket();
            }
        }
        private bool ProcessHeaderPackets(IPacket?packet)
        {
            if (!ProcessHeaderPacket(packet, LoadStreamHeader, _ => _packetProvider.GetNextPacket()?.Done()))
            {
                return(false);
            }

            if (!ProcessHeaderPacket(_packetProvider.GetNextPacket(), LoadComments, pkt => pkt.Done()))
            {
                return(false);
            }

            if (!ProcessHeaderPacket(_packetProvider.GetNextPacket(), LoadBooks, pkt => pkt.Done()))
            {
                return(false);
            }

            _currentPosition = 0;
            ResetDecoder();
            return(true);
        }
Beispiel #6
0
        private static void ReadData(OggOpusStructure structure, IPacketProvider packetProvider)
        {
            bool       finished = false;
            DataPacket packet   = packetProvider.GetNextPacket();

            while (!finished)
            {
                finished = packet.IsEndOfStream;
                byte[] buffer = GetPacketData(packet);

                var frame = new OpusFrame();
                frame.Length      = buffer.Length;
                frame.Data        = buffer;
                frame.SampleCount = GetOpusSamplesPerFrame(frame.Data[0], 48000);
                structure.Frames.Add(frame);

                packet = packetProvider.GetNextPacket();
            }

            structure.SampleCount = structure.Frames.Sum(x => x.SampleCount);
        }
        internal bool TryInit()
        {
            if (!ProcessStreamHeader(_packetProvider.PeekNextPacket()))
            {
                return(false);
            }
            _packetProvider.GetNextPacket().Done();
            DataPacket nextPacket = _packetProvider.GetNextPacket();

            if (!LoadComments(nextPacket))
            {
                throw new InvalidDataException("Comment header was not readable!");
            }
            nextPacket.Done();
            nextPacket = _packetProvider.GetNextPacket();
            if (!LoadBooks(nextPacket))
            {
                throw new InvalidDataException("Book header was not readable!");
            }
            nextPacket.Done();
            InitDecoder();
            return(true);
        }
Beispiel #8
0
        private void NewStream(int streamSerial)
        {
            DataPacket nextPacket = this._packetProvider.GetNextPacket(streamSerial);

            if ((int)nextPacket.PeekByte() != (int)VorbisStreamDecoder.InitialPacketMarker)
            {
                return;
            }
            VorbisStreamDecoder vorbisStreamDecoder = new VorbisStreamDecoder((Func <DataPacket>)(() =>
            {
                IPacketProvider local_0 = this._packetProvider;
                if (local_0 != null)
                {
                    return(local_0.GetNextPacket(streamSerial));
                }
                else
                {
                    return((DataPacket)null);
                }
            }), (Func <int>)(() =>
            {
                IPacketProvider local_0 = this._packetProvider;
                if (local_0 != null)
                {
                    return(local_0.GetTotalPageCount(streamSerial));
                }
                else
                {
                    return(0);
                }
            }));

            try
            {
                if (!vorbisStreamDecoder.TryInit(nextPacket))
                {
                    return;
                }
                this._decoders.Add(vorbisStreamDecoder);
                this._serials.Add(streamSerial);
            }
            catch (InvalidDataException ex)
            {
            }
        }
Beispiel #9
0
        private static void ReadOpusHead(OggOpusStructure structure, IPacketProvider packetProvider)
        {
            DataPacket packet = packetProvider.GetNextPacket();
            byte[] buffer = GetPacketData(packet);
            packet.Done();

            BinaryReader reader = GetBinaryReader(new MemoryStream(buffer), Endianness.LittleEndian);
            if (reader.ReadUTF8(8) != "OpusHead")
            {
                throw new InvalidDataException("Expected OpusHead segment");
            }

            structure.Version = reader.ReadByte();
            structure.ChannelCount = reader.ReadByte();
            structure.PreSkip = reader.ReadInt16();
            structure.SampleRate = reader.ReadInt32();
            structure.OutputGain = reader.ReadInt16();
            structure.ChannelMapping = reader.ReadByte();
        }
        /// <summary>
        /// Looks for the next opus data packet in the Ogg stream and queues it up.
        /// If the end of stream has been reached, this does nothing.
        /// </summary>
        private void QueueNextPacket()
        {
            if (_endOfStream)
            {
                return;
            }

            DataPacket packet = _packetProvider.GetNextPacket();

            if (packet == null)
            {
                _endOfStream    = true;
                _nextDataPacket = null;
                return;
            }

            PageGranulePosition = packet.PageGranulePosition;
            PagePosition        = packet.PageSequenceNumber;

            byte[] buf = new byte[packet.Length];
            packet.Read(buf, 0, packet.Length);
            packet.Done();

            if (buf.Length > 8 && "OpusHead".Equals(Encoding.UTF8.GetString(buf, 0, 8)))
            {
                QueueNextPacket();
            }
            else if (buf.Length > 8 && "OpusTags".Equals(Encoding.UTF8.GetString(buf, 0, 8)))
            {
                Tags = OpusTags.ParsePacket(buf, buf.Length);
                QueueNextPacket();
            }
            else
            {
                _nextDataPacket = buf;
            }
        }
        public void DecodeNextPacket()
        {
            _sw.Start();
            DataPacket dataPacket = null;

            try
            {
                IPacketProvider packetProvider = _packetProvider;
                if (packetProvider != null)
                {
                    dataPacket = packetProvider.GetNextPacket();
                }
                if (dataPacket == null)
                {
                    _eosFound = true;
                }
                else
                {
                    if (!_pagesSeen.Contains(_lastPageSeen = dataPacket.PageSequenceNumber))
                    {
                        _pagesSeen.Add(_lastPageSeen);
                    }
                    if (dataPacket.IsResync)
                    {
                        ResetDecoder(isFullReset: false);
                    }
                    if (dataPacket == _parameterChangePacket)
                    {
                        _isParameterChange = true;
                        ProcessParameterChange(dataPacket);
                    }
                    else if (!UnpackPacket(dataPacket))
                    {
                        dataPacket.Done();
                        _wasteBits += 8 * dataPacket.Length;
                    }
                    else
                    {
                        dataPacket.Done();
                        DecodePacket();
                        int num = OverlapSamples();
                        if (!dataPacket.GranuleCount.HasValue)
                        {
                            dataPacket.GranuleCount = num;
                        }
                        UpdatePosition(num, dataPacket);
                        int num2 = Utils.Sum(_sampleCountHistory) + num;
                        _bitsPerPacketHistory.Enqueue((int)dataPacket.BitsRead);
                        _sampleCountHistory.Enqueue(num);
                        while (num2 > _sampleRate)
                        {
                            _bitsPerPacketHistory.Dequeue();
                            num2 -= _sampleCountHistory.Dequeue();
                        }
                    }
                }
            }
            catch
            {
                dataPacket?.Done();
                throw;
            }
            finally
            {
                _sw.Stop();
            }
        }