dragon66 / icafe

Java library for reading, writing, converting and manipulating images and metadata
Eclipse Public License 1.0
204 stars 58 forks source link

Fix expection when image has only one iptc tag. #38

Closed sinedsem closed 7 years ago

sinedsem commented 7 years ago

When image has only one iptc tag offset == src.length. It is a valid case, but exception is thrown when reading metadata.

dragon66 commented 7 years ago

@sinedsem Can you let me know more details about where exactly the exception was thrown? I don't think the ArrayUtils.subArray itself is wrong. When image has one IPTC tag, the offset should be 0 instead of src.length = 1.

sinedsem commented 7 years ago

@dragon66 hello. I've uploaded an example file for you: https://github.com/sinedsem/test/blob/master/one_iptc_tag.jpg When I try to read metadata from it, I got exception:

java.lang.IllegalArgumentException: Copy range out of array bounds
    at com.icafe4j.util.ArrayUtils.subArray(ArrayUtils.java:913)
    at com.icafe4j.image.meta.iptc.IPTCDataSet.hashCode(IPTCDataSet.java:186)
    at java.util.HashMap.hash(HashMap.java:338)
    at java.util.HashMap.put(HashMap.java:611)
    at java.util.HashSet.add(HashSet.java:219)
    at java.util.AbstractCollection.addAll(AbstractCollection.java:344)
    at java.util.LinkedHashSet.<init>(LinkedHashSet.java:169)
    at com.icafe4j.image.meta.iptc.IPTC.read(IPTC.java:162)
    at com.icafe4j.image.meta.Metadata.ensureDataRead(Metadata.java:497)
    at com.icafe4j.image.meta.iptc.IPTC.<init>(IPTC.java:68)
    at com.icafe4j.image.meta.adobe.IPTC_NAA.<init>(IPTC_NAA.java:49)
    at com.icafe4j.image.meta.adobe.IRB.read(IRB.java:129)
    at com.icafe4j.image.meta.Metadata.ensureDataRead(Metadata.java:497)
    at com.icafe4j.image.meta.adobe.IRB.get8BIM(IRB.java:75)
    at com.icafe4j.image.jpeg.JPEGTweaker.readMetadata(JPEGTweaker.java:1514)
    at com.icafe4j.image.meta.Metadata.readMetadata(Metadata.java:424)
    at com.icafe4j.image.meta.Metadata.readMetadata(Metadata.java:402)

ITPC metadata was inserted there with https://github.com/vnesek/nmote-iim4j . Honestly, now I realized that when I write medatada with "Exif Pilot" there is no such exeption, so more likely the problem is in nmote-iim4j. However, "Exif Pilot" aslo can correctly read metadata written by nmote-iim4j, so could you please check whether one_iptc_tag.jpg is correct or not?

dragon66 commented 7 years ago

@sinedsem Thanks for your details. I found the issue: in the original image, there are actually two IPTC tags instead of one. One is named ObjectName and the other is Keywords. The data size for the second one is 0 which breaks icafe. The straightforward fix for this one is to add a check to IPTC.java inside read() to not create IPTCDataSet if the data size is 0. Something like this:

if(recordSize != 0) {
    IPTCDataSet dataSet = new IPTCDataSet(recordNumber, tag, recordSize, data, i);
    String name = dataSet.getName();
    if(datasetMap.get(name) == null) {
        List<IPTCDataSet> list = new ArrayList<IPTCDataSet>();
        list.add(dataSet);
        datasetMap.put(name, list);
    } else
        datasetMap.get(name).add(dataSet);
}

I will check in a new fix later.

sinedsem commented 7 years ago

Great, thank you!

dragon66 commented 7 years ago

@sinedsem hello, I have updated the repository with fix for this bug. Please take a look and see if it works for you or not. The following is what I got from the one_IPTC_tag.jpg you provided after the fix and Metadata entry 1 is related to IPTC:

2017-01-04 14:15:44,001 [main] INFO  com.icafe4j.test.TestMetadata - Start of metadata information:
2017-01-04 14:15:44,003 [main] INFO  com.icafe4j.test.TestMetadata - Total number of metadata entries: 5
2017-01-04 14:15:44,003 [main] INFO  com.icafe4j.test.TestMetadata - Metadata entry 0 - PHOTOSHOP_IRB
2017-01-04 14:15:44,003 [main] INFO  com.icafe4j.image.meta.adobe.IRB - <<Adobe IRB information starts>>
2017-01-04 14:15:44,003 [main] INFO  com.icafe4j.image.meta.adobe._8BIM - IPTC_NAA [Value: 0x0404] - IPTC-NAA record.
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.image.meta.adobe._8BIM - Type: 8BIM
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.image.meta.adobe._8BIM - Name: 
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.image.meta.adobe._8BIM - Size: 15
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.image.meta.iptc.IPTCDataSet - Record number 2: Application Record
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.image.meta.iptc.IPTCDataSet - Dataset name: ObjectName
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.image.meta.iptc.IPTCDataSet - Dataset tag: 5[0x0005]
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.image.meta.iptc.IPTCDataSet - Dataset size: 5
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.image.meta.iptc.IPTCDataSet - Dataset value: title
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.image.meta.adobe.IRB - <<Adobe IRB information ends>>
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.test.TestMetadata - -----------------------------------------
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.test.TestMetadata - Metadata entry 1 - IPTC
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.image.meta.iptc.IPTCDataSet - Record number 2: Application Record
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.image.meta.iptc.IPTCDataSet - Dataset name: ObjectName
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.image.meta.iptc.IPTCDataSet - Dataset tag: 5[0x0005]
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.image.meta.iptc.IPTCDataSet - Dataset size: 5
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.image.meta.iptc.IPTCDataSet - Dataset value: title
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.test.TestMetadata - -----------------------------------------
2017-01-04 14:15:44,004 [main] INFO  com.icafe4j.test.TestMetadata - Metadata entry 2 - XMP
2017-01-04 14:15:44,010 [main] INFO  com.icafe4j.string.XMLUtils - 
<?xpacket begin="п»ї" id="W5M0MpCehiHzreSzNTczkc9d"?>
<x:xmpmeta x:xmptk='Adobe XMP Core 5.1.0-jc003' xmlns:x='adobe:ns:meta/'>
    <rdf:RDF xmlns:rdf='http://www.w3.org/1999/02/22-rdf-syntax-ns#'>
        <rdf:Description rdf:about='' xmlns:dc='http://purl.org/dc/elements/1.1/'>
            <dc:title0>
                <rdf:Bag>
                    <rdf:li>
                        title
                    </rdf:li>
                </rdf:Bag>
            </dc:title0>
            <dc:subject>
                <rdf:Bag>
                    <rdf:li>
                    </rdf:li>
                </rdf:Bag>
            </dc:subject>
        </rdf:Description>
    </rdf:RDF>
</x:xmpmeta>
<?xpacket end="w"?>

2017-01-04 14:15:44,010 [main] INFO  com.icafe4j.test.TestMetadata - -----------------------------------------
2017-01-04 14:15:44,011 [main] INFO  com.icafe4j.test.TestMetadata - Metadata entry 3 - JPG_JFIF
2017-01-04 14:15:44,011 [main] INFO  com.icafe4j.image.meta.jpeg.JFIFSegment - JPEG JFIF output starts =>
2017-01-04 14:15:44,011 [main] INFO  com.icafe4j.image.meta.jpeg.JFIFSegment - Version: 1.1
2017-01-04 14:15:44,011 [main] INFO  com.icafe4j.image.meta.jpeg.JFIFSegment - Density unit: Dots per inch
2017-01-04 14:15:44,011 [main] INFO  com.icafe4j.image.meta.jpeg.JFIFSegment - XDensity: 96
2017-01-04 14:15:44,011 [main] INFO  com.icafe4j.image.meta.jpeg.JFIFSegment - YDensity: 96
2017-01-04 14:15:44,011 [main] INFO  com.icafe4j.image.meta.jpeg.JFIFSegment - Thumbnail width: 0
2017-01-04 14:15:44,011 [main] INFO  com.icafe4j.image.meta.jpeg.JFIFSegment - Thumbnail height: 0
2017-01-04 14:15:44,011 [main] INFO  com.icafe4j.image.meta.jpeg.JFIFSegment - <= JPEG JFIF output ends
2017-01-04 14:15:44,011 [main] INFO  com.icafe4j.test.TestMetadata - -----------------------------------------
2017-01-04 14:15:44,011 [main] INFO  com.icafe4j.test.TestMetadata - Metadata entry 4 - IMAGE
2017-01-04 14:15:44,011 [main] INFO  com.icafe4j.string.XMLUtils - 

2017-01-04 14:15:44,011 [main] INFO  com.icafe4j.test.TestMetadata - -----------------------------------------
2017-01-04 14:15:44,011 [main] INFO  com.icafe4j.test.TestMetadata - End of metadata information.
sinedsem commented 7 years ago

@dragon66 hello. I have already been using your fix for about 12 hours :-) All works fine. Thanks.