public MpegXingHeader(ByteVector data)
		{
			//frames = 0;
			//size = 0;
			//valid = false;
			Parse(data);
		}
		private void Parse(ByteVector data)
		{
			// Check to see if a valid Xing header is available.

			if (!data.StartsWith("Xing"))
				return;

			// If the XingHeader doesn'type contain the number of frames and the total stream
			// info it'field invalid.

			if ((data[7] & 0x02) == 0)
			{
				TagLibDebugger.Debug("MPEG::XingHeader::parse() -- Xing header doesn't contain the total number of frames.");
				return;
			}

			if ((data[7] & 0x04) == 0)
			{
				TagLibDebugger.Debug("MPEG::XingHeader::parse() -- Xing header doesn't contain the total stream size.");
				return;
			}

			frames = data.Mid(8, 4).ToUInt();
			size = data.Mid(12, 4).ToUInt();

			valid = true;
		}
 public Box GetChild(ByteVector type)
 {
     if (this.Children != null)
     {
         IEnumerator<Box> enumerator = this.Children.GetEnumerator();
         try
         {
             while (enumerator.MoveNext())
             {
                 Box current = enumerator.Current;
                 if (current.BoxType == type)
                 {
                     return current;
                 }
             }
         }
         finally
         {
             if (enumerator == null)
             {
             }
             enumerator.Dispose();
         }
     }
     return null;
 }
 public BitmapInfoHeader(ByteVector data, int offset)
 {
     if (data == null)
     {
         throw new ArgumentNullException("data");
     }
     if ((offset + 40) > data.Count)
     {
         throw new CorruptFileException("Expected 40 bytes.");
     }
     if (offset < 0)
     {
         throw new ArgumentOutOfRangeException("offset");
     }
     this.size = data.Mid(offset, 4).ToUInt(false);
     this.width = data.Mid(offset + 4, 4).ToUInt(false);
     this.height = data.Mid(offset + 8, 4).ToUInt(false);
     this.planes = data.Mid(offset + 12, 2).ToUShort(false);
     this.bit_count = data.Mid(offset + 14, 2).ToUShort(false);
     this.compression_id = data.Mid(offset + 0x10, 4);
     this.size_of_image = data.Mid(offset + 20, 4).ToUInt(false);
     this.x_pixels_per_meter = data.Mid(offset + 0x18, 4).ToUInt(false);
     this.y_pixels_per_meter = data.Mid(offset + 0x1c, 4).ToUInt(false);
     this.colors_used = data.Mid(offset + 0x20, 4).ToUInt(false);
     this.colors_important = data.Mid(offset + 0x24, 4).ToUInt(false);
 }
		protected internal Id3v2PrivateFrame(ByteVector data, Id3v2FrameHeader header) : base(header)
		{
			//this.owner = null;
			//this.data = null;
			//ParseFields(FieldData(data));
			ParsePrivateFields(FieldData(data));
		}
		private void ParseRelativeVolumeFields(ByteVector data)
		{
			int pos = data.Find(TextDelimiter(StringType.Latin1));
			if (pos < 0)
				return;

			identification = data.Mid(0, pos).ToString(StringType.Latin1);
			pos += 1;

			// Each channel is at least 4 buffer.

			while (pos <= data.Count - 4)
			{
				Id3v2ChannelType type = (Id3v2ChannelType)data[pos];
				pos += 1;

				SetVolumeAdjustmentIndex(data.Mid(pos, 2).ToShort(), type);
				pos += 2;

				int bytes = BitsToBytes(data[pos]);
				pos += 1;

				SetPeakVolumeIndex(ParsePeakVolume(data.Mid(pos, bytes)), type);
				pos += bytes;
			}
		}
		// We can make our own handler.
		public Mpeg4IsoHandlerBox(ByteVector handlerType, string name, Mpeg4Box parent) : base("hdlr", 0, parent)
		{
			if (handlerType != null)
				this.handlerType = handlerType.Mid(0, 4);
			
			this.name = name;
		}
 public static AviStream ParseStreamList (ByteVector data)
 {
    if (data == null)
       throw new ArgumentNullException ("data");
    
    AviStream stream = null;
    int pos = 4;
    
    if (data.StartsWith ("strl"))
       while (pos + 8 < data.Count)
       {
          ByteVector id = data.Mid (pos, 4);
          int block_length = (int) data.Mid (pos + 4, 4).ToUInt (false);
          
          if (id == "strh" && stream == null)
          {
             AviStreamHeader stream_header = new AviStreamHeader (data, pos + 8);
             if (stream_header.Type == "vids")
                stream = new AviVideoStream (stream_header);
             else if (stream_header.Type == "auds")
                stream = new AviAudioStream (stream_header);
          }
          else if (stream != null)
             stream.ParseItem (id, data, pos + 8, block_length);
          
          pos += block_length + 8;
       }
    
    return stream;
 }
 protected void Parse (ByteVector data, byte version)
 {
    if (data == null)
       throw new ArgumentNullException ("data");
    
    size = SynchData.ToUInt (data.Mid (0, 4));
 }
      //////////////////////////////////////////////////////////////////////////
      // public methods
      //////////////////////////////////////////////////////////////////////////
		public AsfUnknownObject (AsfFile file, long position) : base (file, position)
		{
			if (file != null)
			{
				data = file.ReadBlock((int) (OriginalSize - 24));
			}
		}
        public override bool ReadPacket(ByteVector packet, int index)
        {
            if (packet == null)
            {
                throw new ArgumentNullException("packet");
            }
            if (index < 0)
            {
                throw new ArgumentOutOfRangeException("index", "index must be at least zero.");
            }
            int num = PacketType(packet);
            if ((num != 0x80) && (index == 0))
            {
                throw new CorruptFileException("Stream does not begin with theora header.");
            }
            if (this.comment_data == null)
            {
                switch (num)
                {
                    case 0x80:
                        this.header = new HeaderPacket(packet);
                        goto Label_009D;

                    case 0x81:
                        this.comment_data = packet.Mid(7);
                        goto Label_009D;
                }
                return true;
            }
        Label_009D:
            return (this.comment_data != null);
        }
 protected override void ParseFields(ByteVector data, byte version)
 {
     if (data.Count < 4)
     {
         throw new CorruptFileException("An object frame must contain at least 4 bytes.");
     }
     int offset = 0;
     this.encoding = (StringType) data[offset++];
     int num2 = data.Find(ByteVector.TextDelimiter(StringType.Latin1), offset);
     if (num2 >= offset)
     {
         this.mime_type = data.ToString(StringType.Latin1, offset, num2 - offset);
         ByteVector pattern = ByteVector.TextDelimiter(this.encoding);
         offset = num2 + 1;
         num2 = data.Find(pattern, offset, pattern.Count);
         if (num2 >= offset)
         {
             this.file_name = data.ToString(this.encoding, offset, num2 - offset);
             offset = num2 + pattern.Count;
             num2 = data.Find(pattern, offset, pattern.Count);
             if (num2 >= offset)
             {
                 this.description = data.ToString(this.encoding, offset, num2 - offset);
                 offset = num2 + pattern.Count;
                 data.RemoveRange(0, offset);
                 this.data = data;
             }
         }
     }
 }
		protected ByteVector FieldData(ByteVector frameData)
		{
			if (frameData != null)
			{
				uint headerSize = Id3v2FrameHeader.Size(header.Version);

				uint frameDataOffset = headerSize;
				uint frameDataLength = Size;

				if (header.Compression || header.DataLengthIndicator)
				{
					frameDataLength = frameData.Mid((int)headerSize, 4).ToUInt();
					frameDataLength += 4;
				}

				// FIXME: Impliment compression and encrpytion.
				/*
				#if HAVE_ZLIB
				   if(d->header->compression()) {
					  ByteVector data(frameDataLength);
					  uLongf uLongTmp = frameDataLength;
					  ::uncompress((Bytef *) data.data(),
								  (uLongf *) &uLongTmp,
								  (Bytef *) frameData.data() + frameDataOffset,
								  size());
					  return data;
				   }
				   else
				#endif
				*/

				return frameData.Mid((int)frameDataOffset, (int)frameDataLength);
			}
			else throw new ArgumentNullException("frameData");
		}
		protected void ParseHeader(ByteVector data)
		{
			if (header != null)
				header.SetData(data);
			else
				header = new Id3v2FrameHeader(data);
		}
 public new ByteVector Render()
 {
     ByteVector output = new ByteVector();
     output =  _data;
     output.Insert(0, Header.Render());
     return output;
 }
		private ByteVector RenderTextIdentifierFields()
		{
			ByteVector vector = new ByteVector();

			if (fieldList.Count > 0)
			{
				vector.Add((byte)textEncoding);

				bool first = true;
				foreach (string field in fieldList)
				{
					// Since the field text is null delimited, if this is not the
					// first element in the text, append the appropriate delimiter
					// for this encoding.

					if (!first)
						vector.Add(TextDelimiter(textEncoding));
					first = false;

					vector.Add(ByteVector.FromString(field, textEncoding));
				}
			}

			return vector;
		}
 public static AviStream ParseStreamList(ByteVector data)
 {
     int num2;
     if (data == null)
     {
         throw new ArgumentNullException("data");
     }
     if (!data.StartsWith("strl"))
     {
         return null;
     }
     AviStream stream = null;
     for (int i = 4; (i + 8) < data.Count; i += num2 + 8)
     {
         ByteVector id = data.Mid(i, 4);
         num2 = (int) data.Mid(i + 4, 4).ToUInt(false);
         if ((id == "strh") && (stream == null))
         {
             AviStreamHeader header = new AviStreamHeader(data, i + 8);
             if (header.Type == "vids")
             {
                 stream = new AviVideoStream(header);
             }
             else if (header.Type == "auds")
             {
                 stream = new AviAudioStream(header);
             }
         }
         else if (stream != null)
         {
             stream.ParseItem(id, data, i + 8, num2);
         }
     }
     return stream;
 }
 public AviStreamHeader(ByteVector data, int offset)
 {
     if (data == null)
     {
         throw new ArgumentNullException("data");
     }
     if (offset < 0)
     {
         throw new ArgumentOutOfRangeException("offset");
     }
     if ((offset + 0x38) > data.Count)
     {
         throw new CorruptFileException("Expected 56 bytes.");
     }
     this.type = data.Mid(offset, 4);
     this.handler = data.Mid(offset + 4, 4);
     this.flags = data.Mid(offset + 8, 4).ToUInt(false);
     this.priority = data.Mid(offset + 12, 4).ToUInt(false);
     this.initial_frames = data.Mid(offset + 0x10, 4).ToUInt(false);
     this.scale = data.Mid(offset + 20, 4).ToUInt(false);
     this.rate = data.Mid(offset + 0x18, 4).ToUInt(false);
     this.start = data.Mid(offset + 0x1c, 4).ToUInt(false);
     this.length = data.Mid(offset + 0x20, 4).ToUInt(false);
     this.suggested_buffer_size = data.Mid(offset + 0x24, 4).ToUInt(false);
     this.quality = data.Mid(offset + 40, 4).ToUInt(false);
     this.sample_size = data.Mid(offset + 0x2c, 4).ToUInt(false);
     this.left = data.Mid(offset + 0x30, 2).ToUShort(false);
     this.top = data.Mid(offset + 50, 2).ToUShort(false);
     this.right = data.Mid(offset + 0x34, 2).ToUShort(false);
     this.bottom = data.Mid(offset + 0x36, 2).ToUShort(false);
 }
 public Picture(ByteVector data)
 {
     if (data == null)
     {
         throw new ArgumentNullException("data");
     }
     if (data.Count < 0x20)
     {
         throw new CorruptFileException("Data must be at least 32 bytes long");
     }
     int startIndex = 0;
     this.type = (PictureType) data.Mid(startIndex, 4).ToUInt();
     startIndex += 4;
     int count = (int) data.Mid(startIndex, 4).ToUInt();
     startIndex += 4;
     this.mime_type = data.ToString(StringType.Latin1, startIndex, count);
     startIndex += count;
     int num3 = (int) data.Mid(startIndex, 4).ToUInt();
     startIndex += 4;
     this.description = data.ToString(StringType.UTF8, startIndex, num3);
     startIndex += num3;
     this.width = (int) data.Mid(startIndex, 4).ToUInt();
     startIndex += 4;
     this.height = (int) data.Mid(startIndex, 4).ToUInt();
     startIndex += 4;
     this.color_depth = (int) data.Mid(startIndex, 4).ToUInt();
     startIndex += 4;
     this.indexed_colors = (int) data.Mid(startIndex, 4).ToUInt();
     startIndex += 4;
     int length = (int) data.Mid(startIndex, 4).ToUInt();
     startIndex += 4;
     this.picture_data = data.Mid(startIndex, length);
 }
 public override void ParseItem(ByteVector id, ByteVector data, int start, int length)
 {
     if (id == "strf")
     {
         base.Codec = new WaveFormatEx(data, start);
     }
 }
		public Id3v2UnknownFrame(ByteVector data) : base(data)
		{
			//fieldData = null;
			//SetData(data);
			ParseHeader(data);
			ParseUnknownFields(data);
		}
 protected override ByteVector Render(ByteVector topData)
 {
     ByteVector vector = new ByteVector(4) {
         topData
     };
     return base.Render(vector);
 }
 public XingHeader(ByteVector data)
 {
     if (data == null)
     {
         throw new ArgumentNullException("data");
     }
     if (!data.StartsWith(FileIdentifier))
     {
         throw new CorruptFileException("Not a valid Xing header");
     }
     int startIndex = 8;
     if ((data[7] & 1) != 0)
     {
         this.frames = data.Mid(startIndex, 4).ToUInt();
         startIndex += 4;
     }
     else
     {
         this.frames = 0;
     }
     if ((data[7] & 2) != 0)
     {
         this.size = data.Mid(startIndex, 4).ToUInt();
         startIndex += 4;
     }
     else
     {
         this.size = 0;
     }
     this.present = true;
 }
		protected internal Id3v2UniqueFileIdentifierFrame(ByteVector data, Id3v2FrameHeader header) : base(header)
		{
			//owner = null;
			//identifier = null;
			//ParseFields(FieldData(data));
			ParseUniqueFields(FieldData(data));
		}
 public bool ReadPage(Page page)
 {
     if (page == null)
     {
         throw new ArgumentNullException("page");
     }
     ByteVector[] packets = page.Packets;
     for (int i = 0; i < packets.Length; i++)
     {
         if ((((byte) (page.Header.Flags & PageFlags.FirstPacketContinued)) == 0) && (this.previous_packet != null))
         {
             if (this.ReadPacket(this.previous_packet))
             {
                 return true;
             }
             this.previous_packet = null;
         }
         ByteVector data = packets[i];
         if (((i == 0) && (((byte) (page.Header.Flags & PageFlags.FirstPacketContinued)) != 0)) && (this.previous_packet != null))
         {
             this.previous_packet.Add(data);
             data = this.previous_packet;
         }
         this.previous_packet = null;
         if (i == (packets.Length - 1))
         {
             this.previous_packet = new ByteVector(data);
         }
         else if (this.ReadPacket(data))
         {
             return true;
         }
     }
     return false;
 }
Exemple #26
0
      public Footer (ByteVector data)
      {
         if (data.Count < Size)
            throw new CorruptFileException ("Provided data is smaller than object size.");
         
         if (!data.StartsWith (FileIdentifier))
            throw new CorruptFileException ("Provided data does not start with File Identifier");
         
         major_version   = data [3];
         revision_number = data [4];
         flags           = (HeaderFlags) data [5];
         
         
         if (major_version == 2 && (flags & (HeaderFlags) 127) != 0)
            throw new CorruptFileException ("Invalid flags set on version 2 tag.");
         
         if (major_version == 3 && (flags & (HeaderFlags) 15) != 0)
            throw new CorruptFileException ("Invalid flags set on version 3 tag.");
         
         if (major_version == 4 && (flags & (HeaderFlags) 7) != 0)
            throw new CorruptFileException ("Invalid flags set on version 4 tag.");
         
         
         ByteVector size_data = data.Mid (6, 4);
         
         foreach (byte b in size_data)
            if (b >= 128)
               throw new CorruptFileException ("One of the bytes in the header was greater than the allowed 128.");

         tag_size = SynchData.ToUInt (size_data);
      }
		private void ParseCommentsFields(ByteVector data)
		{
			if (data.Count < 5)
			{
				TagLibDebugger.Debug("A comment frame must contain at least 5 bytes.");
				return;
			}

			textEncoding = (StringType)data[0];
			language = data.Mid(1, 3);

			int byte_align = textEncoding == StringType.Latin1 || textEncoding == StringType.UTF8 ? 1 : 2;

			ByteVectorCollection l = ByteVectorCollection.Split(data.Mid(4), TextDelimiter(textEncoding), byte_align, 2);

			if (l.Count == 2)
			{
				if (l[0].Data != null && l[0].Data.Count > 0)
					description = l[0].ToString(textEncoding);
				else description = string.Empty;
				
				if (l[1].Data != null && l[1].Data.Count > 0)
					text = l[1].ToString(textEncoding);
				else text = string.Empty;
			}
		}
		protected void Parse(ByteVector data)
		{
			if (data != null)
			{
				if (data.Count < Size)
					return;

				// The first eight buffer, data[0..7], are the File Identifier, "APETAGEX".

				// Read the version number
				version = data.Mid(8, 4).ToUInt(false);

				// Read the tag size
				tagSize = data.Mid(12, 4).ToUInt(false);

				// Read the item count
				itemCount = data.Mid(16, 4).ToUInt(false);

				// Read the flags

				uint flags = data.Mid(20, 4).ToUInt(false);

				headerPresent = (flags >> 31) == 1;
				footerPresent = (flags >> 30) != 1;
				isHeader = (flags >> 29) == 1;
			}
			else throw new ArgumentNullException("data");
		}
 public StreamHeader(ByteVector data, long streamLength)
 {
     if (data == null)
     {
         throw new ArgumentNullException("data");
     }
     if (!data.StartsWith(FileIdentifier))
     {
         throw new CorruptFileException("Data does not begin with identifier.");
     }
     if (data.Count < 0x38L)
     {
         throw new CorruptFileException("Insufficient data in stream header");
     }
     this.stream_length = streamLength;
     this.version = data[3] & 15;
     if (this.version >= 7)
     {
         this.frames = data.Mid(4, 4).ToUInt(false);
         uint num = data.Mid(8, 4).ToUInt(false);
         this.sample_rate = sftable[(((num >> 0x11) & 1) * 2) + ((num >> 0x10) & 1)];
         this.header_data = 0;
     }
     else
     {
         this.header_data = data.Mid(0, 4).ToUInt(false);
         this.version = ((int) (this.header_data >> 11)) & 0x3ff;
         this.sample_rate = 0xac44;
         this.frames = data.Mid(4, (this.version < 5) ? 2 : 4).ToUInt(false);
     }
 }
 public override void ParseItem(ByteVector id, ByteVector data, int start, int length)
 {
     if (id == "strf")
     {
         base.Codec = new BitmapInfoHeader(data, start);
     }
 }
Exemple #31
0
 /// <summary>
 ///    Populates the values in the current instance by parsing
 ///    its field data in a specified version.
 /// </summary>
 /// <param name="data">
 ///    A <see cref="ByteVector" /> object containing the
 ///    extracted field data.
 /// </param>
 /// <param name="version">
 ///    A <see cref="byte" /> indicating the ID3v2 version the
 ///    field data is encoded in.
 /// </param>
 protected abstract void ParseFields(ByteVector data,
                                     byte version);
Exemple #32
0
 public AviHeader(ByteVector data) : this(data, 0)
 {
 }
Exemple #33
0
        /// <summary>
        ///    Creates a box by reading it from a file given its header,
        ///    parent header, handler, and index in its parent.
        /// </summary>
        /// <param name="file">
        ///    A <see cref="TagLib.File" /> object containing the file
        ///    to read from.
        /// </param>
        /// <param name="header">
        ///    A <see cref="BoxHeader" /> object containing the header
        ///    of the box to create.
        /// </param>
        /// <param name="parent">
        ///    A <see cref="BoxHeader" /> object containing the header
        ///    of the parent box.
        /// </param>
        /// <param name="handler">
        ///    A <see cref="IsoHandlerBox" /> object containing the
        ///    handler that applies to the new box.
        /// </param>
        /// <param name="index">
        ///    A <see cref="int" /> value containing the index of the
        ///    new box in its parent.
        /// </param>
        /// <returns>
        ///    A newly created <see cref="Box" /> object.
        /// </returns>
        private static Box CreateBox(TagLib.File file,
                                     BoxHeader header,
                                     BoxHeader parent,
                                     IsoHandlerBox handler,
                                     int index)
        {
            // The first few children of an "stsd" are sample
            // entries.
            if (parent.BoxType == BoxType.Stsd &&
                parent.Box is IsoSampleDescriptionBox &&
                index < (parent.Box as IsoSampleDescriptionBox).EntryCount)
            {
                if (handler != null && handler.HandlerType == BoxType.Soun)
                {
                    return(new IsoAudioSampleEntry(header, file, handler));
                }
                else if (handler != null && handler.HandlerType == BoxType.Vide)
                {
                    return(new IsoVisualSampleEntry(header, file, handler));
                }
                else if (handler != null && handler.HandlerType == BoxType.Alis)
                {
                    if (header.BoxType == BoxType.Text)
                    {
                        return(new TextBox(header, file, handler));
                    }
                    else if (header.BoxType == BoxType.Url)
                    {
                        return(new UrlBox(header, file, handler));
                    }
                    // This could be anything, so just parse it
                    return(new UnknownBox(header, file, handler));
                }
                else
                {
                    return(new IsoSampleEntry(header,
                                              file, handler));
                }
            }

            // Standard items...
            ByteVector type = header.BoxType;

            if (type == BoxType.Mvhd)
            {
                return(new IsoMovieHeaderBox(header, file,
                                             handler));
            }
            else if (type == BoxType.Stbl)
            {
                return(new IsoSampleTableBox(header, file,
                                             handler));
            }
            else if (type == BoxType.Stsd)
            {
                return(new IsoSampleDescriptionBox(header,
                                                   file, handler));
            }
            else if (type == BoxType.Stco)
            {
                return(new IsoChunkOffsetBox(header, file,
                                             handler));
            }
            else if (type == BoxType.Co64)
            {
                return(new IsoChunkLargeOffsetBox(header, file,
                                                  handler));
            }
            else if (type == BoxType.Hdlr)
            {
                return(new IsoHandlerBox(header, file,
                                         handler));
            }
            else if (type == BoxType.Udta)
            {
                return(new IsoUserDataBox(header, file,
                                          handler));
            }
            else if (type == BoxType.Meta)
            {
                return(new IsoMetaBox(header, file, handler));
            }
            else if (type == BoxType.Ilst)
            {
                return(new AppleItemListBox(header, file,
                                            handler));
            }
            else if (type == BoxType.Data)
            {
                return(new AppleDataBox(header, file, handler));
            }
            else if (type == BoxType.Esds)
            {
                return(new AppleElementaryStreamDescriptor(
                           header, file, handler));
            }
            else if (type == BoxType.Free || type == BoxType.Skip)
            {
                return(new IsoFreeSpaceBox(header, file,
                                           handler));
            }
            else if (type == BoxType.Mean || type == BoxType.Name)
            {
                return(new AppleAdditionalInfoBox(header, file,
                                                  handler));
            }

            // If we still don't have a tag, and we're inside an
            // ItemListBox, load the box as an AnnotationBox
            // (Apple tag item).
            if (parent.BoxType == BoxType.Ilst)
            {
                return(new AppleAnnotationBox(header, file,
                                              handler));
            }

            // Nothing good. Go generic.
            return(new UnknownBox(header, file, handler));
        }
Exemple #34
0
 public static ByteVector TextDelimiter(StringType type)
 {
     return(ByteVector.TextDelimiter(type));
 }
Exemple #35
0
        /// <summary>
        ///    Extracts the field data from the raw data portion of an
        ///    ID3v2 frame.
        /// </summary>
        /// <param name="frameData">
        ///    A <see cref="ByteVector" /> object containing fraw frame
        ///    data.
        /// </param>
        /// <param name="offset">
        ///    A <see cref="int" /> value containing the index at which
        ///    the data is contained.
        /// </param>
        /// <param name="version">
        ///    A <see cref="byte" /> value containing the ID3v2 version
        ///    of the data.
        /// </param>
        /// <returns>
        ///    A <see cref="ByteVector" /> object containing the
        ///    extracted field data.
        /// </returns>
        /// <remarks>
        ///    This method is necessary for extracting extra data
        ///    prepended to the frame such as the grouping ID.
        /// </remarks>
        /// <exception cref="ArgumentNullException">
        ///    <paramref name="frameData" /> is <see langword="null" />.
        /// </exception>
        protected ByteVector FieldData(ByteVector frameData,
                                       int offset, byte version)
        {
            if (frameData == null)
            {
                throw new ArgumentNullException("frameData");
            }

            int data_offset = offset + (int)FrameHeader.Size(version);
            int data_length = (int)Size;

            if ((Flags & (FrameFlags.Compression |
                          FrameFlags.DataLengthIndicator)) != 0)
            {
                data_offset += 4;
                data_length -= 4;
            }

            if ((Flags & FrameFlags.GroupingIdentity) != 0)
            {
                if (frameData.Count >= data_offset)
                {
                    throw new TagLib.CorruptFileException(
                              "Frame data incomplete.");
                }
                group_id = frameData [data_offset++];
                data_length--;
            }

            if ((Flags & FrameFlags.Encryption) != 0)
            {
                if (frameData.Count >= data_offset)
                {
                    throw new TagLib.CorruptFileException(
                              "Frame data incomplete.");
                }
                encryption_id = frameData [data_offset++];
                data_length--;
            }

            data_length = Math.Min(data_length, frameData.Count - data_offset);
            if (data_length < 0)
            {
                throw new CorruptFileException(
                          "Frame size less than zero.");
            }

            ByteVector data = frameData.Mid(data_offset,
                                            data_length);

            if ((Flags & FrameFlags.Unsynchronisation) != 0)
            {
                int before_length = data.Count;
                SynchData.ResynchByteVector(data);
                data_length -= (data.Count - before_length);
            }

            // FIXME: Implement encryption.
            if ((Flags & FrameFlags.Encryption) != 0)
            {
                throw new NotImplementedException();
            }

            // FIXME: Implement compression.
            if ((Flags & FrameFlags.Compression) != 0)
            {
                throw new NotImplementedException();
            }

            /*
             * if(d->header->compression()) {
             *      ByteVector data(frameDataLength);
             *      uLongf uLongTmp = frameDataLength;
             *      ::uncompress((Bytef *) data.data(),
             *      (uLongf *) &uLongTmp,
             *      (Bytef *) frameData.data() + frameDataOffset,
             *      size());
             *      return data;
             * }
             */

            return(data);
        }
Exemple #36
0
        /// <summary>
        ///    Reads an APP1 segment to find EXIF or XMP metadata.
        /// </summary>
        /// <param name="length">
        ///    The length of the segment that will be read.
        /// </param>
        private void ReadAPP1Segment(ushort length)
        {
            long       position = Tell;
            ByteVector data     = null;

            // for an Exif segment, the data block consists of 14 bytes of:
            //    * 6 bytes Exif identifier string
            //    * 2 bytes bigendian indication MM (or II)
            //    * 2 bytes Tiff magic number (42)
            //    * 4 bytes offset of the first IFD in this segment
            //
            //    the last two points are alreay encoded according to
            //    big- or littleendian
            int exif_header_length = 14;

            // could be an Exif segment
            if ((ImageTag.TagTypes & TagLib.TagTypes.TiffIFD) == 0x00 && length >= exif_header_length)
            {
                data = ReadBlock(exif_header_length);

                if (data.Count == exif_header_length &&
                    data.Mid(0, 6).ToString().Equals(EXIF_IDENTIFIER))
                {
                    bool is_bigendian = data.Mid(6, 2).ToString().Equals("MM");

                    ushort magic = data.Mid(8, 2).ToUShort(is_bigendian);
                    if (magic != 42)
                    {
                        throw new Exception(String.Format("Invalid TIFF magic: {0}", magic));
                    }

                    uint ifd_offset = data.Mid(10, 4).ToUInt(is_bigendian);

                    var exif   = new IFDTag();
                    var reader = new IFDReader(this, is_bigendian, exif.Structure, position + 6, ifd_offset, (uint)(length - 6));
                    reader.Read();
                    ImageTag.AddTag(exif);

                    AddMetadataBlock(position - 4, length + 4);

                    return;
                }
            }

            int xmp_header_length = XmpTag.XAP_NS.Length + 1;

            // could be an Xmp segment
            if ((ImageTag.TagTypes & TagLib.TagTypes.XMP) == 0x00 && length >= xmp_header_length)
            {
                // if already data is read for determining the Exif segment,
                // just read the remaining bytes.
                // NOTE: that (exif_header_length < xmp_header_length) holds
                if (data == null)
                {
                    data = ReadBlock(xmp_header_length);
                }
                else
                {
                    data.Add(ReadBlock(xmp_header_length - exif_header_length));
                }

                if (data.ToString().Equals(XmpTag.XAP_NS + "\0"))
                {
                    ByteVector xmp_data = ReadBlock(length - xmp_header_length);

                    ImageTag.AddTag(new XmpTag(xmp_data.ToString(), this));

                    AddMetadataBlock(position - 4, length + 4);
                }
            }
        }
Exemple #37
0
 public GeneralEncapsulatedObjectFrame(ByteVector data,
                                       byte version)
     : base(data, version)
 {
     SetData(data, 0, version, true);
 }
 /// <summary>
 ///    Constructs and initializes a new instance of <see
 ///    cref="AppleDataBox" /> with specified data and flags.
 /// </summary>
 /// <param name="data">
 ///    A <see cref="ByteVector" /> object containing the data to
 ///    store in the new instance.
 /// </param>
 /// <param name="flags">
 ///    A <see cref="uint" /> value containing flags to use for
 ///    the new instance.
 /// </param>
 public AppleDataBox(ByteVector data, uint flags)
     : base("data", 0, flags)
 {
     Data = data;
 }
 public void Mid()
 {
     Assert.AreEqual(ByteVector.FromString("KLMNOPQRSTUVWXYZ", StringType.UTF8), TestVector.Mid(10));
     Assert.AreEqual(ByteVector.FromString("PQRSTU", StringType.UTF8), TestVector.Mid(15, 6));
 }
Exemple #40
0
 public WaveFormatEx(ByteVector data) : this(data, 0)
 {
 }
Exemple #41
0
 public void SetText(params string[] text)
 {
     raw_data = null;
     Text     = text;
 }
Exemple #42
0
 protected internal UserTextInformationFrame(ByteVector data, int offset, FrameHeader header, byte version) :
     base(data, offset, header, version)
 {
 }
Exemple #43
0
 public void SetText(StringCollection fields)
 {
     raw_data = null;
     Text     = fields != null?fields.ToArray() : null;
 }
Exemple #44
0
        /// <summary>
        ///    Renders the current instance, encoded in a specified
        ///    ID3v2 version.
        /// </summary>
        /// <param name="version">
        ///    A <see cref="byte" /> value specifying the version of
        ///    ID3v2 to use when encoding the current instance.
        /// </param>
        /// <returns>
        ///    A <see cref="ByteVector" /> object containing the
        ///    rendered version of the current instance.
        /// </returns>
        /// <exception cref="NotImplementedException">
        ///    The current instance uses some feature that cannot be
        ///    implemented in the specified ID3v2 version, or uses a
        ///    feature, such as encryption or compression, which is not
        ///    yet implemented in the library.
        /// </exception>
        public virtual ByteVector Render(byte version)
        {
            // Remove flags that are not supported by older versions
            // of ID3v2.
            if (version < 4)
            {
                Flags &= ~(FrameFlags.DataLengthIndicator |
                           FrameFlags.Unsynchronisation);
            }

            if (version < 3)
            {
                Flags &= ~(FrameFlags.Compression |
                           FrameFlags.Encryption |
                           FrameFlags.FileAlterPreservation |
                           FrameFlags.GroupingIdentity |
                           FrameFlags.ReadOnly |
                           FrameFlags.TagAlterPreservation);
            }

            ByteVector field_data = RenderFields(version);

            // If we don't have any content, don't render anything.
            // This will cause the frame to not be rendered.
            if (field_data.Count == 0)
            {
                return(new ByteVector());
            }

            ByteVector front_data = new ByteVector();

            if ((Flags & (FrameFlags.Compression |
                          FrameFlags.DataLengthIndicator)) != 0)
            {
                front_data.Add(ByteVector.FromUInt((uint)
                                                   field_data.Count));
            }

            if ((Flags & FrameFlags.GroupingIdentity) != 0)
            {
                front_data.Add(group_id);
            }

            if ((Flags & FrameFlags.Encryption) != 0)
            {
                front_data.Add(encryption_id);
            }

            // FIXME: Implement compression.
            if ((Flags & FrameFlags.Compression) != 0)
            {
                throw new NotImplementedException(
                          "Compression not yet supported");
            }

            // FIXME: Implement encryption.
            if ((Flags & FrameFlags.Encryption) != 0)
            {
                throw new NotImplementedException(
                          "Encryption not yet supported");
            }

            if ((Flags & FrameFlags.Unsynchronisation) != 0)
            {
                SynchData.UnsynchByteVector(field_data);
            }

            if (front_data.Count > 0)
            {
                field_data.Insert(0, front_data);
            }

            header.FrameSize = (uint)field_data.Count;
            ByteVector header_data = header.Render(version);

            header_data.Add(field_data);

            return(header_data);
        }
Exemple #45
0
 protected internal TextInformationFrame(ByteVector data, int offset, FrameHeader header, byte version) :
     base(header)
 {
     SetData(data, offset, version, false);
 }
Exemple #46
0
        protected override ByteVector RenderFields(byte version)
        {
            if (raw_data != null && raw_version == version && raw_encoding == Tag.DefaultEncoding)
            {
                return(raw_data);
            }
            StringType encoding = CorrectEncoding(TextEncoding, version);
            ByteVector v        = new ByteVector((byte)encoding);

            string[] text = text_fields;
            bool     txxx = FrameId == FrameType.TXXX;

            if (version > 3 || txxx)
            {
                if (txxx)
                {
                    if (text.Length == 0)
                    {
                        text = new string[]
                        {
                            null, null
                        };
                    }
                    else if (text.Length == 1)
                    {
                        text = new string[]
                        {
                            text[0], null
                        };
                    }
                }
                for (int i = 0; i < text.Length; i++)
                {
                    if (i != 0)
                    {
                        v.Add(ByteVector.TextDelimiter(encoding));
                    }
                    if (text[i] != null)
                    {
                        v.Add(ByteVector.FromString(text[i], encoding));
                    }
                }
            }
            else if (FrameId == FrameType.TCON)
            {
                byte          id;
                bool          prev_value_indexed = true;
                StringBuilder data = new StringBuilder();
                foreach (string s in text)
                {
                    if (!prev_value_indexed)
                    {
                        data.Append("/").Append(s);
                        continue;
                    }
                    if (prev_value_indexed = byte.TryParse(s, out id))
                    {
                        data.AppendFormat(CultureInfo.InvariantCulture, "({0})", id);
                    }
                    else
                    {
                        data.Append(s);
                    }
                }
                v.Add(ByteVector.FromString(data.ToString(), encoding));
            }
            else
            {
                v.Add(ByteVector.FromString(string.Join("/", text), encoding));
            }
            return(v);
        }
Exemple #47
0
 public TextInformationFrame(ByteVector data, byte version) :
     base(data, version)
 {
     SetData(data, 0, version, true);
 }
Exemple #48
0
 public UserTextInformationFrame(ByteVector data, byte version) :
     base(data, version)
 {
 }
Exemple #49
0
        protected void ParseRawData()
        {
            if (raw_data == null)
            {
                return;
            }
            ByteVector data = raw_data;

            raw_data = null;
            encoding = (StringType)data[0];
            List <string> field_list = new List <string>();
            ByteVector    delim      = ByteVector.TextDelimiter(encoding);

            if (raw_version > 3 || FrameId == FrameType.TXXX)
            {
                field_list.AddRange(data.ToStrings(encoding, 1));
            }
            else if (data.Count > 1 && !data.Mid(1, delim.Count).Equals(delim))
            {
                string value      = data.ToString(encoding, 1, data.Count - 1);
                int    null_index = value.IndexOf('\x00');
                if (null_index >= 0)
                {
                    value = value.Substring(0, null_index);
                }
                if (FrameId == FrameType.TCOM || FrameId == FrameType.TEXT || FrameId == FrameType.TOLY || FrameId == FrameType.TOPE || FrameId == FrameType.TPE1 || FrameId == FrameType.TPE2 || FrameId == FrameType.TPE3 || FrameId == FrameType.TPE4)
                {
                    field_list.AddRange(value.Split('/'));
                }
                else if (FrameId == FrameType.TCON)
                {
                    while (value.Length > 1 && value[0] == '(')
                    {
                        int closing = value.IndexOf(')');
                        if (closing < 0)
                        {
                            break;
                        }
                        string number = value.Substring(1, closing - 1);
                        field_list.Add(number);
                        value = value.Substring(closing + 1).TrimStart('/', ' ');
                        string text = Genres.IndexToAudio(number);
                        if (text != null && value.StartsWith(text))
                        {
                            value = value.Substring(text.Length).TrimStart('/', ' ');
                        }
                    }
                    if (value.Length > 0)
                    {
                        field_list.AddRange(value.Split(new char[] { '/' }));
                    }
                }
                else
                {
                    field_list.Add(value);
                }
            }
            while (field_list.Count != 0 && string.IsNullOrEmpty(field_list[field_list.Count - 1]))
            {
                field_list.RemoveAt(field_list.Count - 1);
            }
            text_fields = field_list.ToArray();
        }
Exemple #50
0
 public static TextInformationFrame Get(Tag tag, ByteVector ident)
 {
     return(Get(tag, ident, false));
 }
Exemple #51
0
 protected override void ParseFields(ByteVector data, byte version)
 {
     raw_data     = data;
     raw_version  = version;
     raw_encoding = (StringType)data[0];
 }
Exemple #52
0
 public TextInformationFrame(ByteVector ident) :
     this(ident, Id3v2.Tag.DefaultEncoding)
 {
 }
Exemple #53
0
 public static TextInformationFrame Get(Tag tag, ByteVector ident, bool create)
 {
     return(Get(tag, ident, Tag.DefaultEncoding, create));
 }
Exemple #54
0
 /// <summary>
 ///    Implements the <see cref="CodecProvider" /> delegate to
 ///    provide support for recognizing a Vorbis stream from the
 ///    header packet.
 /// </summary>
 /// <param name="packet">
 ///    A <see cref="ByteVector" /> object containing the stream
 ///    header packet.
 /// </param>
 /// <returns>
 ///    A <see cref="Codec"/> object containing a codec capable
 ///    of parsing the stream of <see langref="null" /> if the
 ///    stream is not a Vorbis stream.
 /// </returns>
 public static Codec FromPacket(ByteVector packet)
 {
     return((PacketType(packet) == 1) ? new Vorbis() : null);
 }
Exemple #55
0
 /// <summary>
 ///    Constructs and initializes a new instance of <see
 ///    cref="CommentsFrame" /> by reading its raw data in a
 ///    specified ID3v2 version.
 /// </summary>
 /// <param name="data">
 ///    A <see cref="ByteVector" /> object starting with the raw
 ///    representation of the new frame.
 /// </param>
 /// <param name="version">
 ///    A <see cref="byte" /> indicating the ID3v2 version the
 ///    raw frame is encoded in.
 /// </param>
 public CommentsFrame(ByteVector data, byte version)
     : base(data, version)
 {
     SetData(data, 0, version, true);
 }
Exemple #56
0
 public TextInformationFrame(ByteVector ident, StringType encoding) :
     base(ident, 4)
 {
     this.encoding = encoding;
 }
Exemple #57
0
 protected internal PopularimeterFrame(ByteVector data, int offset, FrameHeader header, byte version) :
     base(header)
 {
     SetData(data, offset, version, false);
 }
Exemple #58
0
        /// <summary>
        ///    Saves the changes made in the current instance to the
        ///    file it represents.
        /// </summary>
        public override void Save()
        {
            if (udta_box == null)
            {
                udta_box = new IsoUserDataBox();
            }

            // Try to get into write mode.
            Mode = File.AccessMode.Write;
            try {
                FileParser parser = new FileParser(this);
                parser.ParseBoxHeaders();

                InvariantStartPosition = parser.MdatStartPosition;
                InvariantEndPosition   = parser.MdatEndPosition;

                long size_change    = 0;
                long write_position = 0;

                ByteVector tag_data = udta_box.Render();

                // If we don't have a "udta" box to overwrite...
                if (parser.UdtaTree == null ||
                    parser.UdtaTree.Length == 0 ||
                    parser.UdtaTree [parser.UdtaTree.Length - 1
                    ].BoxType != BoxType.Udta)
                {
                    // Stick the box at the end of the moov box.
                    BoxHeader moov_header = parser.MoovTree [
                        parser.MoovTree.Length - 1];
                    size_change    = tag_data.Count;
                    write_position = moov_header.Position +
                                     moov_header.TotalBoxSize;
                    Insert(tag_data, write_position, 0);

                    // Overwrite the parent box sizes.
                    for (int i = parser.MoovTree.Length - 1; i >= 0;
                         i--)
                    {
                        size_change = parser.MoovTree [i
                                      ].Overwrite(this, size_change);
                    }
                }
                else
                {
                    // Overwrite the old box.
                    BoxHeader udta_header = parser.UdtaTree [
                        parser.UdtaTree.Length - 1];
                    size_change = tag_data.Count -
                                  udta_header.TotalBoxSize;
                    write_position = udta_header.Position;
                    Insert(tag_data, write_position,
                           udta_header.TotalBoxSize);

                    // Overwrite the parent box sizes.
                    for (int i = parser.UdtaTree.Length - 2; i >= 0;
                         i--)
                    {
                        size_change = parser.UdtaTree [i
                                      ].Overwrite(this, size_change);
                    }
                }

                // If we've had a size change, we may need to adjust
                // chunk offsets.
                if (size_change != 0)
                {
                    // We may have moved the offset boxes, so we
                    // need to reread.
                    parser.ParseChunkOffsets();
                    InvariantStartPosition = parser.MdatStartPosition;
                    InvariantEndPosition   = parser.MdatEndPosition;

                    foreach (Box box in parser.ChunkOffsetBoxes)
                    {
                        IsoChunkLargeOffsetBox co64 =
                            box as IsoChunkLargeOffsetBox;

                        if (co64 != null)
                        {
                            co64.Overwrite(this,
                                           size_change,
                                           write_position);
                            continue;
                        }

                        IsoChunkOffsetBox stco =
                            box as IsoChunkOffsetBox;

                        if (stco != null)
                        {
                            stco.Overwrite(this,
                                           size_change,
                                           write_position);
                            continue;
                        }
                    }
                }

                TagTypesOnDisk = TagTypes;
            } finally {
                Mode = File.AccessMode.Closed;
            }
        }
Exemple #59
0
 public PopularimeterFrame(ByteVector data, byte version) :
     base(data, version)
 {
     SetData(data, 0, version, true);
 }
Exemple #60
0
        /// <summary>
        ///    Saves the changes made in the current instance to the
        ///    file it represents.
        /// </summary>
        public override void Save()
        {
            if (udta_boxes.Count == 0)
            {
                IsoUserDataBox udtaBox = new IsoUserDataBox();
                udta_boxes.Add(udtaBox);
            }

            // Try to get into write mode.
            Mode = File.AccessMode.Write;
            try {
                FileParser parser = new FileParser(this);
                parser.ParseBoxHeaders();

                InvariantStartPosition = parser.MdatStartPosition;
                InvariantEndPosition   = parser.MdatEndPosition;

                long size_change    = 0;
                long write_position = 0;

                // To avoid rewriting udta blocks which might not have been modified,
                // the code here will work correctly if:
                // 1. There is a single udta for the entire file
                //   - OR -
                // 2. There are multiple utdtas, but only 1 of them contains the Apple ILST box.
                // We should be OK in the vast majority of cases
                IsoUserDataBox udtaBox = FindAppleTagUdta();
                if (null == udtaBox)
                {
                    udtaBox = new IsoUserDataBox();
                }
                ByteVector tag_data = udtaBox.Render();

                // If we don't have a "udta" box to overwrite...
                if (udtaBox.ParentTree == null ||
                    udtaBox.ParentTree.Length == 0)
                {
                    // Stick the box at the end of the moov box.
                    BoxHeader moov_header = parser.MoovTree [
                        parser.MoovTree.Length - 1];
                    size_change    = tag_data.Count;
                    write_position = moov_header.Position +
                                     moov_header.TotalBoxSize;
                    Insert(tag_data, write_position, 0);

                    // Overwrite the parent box sizes.
                    for (int i = parser.MoovTree.Length - 1; i >= 0;
                         i--)
                    {
                        size_change = parser.MoovTree [i
                                      ].Overwrite(this, size_change);
                    }
                }
                else
                {
                    // Overwrite the old box.
                    BoxHeader udta_header = udtaBox.ParentTree[udtaBox.ParentTree.Length - 1];
                    size_change = tag_data.Count -
                                  udta_header.TotalBoxSize;
                    write_position = udta_header.Position;
                    Insert(tag_data, write_position,
                           udta_header.TotalBoxSize);

                    // Overwrite the parent box sizes.
                    for (int i = udtaBox.ParentTree.Length - 2; i >= 0;
                         i--)
                    {
                        size_change = udtaBox.ParentTree [i
                                      ].Overwrite(this, size_change);
                    }
                }

                // If we've had a size change, we may need to adjust
                // chunk offsets.
                if (size_change != 0)
                {
                    // We may have moved the offset boxes, so we
                    // need to reread.
                    parser.ParseChunkOffsets();
                    InvariantStartPosition = parser.MdatStartPosition;
                    InvariantEndPosition   = parser.MdatEndPosition;

                    foreach (Box box in parser.ChunkOffsetBoxes)
                    {
                        IsoChunkLargeOffsetBox co64 =
                            box as IsoChunkLargeOffsetBox;

                        if (co64 != null)
                        {
                            co64.Overwrite(this,
                                           size_change,
                                           write_position);
                            continue;
                        }

                        IsoChunkOffsetBox stco =
                            box as IsoChunkOffsetBox;

                        if (stco != null)
                        {
                            stco.Overwrite(this,
                                           size_change,
                                           write_position);
                            continue;
                        }
                    }
                }

                TagTypesOnDisk = TagTypes;
            } finally {
                Mode = File.AccessMode.Closed;
            }
        }