Skip to content

Commit 7fb97a1

Browse files
authored
Merge pull request trippo#539 from slimtim/issue_538
Improve memory usage estimates
2 parents ad3d459 + 0d5cec5 commit 7fb97a1

File tree

2 files changed

+103
-5
lines changed

2 files changed

+103
-5
lines changed
Lines changed: 75 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,75 @@
1+
<?php
2+
/**
3+
* Licensed under the Apache License, Version 2.0 (the "License");
4+
* you may not use this file except in compliance with the License.
5+
* You may obtain a copy of the License at
6+
* http://www.apache.org/licenses/LICENSE-2.0
7+
* Unless required by applicable law or agreed to in writing, software
8+
* distributed under the License is distributed on an "AS IS" BASIS,
9+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
10+
* See the License for the specific language governing permissions and
11+
* limitations under the License
12+
*
13+
* This code was originally taken from:
14+
* https://github.com/ktomk/Miscellaneous/blob/master/get_png_imageinfo/get_png_imageinfo.php
15+
* It has been modified to fix bugs and improve code formatting
16+
*
17+
* Get image-information from PNG file
18+
*
19+
* php's getimagesize does not support additional image information
20+
* from PNG files like channels or bits.
21+
*
22+
* get_png_imageinfo() can be used to obtain this information
23+
* from PNG files.
24+
*
25+
* @author Tom Klingenberg <lastflood.net>
26+
* @license Apache 2.0
27+
* @link https://github.com/ktomk/Miscellaneous/blob/master/get_png_imageinfo/get_png_imageinfo.php
28+
* @link http://www.libpng.org/pub/png/spec/iso/index-object.html#11IHDR
29+
*
30+
* @param string $file filename
31+
* @return array|bool image information, FALSE on error
32+
*/
33+
function get_png_imageinfo($file) {
34+
if (! is_file($file)) {
35+
return false;
36+
}
37+
38+
$info = unpack(
39+
'a8sig/Nchunksize/A4chunktype/Nwidth/Nheight/Cbit-depth/Ccolor/Ccompression/Cfilter/Cinterface',
40+
file_get_contents($file, 0, null, 0, 29)
41+
);
42+
43+
if (empty($info)) {
44+
return false;
45+
}
46+
if ("\x89\x50\x4E\x47\x0D\x0A\x1A\x0A" != array_shift($info)) {
47+
return false; // no PNG signature
48+
}
49+
if (13 != array_shift($info)) {
50+
return false; // wrong length for IHDR chunk
51+
}
52+
if ('IHDR'!==array_shift($info)) {
53+
return false; // a non-IHDR chunk singals invalid data
54+
}
55+
56+
$color = $info['color'];
57+
$type = array(
58+
0 => 'Greyscale',
59+
2 => 'Truecolour',
60+
3 => 'Indexed-colour',
61+
4 => 'Greyscale with alpha',
62+
6 => 'Truecolour with alpha'
63+
);
64+
65+
if (empty($type[$color])) {
66+
return false; // invalid color value
67+
}
68+
69+
$info['color-type'] = $type[$color];
70+
$samples = ((($color % 4) % 3) ? 3 : 1) + ($color > 3 ? 1 : 0);
71+
$info['channels'] = $samples;
72+
$info['bits'] = $info['bit-depth'];
73+
74+
return $info;
75+
}

filemanager/include/utils.php

Lines changed: 28 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -844,16 +844,39 @@ function image_check_memory_usage($img, $max_breedte, $max_hoogte)
844844
$memory_limit = abs(intval(str_replace(array('G'), '', $mem) * 1024 * 1024 * 1024));
845845
}
846846

847-
$image_properties = getimagesize($img);
847+
if (($image_properties = getimagesize($img)) === false) {
848+
return false;
849+
}
848850
$image_width = $image_properties[0];
849851
$image_height = $image_properties[1];
852+
853+
if ($image_properties[2] == IMAGETYPE_PNG) {
854+
// PHP's getimagesize() doesn't return the number of channels for PNG files
855+
require_once __DIR__ . '/get_png_imageinfo.php';
856+
if ($png_properties = get_png_imageinfo($img)) {
857+
$image_properties['bits'] = $png_properties['bits'];
858+
$image_properties['channels'] = $png_properties['channels'];
859+
}
860+
}
861+
862+
$image_bits = 0;
863+
$image_channels = 0;
850864
if (isset($image_properties['bits'])) {
851865
$image_bits = $image_properties['bits'];
852-
} else {
853-
$image_bits = 0;
866+
$image_channels = isset($image_properties['channels']) ? $image_properties['channels'] : 1;
854867
}
855-
$image_memory_usage = $K64 + ($image_width * $image_height * ($image_bits >> 3) * 2);
856-
$thumb_memory_usage = $K64 + ($max_breedte * $max_hoogte * ($image_bits >> 3) * 2);
868+
869+
if ($image_properties[2] == IMAGETYPE_GIF) {
870+
// GIF supports up to 8 bits per pixel
871+
if (empty($image_bits)) {
872+
$image_bits = 8;
873+
}
874+
// GIF uses indexed color which obviates channels
875+
$image_channels = 1;
876+
}
877+
878+
$image_memory_usage = $K64 + ($image_width * $image_height * ($image_bits * $image_channels / 8) * 2);
879+
$thumb_memory_usage = $K64 + ($max_breedte * $max_hoogte * ($image_bits * $image_channels / 8) * 2);
857880
$memory_needed = abs(intval($memory_usage + $image_memory_usage + $thumb_memory_usage));
858881

859882
if ($memory_needed > $memory_limit) {

0 commit comments

Comments
 (0)