Bug #77546 [Com]: iptcembed broken function

From: Date: Fri, 08 Feb 2019 05:06:13 +0000
Subject: Bug #77546 [Com]: iptcembed broken function
References: 1  Groups: php.bugs 
Request: Send a blank email to php-bugs+get-219422@lists.php.net to get a copy of this message
Edit report at https://bugs.php.net/bug.php?id=77546&edit=1

 ID:                 77546
 Comment by:         imagevuex at gmail dot com
 Reported by:        php at degoulet dot net
 Summary:            iptcembed broken function
 Status:             Closed
 Type:               Bug
 Package:            *Graphics related
 Operating System:   linux
 PHP Version:        7.3.1
 Block user comment: N
 Private report:     N

 New Comment:

Temporary solution, check if the image stream is valid with getimagesizefromstring() before writing
to file:

$content = iptcembed($iptc, $file,0);
if($content && @getimagesizefromstring($content)) // is valid


Previous Comments:
------------------------------------------------------------------------
[2019-02-06 07:48:36] imagevuex at gmail dot com

+1

PHP 7.3 breaks our gallery app as iptcembed() is corrupting JPG images (getimagesize error). Looking
forward to see this fixed.

------------------------------------------------------------------------
[2019-01-30 16:11:23] krakjoe@php.net

Automatic comment on behalf of g.degoulet@of2m.fr
Revision: http://git.php.net/?p=php-src.git;a=commit;h=f27f9022660d28c13c6209f4679768dcbd961b43
Log: Fix #77546 iptcembed broken function

------------------------------------------------------------------------
[2019-01-30 10:42:24] 

The following pull request has been associated:

Patch Name: bug: https://bugs.php.net/bug.php?id=77546
On GitHub:  https://github.com/php/php-src/pull/3774
Patch:      https://github.com/php/php-src/pull/3774.patch

------------------------------------------------------------------------
[2019-01-30 10:24:00] php at degoulet dot net

Description:
------------
iptcembed ( string $iptcdata , string $jpeg_file_name [, int $spool = 0 ] ) : mixed

when spool is < 2, this function should return a valid jpeg stream content.
on php 7.3 branch, sometime the stream is not valid : this bug this to be related to this commit https://github.com/php/php-src/commit/4fbff82c1079f2c48c769c94f0d9269be7508a59#diff-98113f2c152c3d95d366989462658a39

ext/standard/iptc.c +278

actual code
psheader[ 2 ] = (char) (iptcdata_len+28)>>8;

patch
psheader[ 2 ] = (char) ((iptcdata_len+28)>>8);


Test script:
---------------
<?php
/*
$file="1x1.jpg";
$ret=imagejpeg(imagecreatetruecolor(1, 1), $file, 100);
echo md5(file_get_contents($file)).PHP_EOL;
echo base64_encode(file_get_contents($file)).PHP_EOL;
unlink($file);
*/

function iptc_make_tag($rec, $data, $value)
  {
    $length = strlen($value);
    $retval = chr(0x1C) . chr($rec) . chr($data);
    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); }
    return $retval . $value;
  }


$file="1x1.jpg";
$file2="1x1_with_iptc_tags.jpg";
$base64_1x1_jpeg="/9j/4AAQSkZJRgABAQEAYABgAAD//gA8Q1JFQVRPUjogZ2QtanBlZyB2MS4wICh1c2luZyBJSkcgSlBFRyB2ODApLCBxdWFsaXR5ID0gMTAwCv/bAEMAAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAf/bAEMBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAf/AABEIAAEAAQMBEQACEQEDEQH/xAAfAAABBQEBAQEBAQAAAAAAAAAAAQIDBAUGBwgJCgv/xAC1EAACAQMDAgQDBQUEBAAAAX0BAgMABBEFEiExQQYTUWEHInEUMoGRoQgjQrHBFVLR8CQzYnKCCQoWFxgZGiUmJygpKjQ1Njc4OTpDREVGR0hJSlNUVVZXWFlaY2RlZmdoaWpzdHV2d3h5eoOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3uLm6wsPExcbHyMnK0tPU1dbX2Nna4eLj5OXm5+jp6vHy8/T19vf4+fr/xAAfAQADAQEBAQEBAQEBAAAAAAAAAQIDBAUGBwgJCgv/xAC1EQACAQIEBAMEBwUEBAABAncAAQIDEQQFITEGEkFRB2FxEyIygQgUQpGhscEJIzNS8BVictEKFiQ04SXxFxgZGiYnKCkqNTY3ODk6Q0RFRkdISUpTVFVWV1hZWmNkZWZnaGlqc3R1dnd4eXqCg4SFhoeIiYqSk5SVlpeYmZqio6Slpqeoqaqys7S1tre4ubrCw8TFxsfIycrS09TV1tfY2dri4+Tl5ufo6ery8/T19vf4+fr/2gAMAwEAAhEDEQA/AP8AP/oA/9k=";
#write file
$fd=fopen($file,"wb");
if ($fd) { fputs($fd,base64_decode($base64_1x1_jpeg)); fclose($fd); }
#check file md5
$md5=md5_file($file);
if ($md5!="07dd8594450e8c18ab8a79d7cb4573c7") { echo "md5
error".PHP_EOL;exit(1); }
#check jpeg properties
list($width, $height, $type, $attr) = getimagesize($file,$info);
if ($width!=1) { echo "width error".PHP_EOL;exit(1); }
if ($height!=1) { echo "height error".PHP_EOL;exit(1); }
if ($type!=2) { echo "type error".PHP_EOL;exit(1); }
if (!isset($info["APP0"])) { echo "APP0 error".PHP_EOL;exit(1); }

#our iptc tags
$tags=array();
$tags["2#105"]= "Tauren";
$tags["2#120"]= "Tauren with Trunk";
$tags["2#110"]= "Copyright 2004-2016, Blizzard";
$tags["2#025"]= "Tauren, Chaman, Blizzard";
$tags["2#090"]= "Thunder Bluffs";
#feed iptc string for iptcembed
$iptc='';
foreach ($tags as $tag => $string) { $rec=$tag[0]; $tag = substr($tag, 2); $iptc .=
iptc_make_tag($rec, $tag, $string); }
#check iptc string md5
if (md5(base64_encode($iptc))!="7056c4b3060f92a4f9e5b7d0caa61859") { echo "iptc md5
error".PHP_EOL;exit(1); }

#
$content = iptcembed($iptc, $file,0);
if ($content === false) {echo "iptcembed error".PHP_EOL;exit(1); }
$fd=fopen($file2,"wb");
if ($fd) { fputs($fd,$content); fclose($fd); }

#check jpeg properties for new image with iptc tags
echo "new generated image with itpc tags : $file2".PHP_EOL;
$ret = getimagesize($file2,$info);
if ($ret===false) { echo "getimagesize error".PHP_EOL;exit(1); }
list($width, $height, $type, $attr) = $ret;
if ($width!=1) { echo "width error".PHP_EOL;exit(1); }
if ($height!=1) { echo "height error".PHP_EOL;exit(1); }
if ($type!=2) { echo "type error".PHP_EOL;exit(1); }
if (!isset($info["APP0"])) { echo "APP0 error".PHP_EOL;exit(1); }
if (!isset($info["APP13"])) { echo "APP13 error".PHP_EOL;exit(1); }

$error=0;
$iptc_data_from_created_image = iptcparse($info['APP13']);
foreach ($tags as $tag => $string) {
  #check if tag exists
  if (!isset($iptc_data_from_created_image[$tag])) {
    echo "error iptc tag $tag not found".PHP_EOL;
    $error++;
  } else {
    #check value
    if ($iptc_data_from_created_image[$tag][0]!=$string) {
      echo "error tag $tag : bad value ($string !=
".$iptc_data_from_created_image[$tag][0].")".PHP_EOL;
      $error++;
    }
  }
}
if ($error==0) { echo "OK".PHP_EOL;exit(0);}
echo "something wrong: $error errors".PHP_EOL;
@unlink($file);
@unlink($file2);
?>

Expected result:
----------------
on php 7.2, my debug script returns


new generated image with itpc tags : 1x1_with_iptc_tags.jpg
OK


Actual result:
--------------
on php 7.3, my debug script returns

generated image : 1x1_with_iptc_tags.jpg
getimagesize error


------------------------------------------------------------------------



--
Edit this bug report at https://bugs.php.net/bug.php?id=77546&edit=1


Thread (7 messages)

« previous php.bugs (#219422) next »