diff options
| author | Christopher Jones <sixd@php.net> | 2013-09-18 19:49:40 -0700 |
|---|---|---|
| committer | Christopher Jones <sixd@php.net> | 2013-09-18 19:49:40 -0700 |
| commit | 3d165224da8b814b1a97f9ff02d27914a70b1f3f (patch) | |
| tree | ee96648a25758e87faedb63c686d1177c6304970 /ext/standard/php_fopen_wrapper.c | |
| parent | b740bfc741d127349a6e7e27b65e7e2706c1033d (diff) | |
| parent | 86dfe7be49a674358e69003413c4a48bee3463ed (diff) | |
| download | php-git-3d165224da8b814b1a97f9ff02d27914a70b1f3f.tar.gz | |
Merge branch 'master' of https://git.php.net/repository/php-src
# By Michael Wallner (18) and others
# Via David Soria Parra (8) and others
* 'master' of https://git.php.net/repository/php-src: (37 commits)
better way to fix PRIu64 availability on windows
Revert "EmptyIterator now implements Countable; fixes bug 60577"
RFC 6598 reserved ip range starts at 100.64.0.0
fix a very rare case of use of uninitialized value combined with a memleak
fix test concurrency
fix test concurrency
fix test concurrency
fix test concurrency
fix test concurrency
fix build - PRIu64 vs %I64u
final bits
we need to use the full stream wrapper for filters
let the libsqlite3 symbols be exported in dll
NEWS/UPGRADING{,.INTERNALS} notes about temp POST stream
Exclude bison 3.0 by Mike
NEWS for added reserved ip addresses according to RFC 6598
Add RFC 6598 IPs to reserved addresses
upload2G note
NEWS for #60577
NEWS for bug #64441
...
Diffstat (limited to 'ext/standard/php_fopen_wrapper.c')
| -rw-r--r-- | ext/standard/php_fopen_wrapper.c | 84 |
1 files changed, 54 insertions, 30 deletions
diff --git a/ext/standard/php_fopen_wrapper.c b/ext/standard/php_fopen_wrapper.c index 0fb27baacd..76f77ebf7b 100644 --- a/ext/standard/php_fopen_wrapper.c +++ b/ext/standard/php_fopen_wrapper.c @@ -63,6 +63,12 @@ php_stream_ops php_stream_output_ops = { NULL /* set_option */ }; +typedef struct php_stream_input { /* {{{ */ + php_stream **body_ptr; + off_t position; +} php_stream_input_t; +/* }}} */ + static size_t php_stream_input_write(php_stream *stream, const char *buf, size_t count TSRMLS_DC) /* {{{ */ { return -1; @@ -71,42 +77,36 @@ static size_t php_stream_input_write(php_stream *stream, const char *buf, size_t static size_t php_stream_input_read(php_stream *stream, char *buf, size_t count TSRMLS_DC) /* {{{ */ { - off_t *position = (off_t*)stream->abstract; - size_t read_bytes = 0; - - if (!stream->eof) { - if (SG(request_info).raw_post_data) { /* data has already been read by a post handler */ - read_bytes = SG(request_info).raw_post_data_length - *position; - if (read_bytes <= count) { - stream->eof = 1; - } else { - read_bytes = count; - } - if (read_bytes) { - memcpy(buf, SG(request_info).raw_post_data + *position, read_bytes); - } - } else if (sapi_module.read_post) { - read_bytes = sapi_module.read_post(buf, count TSRMLS_CC); - if (read_bytes <= 0) { - stream->eof = 1; - read_bytes = 0; - } - /* Increment SG(read_post_bytes) only when something was actually read. */ - SG(read_post_bytes) += read_bytes; - } else { - stream->eof = 1; + php_stream_input_t *input = stream->abstract; + size_t read; + + if (!SG(post_read) && SG(read_post_bytes) < input->position + count) { + /* read requested data from SAPI */ + int read_bytes = sapi_read_post_block(buf, count TSRMLS_CC); + + if (read_bytes > 0) { + php_stream_seek(*input->body_ptr, 0, SEEK_END); + php_stream_write(*input->body_ptr, buf, read_bytes); } } - *position += read_bytes; + php_stream_seek(*input->body_ptr, input->position, SEEK_SET); + read = php_stream_read(*input->body_ptr, buf, count); + + if (!read || read == (size_t) -1) { + stream->eof = 1; + } else { + input->position += read; + } - return read_bytes; + return read; } /* }}} */ static int php_stream_input_close(php_stream *stream, int close_handle TSRMLS_DC) /* {{{ */ { efree(stream->abstract); + stream->abstract = NULL; return 0; } @@ -118,13 +118,27 @@ static int php_stream_input_flush(php_stream *stream TSRMLS_DC) /* {{{ */ } /* }}} */ +static int php_stream_input_seek(php_stream *stream, off_t offset, int whence, off_t *newoffset TSRMLS_DC) /* {{{ */ +{ + php_stream *inner = stream->abstract; + + if (inner) { + int sought = php_stream_seek(inner, offset, whence); + *newoffset = inner->position; + return sought; + } + + return -1; +} +/* }}} */ + php_stream_ops php_stream_input_ops = { php_stream_input_write, php_stream_input_read, php_stream_input_close, php_stream_input_flush, "Input", - NULL, /* seek */ + php_stream_input_seek, NULL, /* cast */ NULL, /* stat */ NULL /* set_option */ @@ -204,13 +218,23 @@ php_stream * php_stream_url_wrap_php(php_stream_wrapper *wrapper, const char *pa } if (!strcasecmp(path, "input")) { + php_stream_input_t *input; + if ((options & STREAM_OPEN_FOR_INCLUDE) && !PG(allow_url_include) ) { if (options & REPORT_ERRORS) { php_error_docref(NULL TSRMLS_CC, E_WARNING, "URL file-access is disabled in the server configuration"); } return NULL; } - return php_stream_alloc(&php_stream_input_ops, ecalloc(1, sizeof(off_t)), 0, "rb"); + + input = ecalloc(1, sizeof(*input)); + if (*(input->body_ptr = &SG(request_info).request_body)) { + php_stream_rewind(*input->body_ptr); + } else { + *input->body_ptr = php_stream_temp_create(TEMP_STREAM_DEFAULT, SAPI_POST_BLOCK_SIZE); + } + + return php_stream_alloc(&php_stream_input_ops, input, 0, "rb"); } if (!strcasecmp(path, "stdin")) { @@ -259,8 +283,8 @@ php_stream * php_stream_url_wrap_php(php_stream_wrapper *wrapper, const char *pa fd = dup(STDERR_FILENO); } } else if (!strncasecmp(path, "fd/", 3)) { - char *start, - *end; + const char *start; + char *end; long fildes_ori; int dtablesize; |
