Bug #54173 [Fbk->NoF]: After you write IPTC several times in the same JPEG file, the file is corrupted
| From: | php-bugs at lists dot php dot net | Date: | Sun, 26 Jul 2015 04:22:16 +0000 |
| Subject: | Bug #54173 [Fbk->NoF]: After you write IPTC several times in the same JPEG file, the file is corrupted | ||
| References: | 1 | Groups: | php.bugs |
| Request: | Send a blank email to php-bugs+get-194716@lists.php.net to get a copy of this message | ||
Edit report at https://bugs.php.net/bug.php?id=54173&edit=1
ID: 54173
Updated by: php-bugs@lists.php.net
Reported by: axelgauffre at gmail dot com
Summary: After you write IPTC several times in the same JPEG
file, the file is corrupted
-Status: Feedback
+Status: No Feedback
Type: Bug
Package: GD related
Operating System: Vista 64
PHP Version: 5.3.5
Assigned To: cmb
Private report: N
New Comment:
No feedback was provided. The bug is being suspended because
we assume that you are no longer experiencing the problem.
If this is not the case and you are able to provide the
information that was requested earlier, please do so and
change the status of the bug back to "Re-Opened". Thank you.
Previous Comments:
------------------------------------------------------------------------
[2015-07-18 19:14:18] cmb@php.net
Well, actually I can't confirm this very issue. I'd need
020SC_BF0196D001_M.jpg or some other image that shows this
behavior. Could you please supply a download link to such an
image?
What I can confirm is that there is a superfluous byte added on
repeat calls to iptcembed(), which I reported as bug #70096.
------------------------------------------------------------------------
[2015-07-18 00:11:39] cmb@php.net
Confirmed.
------------------------------------------------------------------------
[2015-07-18 00:11:39] cmb@php.net
Confirmed.
------------------------------------------------------------------------
[2011-03-06 11:27:50] axelgauffre at gmail dot com
Description:
------------
Sometimes writing IPTC in a JPEG file seems to corrupt it.
This behaviour happens after you write several times in the same file (after 10 to
20 times or so...).
The consequence is that the next call to GetImageSize on this file will fail.
I don't know if the problem comes from iptcembed or from GetImageSize.
I am using Wampserver 2 with PHP 5.3.0 on Vista 64.
Test script:
---------------
<?php
$file_path_and_name="020SC_BF0196D001_M.jpg";
$iptc_field_to_modify="2#005";
//Read IPTC from file
if (!GetImageSize($file_path_and_name, $getimagesize_result))
{
echo("GetImageSize error<br />");
die();
}
//Handle return from GetImageSize
if (!isset($getimagesize_result["APP13"]))
$iptc_array=array();
else
{
//Get APP13
$iptcparse_result=iptcparse($getimagesize_result["APP13"]);
if ($iptcparse_result===false)
{
echo("iptcparse error<br />");
die();
}
//Handle iptcparse result
$iptc_array=array();
foreach ($iptcparse_result as $iptcparse_index => &$iptcparse_value)
{
$iptc_array[$iptcparse_index]="";
for($i=0;$i<count($iptcparse_value);$i++)
$iptc_array[$iptcparse_index].=($i<count($iptcparse_value)-1)?$iptcparse_value[$i].",":$iptcparse_value[$i];
}
}
//foreach($iptc_array as $index => $value)
// echo($index." ".$value."<br />");
if (isset($iptc_array["2#005"]))
echo($iptc_array["2#005"]."<br />");
//Modify the value in the IPTC array
$iptc_array[$iptc_field_to_modify]=rand (1, 1000);
//Transform the the IPTC array into a string to be used by iptcembed
$string_for_iptcembed="";
foreach($iptc_array as $iptc_array_index => &$iptc_array_value)
{
$iptc_array_index=substr($iptc_array_index, 2);
$length = strlen($iptc_array_value);
$retval = chr(0x1C).chr(2).chr($iptc_array_index);
if($length < 0x8000)
$retval .= chr($length >> 8).chr($length& 0xFF);
else{
$retval .= chr(0x80).chr(0x04).
chr(($length >> 24)& 0xFF).
chr(($length >> 16)& 0xFF).
chr(($length >> 8)& 0xFF).
chr($length& 0xFF);
}
$string_for_iptcembed.=$retval.$iptc_array_value;
}
//Call to iptcembed
$binary_data=iptcembed($string_for_iptcembed, $file_path_and_name);
if ($binary_data===false)
{
echo("iptcembed error<br />");
die();
}
//TODO ??? It doesn't solve the problem anyway...
//@unlink($file_path_and_name);//delete if exists
//Open file for writing
if (DIRECTORY_SEPARATOR=="/")
$file = fopen($file_path_and_name, "w");//linux
else if (DIRECTORY_SEPARATOR=="\\")
$file = fopen($file_path_and_name, "wb");//windows
if(!$file)
{
echo("fopen error<br />");
die();
}
//Writing
if (false===fwrite($file, $binary_data))
{
echo("fwrite error<br />");
if(fclose($file)===false)
echo("fclose error<br />");
die();
}
//Close file
if(fclose($file)===false)
{
echo("fclose error<br />");
die();
}
//Let's check that everything went fine:
//Sometimes writing IPTC in a JPEG file seems to corrupt it.
//This behaviour happens after you write several times in the same file (after 10 to 20 times or
so...).
//The only solution I found to fix the problem: create a new file with imagecreatefromjpeg. But this
has 2 main inconvenients:
// - it takes long (3 to 4 seconds with a high res file)
// - you loose every other metadata: XMP, EXIF...
if(false===GetImageSize($file_path_and_name, $bogus))
{
echo("!!!!!!!!!!!!!!!!!!!!!! GetImageSize error !!!!!!!!!!!!!!!!!!!!!!!!!!!<br
/>");
$image = imagecreatefromjpeg($file_path_and_name);
if ($image===false)
{
echo("imagecreatefromjpeg error<br />");
die();
}
if (false===imagejpeg($image, $file_path_and_name))
{
echo("imagejpeg error<br />");
die();
}
}
?>
Expected result:
----------------
Each call should do exactly the same as the previous one : read and write IPTC
metadata.
Actual result:
--------------
After several times, GetImageSize returns false.
------------------------------------------------------------------------
--
Edit this bug report at https://bugs.php.net/bug.php?id=54173&edit=1