mirror of
https://github.com/php/php-src.git
synced 2024-11-23 09:54:15 +08:00
Fix GH-15980: Signed integer overflow in main/streams/streams.c
We need to avoid signed integer overflows which are undefined behavior. We catch that, and set `offset` to `ZEND_LONG_MAX` (which is also the largest value of `zend_off_t` on all platforms). Of course, after such a seek a stream is no longer readable, but that matches the current behavior for offsets near `ZEND_LONG_MAX`. Closes GH-15989.
This commit is contained in:
parent
f303840a86
commit
6a04c79e41
2
NEWS
2
NEWS
@ -29,6 +29,8 @@ PHP NEWS
|
||||
- Streams:
|
||||
. Fixed bugs GH-15908 and GH-15026 (leak / assertion failure in streams.c).
|
||||
(nielsdos)
|
||||
. Fixed bug GH-15980 (Signed integer overflow in main/streams/streams.c).
|
||||
(cmb)
|
||||
|
||||
- TSRM:
|
||||
. Prevent closing of unrelated handles. (cmb)
|
||||
|
11
ext/standard/tests/streams/gh15980.phpt
Normal file
11
ext/standard/tests/streams/gh15980.phpt
Normal file
@ -0,0 +1,11 @@
|
||||
--TEST--
|
||||
GH-15980 (Signed integer overflow in main/streams/streams.c)
|
||||
--FILE--
|
||||
<?php
|
||||
$s = fopen(__FILE__, "r");
|
||||
fseek($s, 1);
|
||||
fseek($s, PHP_INT_MAX, SEEK_CUR);
|
||||
var_dump(ftell($s) > 1);
|
||||
?>
|
||||
--EXPECT--
|
||||
bool(true)
|
@ -1354,8 +1354,13 @@ PHPAPI int _php_stream_seek(php_stream *stream, zend_off_t offset, int whence)
|
||||
|
||||
switch(whence) {
|
||||
case SEEK_CUR:
|
||||
offset = stream->position + offset;
|
||||
whence = SEEK_SET;
|
||||
ZEND_ASSERT(stream->position >= 0);
|
||||
if (UNEXPECTED(offset > ZEND_LONG_MAX - stream->position)) {
|
||||
offset = ZEND_LONG_MAX;
|
||||
} else {
|
||||
offset = stream->position + offset;
|
||||
}
|
||||
whence = SEEK_SET;
|
||||
break;
|
||||
}
|
||||
ret = stream->ops->seek(stream, offset, whence, &stream->position);
|
||||
|
Loading…
Reference in New Issue
Block a user