Example #1
0
        IFD parseDngPrivateData(Tag t)
        {
            /*
             * 1. Six bytes containing the zero-terminated string "Adobe". (The DNG specification calls for the DNGPrivateData tag to start with an ASCII string identifying the creator/format).
             * 2. 4 bytes: an ASCII string ("MakN" for a Makernote),  indicating what sort of data is being stored here. Note that this is not zero-terminated.
             * 3. A four-byte count (number of data bytes following); this is the length of the original MakerNote data. (This is always in "most significant byte first" format).
             * 4. 2 bytes: the byte-order indicator from the original file (the usual 'MM'/4D4D or 'II'/4949).
             * 5. 4 bytes: the original file offset for the MakerNote tag data (stored according to the byte order given above).
             * 6. The contents of the MakerNote tag. This is a simple byte-for-byte copy, with no modification.
             */
            uint size = t.dataCount;

            Common.ConvertArray(ref t.data, out byte[] data);
            Common.ByteToChar(ref data, out char[] dataAsChar);
            string id = new String(dataAsChar);

            if (!id.StartsWith("Adobe"))
            {
                Debug.WriteLine("Not Adobe Private data");
                return(null);
            }

            if (!(data[6] == 'M' && data[7] == 'a' && data[8] == 'k' && data[9] == 'N'))
            {
                Debug.WriteLine("Not Makernote");
                return(null);
            }

            data = data.Skip(10).ToArray();
            uint count;

            count = (uint)data[0] << 24 | (uint)data[1] << 16 | (uint)data[2] << 8 | data[3];

            data = data.Skip(4).ToArray();
            if (count > size)
            {
                Debug.WriteLine("Error reading TIFF structure (invalid size). File Corrupt");
                return(null);
            }
            Endianness makernote_endian = Endianness.unknown;

            if (data[0] == 0x49 && data[1] == 0x49)
            {
                makernote_endian = Endianness.little;
            }
            else if (data[0] == 0x4D && data[1] == 0x4D)
            {
                makernote_endian = Endianness.big;
            }
            else
            {
                Debug.WriteLine("Cannot determine endianess of DNG makernote");
                return(null);
            }
            data = data.Skip(2).ToArray();
            uint org_offset;


            org_offset = (uint)data[0] << 24 | (uint)data[1] << 16 | (uint)data[2] << 8 | data[3];

            data = data.Skip(4).ToArray();
            /* We don't parse original makernotes that are placed after 300MB mark in the original file */
            if (org_offset + count > 300 * 1024 * 1024)
            {
                Debug.WriteLine("Adobe Private data: original offset of makernote is past 300MB offset");
                return(null);
            }
            /* Create fake tiff with original offsets */
            //byte[] maker_data = new byte[count];
            // Common.memcopy(ref maker_data, ref data, count, 0, 0);
            TIFFBinaryReader maker_map = new TIFFBinaryReader(TIFFBinaryReader.streamFromArray(data));

            IFD maker_ifd;

            try
            {
                maker_ifd = parseMakerNote(maker_map, 0, makernote_endian);
            }
            catch (TiffParserException e)
            {
                Debug.WriteLine(e.Message);
                return(null);
            }
            return(maker_ifd);
        }