Ejemplo n.º 1
0
        /// <summary>
        ///    Constructs and initializes a new instance of <see
        ///    cref="FullBox" /> with a provided header and handler by
        ///    reading the contents from a specified file.
        /// </summary>
        /// <param name="header">
        ///    A <see cref="BoxHeader" /> object containing the header
        ///    to use for the new instance.
        /// </param>
        /// <param name="file">
        ///    A <see cref="TagLibSharp.File" /> object to read the contents
        ///    of the box from.
        /// </param>
        /// <param name="handler">
        ///    A <see cref="IsoHandlerBox" /> object containing the
        ///    handler that applies to the new instance.
        /// </param>
        /// <exception cref="ArgumentNullException">
        ///    <paramref name="file" /> is <see langword="null" />.
        /// </exception>
        protected FullBox(BoxHeader header, TagLibSharp.File file,
                          IsoHandlerBox handler)
            : base(header, handler)
        {
            if (file == null)
            {
                throw new ArgumentNullException("file");
            }

            file.Seek(base.DataPosition);
            ByteVector header_data = file.ReadBlock(4);

            version = header_data [0];
            flags   = header_data.Mid(1, 3).ToUInt();
        }
Ejemplo n.º 2
0
        /// <summary>
        ///    Constructs and initializes a new instance of <see
        ///    cref="List" /> by reading the contents of a raw RIFF list
        ///    from a specified position in a <see cref="TagLibSharp.File"/>.
        /// </summary>
        /// <param name="file">
        ///    A <see cref="TagLibSharp.File" /> object containing the file
        ///    from which the contents of the new instance is to be
        ///    read.
        /// </param>
        /// <param name="position">
        ///    A <see cref="long" /> value specify at what position to
        ///    read the list.
        /// </param>
        /// <param name="length">
        ///    A <see cref="int" /> value specifying the number of bytes
        ///    to read.
        /// </param>
        /// <exception cref="ArgumentNullException">
        ///    <paramref name="file" /> is <see langword="null" />.
        /// </exception>
        /// <exception cref="ArgumentOutOfRangeException">
        ///    <paramref name="position" /> is less than zero or greater
        ///    than the size of the file.
        /// </exception>
        public List(TagLibSharp.File file, long position, int length)
        {
            if (file == null)
            {
                throw new ArgumentNullException("file");
            }

            if (length < 0)
            {
                throw new ArgumentOutOfRangeException(
                          "length");
            }

            if (position < 0 || position > file.Length - length)
            {
                throw new ArgumentOutOfRangeException(
                          "position");
            }

            file.Seek(position);
            Parse(file.ReadBlock(length));
        }
Ejemplo n.º 3
0
        /// <summary>
        ///    Constructs and initializes a new instance of <see
        ///    cref="IsoHandlerBox" /> with a provided header and
        ///    handler by reading the contents from a specified file.
        /// </summary>
        /// <param name="header">
        ///    A <see cref="BoxHeader" /> object containing the header
        ///    to use for the new instance.
        /// </param>
        /// <param name="file">
        ///    A <see cref="TagLibSharp.File" /> object to read the contents
        ///    of the box from.
        /// </param>
        /// <param name="handler">
        ///    A <see cref="IsoHandlerBox" /> object containing the
        ///    handler that applies to the new instance.
        /// </param>
        /// <exception cref="ArgumentNullException">
        ///    <paramref name="file" /> is <see langword="null" />.
        /// </exception>
        public IsoHandlerBox(BoxHeader header, TagLibSharp.File file,
                             IsoHandlerBox handler)
            : base(header, file, handler)
        {
            if (file == null)
            {
                throw new System.ArgumentNullException("file");
            }

            file.Seek(DataPosition + 4);
            ByteVector box_data = file.ReadBlock(DataSize - 4);

            handler_type = box_data.Mid(0, 4);

            int end = box_data.Find((byte)0, 16);

            if (end < 16)
            {
                end = box_data.Count;
            }
            name = box_data.ToString(StringType.UTF8, 16, end - 16);
        }
Ejemplo n.º 4
0
        /// <summary>
        ///    Constructs and initializes a new instance of <see
        ///    cref="VideoHeader" /> by reading it from a specified
        ///    location in a specified file.
        /// </summary>
        /// <param name="file">
        ///    A <see cref="TagLibSharp.File" /> object to read from.
        /// </param>
        /// <param name="position">
        ///    A <see cref="long" /> value indicating the position in
        ///    <paramref name="file" /> at which the header begins.
        /// </param>
        /// <exception cref="ArgumentNullException">
        ///    <paramref name="file" /> is <see langword="null" />.
        /// </exception>
        /// <exception cref="CorruptFileException">
        ///    Insufficient data could be read for the header.
        /// </exception>
        public VideoHeader(TagLibSharp.File file, long position)
        {
            if (file == null)
            {
                throw new ArgumentNullException("file");
            }

            file.Seek(position);
            ByteVector data = file.ReadBlock(7);

            if (data.Count < 7)
            {
                throw new CorruptFileException(
                          "Insufficient data in header.");
            }

            width            = data.Mid(0, 2).ToUShort() >> 4;
            height           = data.Mid(1, 2).ToUShort() & 0x0FFF;
            frame_rate_index = data [3] & 0x0F;
            bitrate          = (int)((data.Mid(4, 3).ToUInt() >> 6) &
                                     0x3FFFF);
        }
Ejemplo n.º 5
0
        /// <summary>
        ///    Constructs and initializes a new instance of <see
        ///    cref="IsoMovieHeaderBox" /> with a provided header and
        ///    handler by reading the contents from a specified file.
        /// </summary>
        /// <param name="header">
        ///    A <see cref="BoxHeader" /> object containing the header
        ///    to use for the new instance.
        /// </param>
        /// <param name="file">
        ///    A <see cref="TagLibSharp.File" /> object to read the contents
        ///    of the box from.
        /// </param>
        /// <param name="handler">
        ///    A <see cref="IsoHandlerBox" /> object containing the
        ///    handler that applies to the new instance.
        /// </param>
        /// <exception cref="ArgumentNullException">
        ///    <paramref name="file" /> is <see langword="null" />.
        /// </exception>
        public IsoMovieHeaderBox(BoxHeader header, TagLibSharp.File file,
                                 IsoHandlerBox handler)
            : base(header, file, handler)
        {
            if (file == null)
            {
                throw new ArgumentNullException("file");
            }

            int        bytes_remaining = DataSize;
            ByteVector data;

            if (Version == 1)
            {
                // Read version one (large integers).
                data = file.ReadBlock(Math.Min(28,
                                               bytes_remaining));
                if (data.Count >= 8)
                {
                    creation_time = data.Mid(0,
                                             8).ToULong();
                }
                if (data.Count >= 16)
                {
                    modification_time = data.Mid(8,
                                                 8).ToULong();
                }
                if (data.Count >= 20)
                {
                    timescale = data.Mid(16, 4).ToUInt();
                }
                if (data.Count >= 28)
                {
                    duration = data.Mid(20, 8).ToULong();
                }
                bytes_remaining -= 28;
            }
            else
            {
                // Read version zero (normal integers).
                data = file.ReadBlock(Math.Min(16,
                                               bytes_remaining));
                if (data.Count >= 4)
                {
                    creation_time = data.Mid(0,
                                             4).ToUInt();
                }
                if (data.Count >= 8)
                {
                    modification_time = data.Mid(4,
                                                 4).ToUInt();
                }
                if (data.Count >= 12)
                {
                    timescale = data.Mid(8, 4).ToUInt();
                }
                if (data.Count >= 16)
                {
                    duration = data.Mid(12, 4).ToUInt();
                }
                bytes_remaining -= 16;
            }

            data = file.ReadBlock(Math.Min(6, bytes_remaining));
            if (data.Count >= 4)
            {
                rate = data.Mid(0, 4).ToUInt();
            }
            if (data.Count >= 6)
            {
                volume = data.Mid(4, 2).ToUShort();
            }
            file.Seek(file.Tell + 70);
            bytes_remaining -= 76;

            data = file.ReadBlock(Math.Min(4,
                                           bytes_remaining));

            if (data.Count >= 4)
            {
                next_track_id = data.Mid(0, 4).ToUInt();
            }
        }
Ejemplo n.º 6
0
        /// <summary>
        ///    Constructs and initializes a new instance of <see
        ///    cref="AudioHeader" /> by reading its contents from a
        ///    <see cref="ByteVector" /> object and its Xing Header from
        ///    the appropriate location in the specified file.
        /// </summary>
        /// <param name="data">
        ///    A <see cref="ByteVector" /> object containing the header
        ///    to read.
        /// </param>
        /// <param name="file">
        ///    A <see cref="TagLibSharp.File" /> object to read the Xing
        ///    header from.
        /// </param>
        /// <param name="position">
        ///    A <see cref="long" /> value indicating the position in
        ///    <paramref name="file" /> at which the header begins.
        /// </param>
        /// <exception cref="CorruptFileException">
        ///    <paramref name="data" /> is less than 4 bytes long,
        ///    does not begin with a MPEG audio synch, has a negative
        ///    bitrate, or has a sample rate of zero.
        /// </exception>
        private AudioHeader(ByteVector data, TagLibSharp.File file,
                            long position)
        {
            this.duration = TimeSpan.Zero;
            stream_length = 0;

            if (data.Count < 4)
            {
                throw new CorruptFileException(
                          "Insufficient header length.");
            }

            if (data [0] != 0xFF)
            {
                throw new CorruptFileException(
                          "First byte did not match MPEG synch.");
            }

            // Checking bits from high to low:
            //
            // First 3 bits MUST be set. Bits 4 and 5 can
            // be 00, 10, or 11 but not 01. One or more of
            // bits 6 and 7 must be set. Bit 8 can be
            // anything.
            if ((data [1] & 0xE6) <= 0xE0 || (data [1] & 0x18) == 0x08)
            {
                throw new CorruptFileException(
                          "Second byte did not match MPEG synch.");
            }

            flags = data.ToUInt();

            if (((flags >> 12) & 0x0F) == 0x0F)
            {
                throw new CorruptFileException(
                          "Header uses invalid bitrate index.");
            }

            if (((flags >> 10) & 0x03) == 0x03)
            {
                throw new CorruptFileException(
                          "Invalid sample rate.");
            }

            xing_header = XingHeader.Unknown;

            vbri_header = VBRIHeader.Unknown;

            // Check for a Xing header that will help us in
            // gathering information about a VBR stream.
            file.Seek(position + XingHeader.XingHeaderOffset(
                          Version, ChannelMode));

            ByteVector xing_data = file.ReadBlock(16);

            if (xing_data.Count == 16 && xing_data.StartsWith(
                    XingHeader.FileIdentifier))
            {
                xing_header = new XingHeader(xing_data);
            }

            if (xing_header.Present)
            {
                return;
            }

            // A Xing header could not be found, next chec for a
            // Fraunhofer VBRI header.
            file.Seek(position + VBRIHeader.VBRIHeaderOffset());

            // Only get the first 24 bytes of the Header.
            // We're not interested in the TOC entries.
            ByteVector vbri_data = file.ReadBlock(24);

            if (vbri_data.Count == 24 &&
                vbri_data.StartsWith(VBRIHeader.FileIdentifier))
            {
                vbri_header = new VBRIHeader(vbri_data);
            }
        }
Ejemplo n.º 7
0
        /// <summary>
        ///    Searches for an audio header in a <see cref="TagLibSharp.File"
        ///    /> starting at a specified position and searching through
        ///    a specified number of bytes.
        /// </summary>
        /// <param name="header">
        ///    A <see cref="AudioHeader" /> object in which the found
        ///    header will be stored.
        /// </param>
        /// <param name="file">
        ///    A <see cref="TagLibSharp.File" /> object to search.
        /// </param>
        /// <param name="position">
        ///    A <see cref="long" /> value specifying the seek position
        ///    in <paramref name="file" /> at which to start searching.
        /// </param>
        /// <param name="length">
        ///    A <see cref="int" /> value specifying the maximum number
        ///    of bytes to search before aborting.
        /// </param>
        /// <returns>
        ///    A <see cref="bool" /> value indicating whether or not a
        ///    header was found.
        /// </returns>
        /// <exception cref="ArgumentNullException">
        ///    <paramref name="file" /> is <see langword="null" />.
        /// </exception>
        public static bool Find(out AudioHeader header,
                                TagLibSharp.File file, long position, int length)
        {
            if (file == null)
            {
                throw new ArgumentNullException("file");
            }

            long end = position + length;

            header = AudioHeader.Unknown;

            file.Seek(position);

            ByteVector buffer = file.ReadBlock(3);

            if (buffer.Count < 3)
            {
                return(false);
            }

            do
            {
                file.Seek(position + 3);
                buffer = buffer.Mid(buffer.Count - 3);
                buffer.Add(file.ReadBlock(
                               (int)File.BufferSize));

                for (int i = 0; i < buffer.Count - 3 &&
                     (length < 0 || position + i < end); i++)
                {
                    if (buffer[i] == 0xFF &&
                        buffer[i + 1] >= 0xF0)                          // 0xFFF
                    {
                        try
                        {
                            BitStream bits = new BitStream(buffer.Mid(i, 7).Data);

                            // 12 bits sync header
                            bits.ReadInt32(12);

                            // 1 bit mpeg 2/4
                            bits.ReadInt32(1);

                            // 2 bits layer
                            bits.ReadInt32(2);

                            // 1 bit protection absent
                            bits.ReadInt32(1);

                            // 2 bits profile object type
                            bits.ReadInt32(2);

                            // 4 bits sampling frequency index
                            int samplerateindex = bits.ReadInt32(4);
                            if (samplerateindex >= sample_rates.Length)
                            {
                                return(false);
                            }
                            long samplerate = sample_rates[samplerateindex];

                            // 1 bit private bit
                            bits.ReadInt32(1);

                            // 3 bits channel configuration
                            int channelconfigindex = bits.ReadInt32(3);
                            if (channelconfigindex >= channels.Length)
                            {
                                return(false);
                            }

                            // 4 copyright bits
                            bits.ReadInt32(4);

                            // 13 bits frame length
                            long framelength = bits.ReadInt32(13);                             // double check framelength
                            if (framelength < 7)
                            {
                                return(false);
                            }

                            // 11 bits buffer fullness
                            bits.ReadInt32(11);

                            // 2 bits number of raw data blocks in frame
                            int numberofframes = bits.ReadInt32(2) + 1;

                            long numberofsamples = numberofframes * 1024;
                            long bitrate         = framelength * 8 * samplerate / numberofsamples;

                            header = new AudioHeader(channels[channelconfigindex],
                                                     (int)bitrate,
                                                     (int)samplerate,
                                                     (int)numberofsamples,
                                                     numberofframes);

                            return(true);
                        }
                        catch (CorruptFileException)
                        {
                        }
                    }
                }

                position += File.BufferSize;
            } while (buffer.Count > 3 && (length < 0 || position < end));

            return(false);
        }