diff options
Diffstat (limited to 'main/streams')
-rw-r--r-- | main/streams/php_stream_transport.h | 35 | ||||
-rw-r--r-- | main/streams/plain_wrapper.c | 12 | ||||
-rw-r--r-- | main/streams/streams.c | 61 | ||||
-rw-r--r-- | main/streams/xp_socket.c | 3 |
4 files changed, 66 insertions, 45 deletions
diff --git a/main/streams/php_stream_transport.h b/main/streams/php_stream_transport.h index c599a65d0f..dc10eb4e92 100644 --- a/main/streams/php_stream_transport.h +++ b/main/streams/php_stream_transport.h @@ -163,23 +163,30 @@ typedef struct _php_stream_xport_param { } outputs; } php_stream_xport_param; - -/* These functions provide crypto support on the underlying transport */ +/* Because both client and server streams use the same mechanisms + for encryption we use the LSB to denote clients. +*/ typedef enum { - STREAM_CRYPTO_METHOD_SSLv2_CLIENT, - STREAM_CRYPTO_METHOD_SSLv3_CLIENT, - STREAM_CRYPTO_METHOD_SSLv23_CLIENT, - STREAM_CRYPTO_METHOD_TLS_CLIENT, - STREAM_CRYPTO_METHOD_TLSv1_1_CLIENT, - STREAM_CRYPTO_METHOD_TLSv1_2_CLIENT, - STREAM_CRYPTO_METHOD_SSLv2_SERVER, - STREAM_CRYPTO_METHOD_SSLv3_SERVER, - STREAM_CRYPTO_METHOD_SSLv23_SERVER, - STREAM_CRYPTO_METHOD_TLS_SERVER, - STREAM_CRYPTO_METHOD_TLSv1_1_SERVER, - STREAM_CRYPTO_METHOD_TLSv1_2_SERVER + STREAM_CRYPTO_METHOD_SSLv2_CLIENT = (1 << 1 | 1), + STREAM_CRYPTO_METHOD_SSLv3_CLIENT = (1 << 2 | 1), + STREAM_CRYPTO_METHOD_SSLv23_CLIENT = ((1 << 1) | (1 << 2) | 1), + STREAM_CRYPTO_METHOD_TLSv1_0_CLIENT = (1 << 3 | 1), + STREAM_CRYPTO_METHOD_TLSv1_1_CLIENT = (1 << 4 | 1), + STREAM_CRYPTO_METHOD_TLSv1_2_CLIENT = (1 << 5 | 1), + STREAM_CRYPTO_METHOD_TLS_CLIENT = ((1 << 3) | (1 << 4) | (1 << 5) | 1), + STREAM_CRYPTO_METHOD_ANY_CLIENT = ((1 << 1) | (1 << 2) | (1 << 3) | (1 << 4) | (1 << 5) | 1), + STREAM_CRYPTO_METHOD_SSLv2_SERVER = (1 << 1), + STREAM_CRYPTO_METHOD_SSLv3_SERVER = (1 << 2), + STREAM_CRYPTO_METHOD_SSLv23_SERVER = ((1 << 1) | (1 << 2)), + STREAM_CRYPTO_METHOD_TLSv1_0_SERVER = (1 << 3), + STREAM_CRYPTO_METHOD_TLSv1_1_SERVER = (1 << 4), + STREAM_CRYPTO_METHOD_TLSv1_2_SERVER = (1 << 5), + STREAM_CRYPTO_METHOD_TLS_SERVER = ((1 << 3) | (1 << 4) | (1 << 5)), + STREAM_CRYPTO_METHOD_ANY_SERVER = ((1 << 1) | (1 << 2) | (1 << 3) | (1 << 4) | (1 << 5)) } php_stream_xport_crypt_method_t; +/* These functions provide crypto support on the underlying transport */ + BEGIN_EXTERN_C() PHPAPI int php_stream_xport_crypto_setup(php_stream *stream, php_stream_xport_crypt_method_t crypto_method, php_stream *session_stream TSRMLS_DC); PHPAPI int php_stream_xport_crypto_enable(php_stream *stream, int activate TSRMLS_DC); diff --git a/main/streams/plain_wrapper.c b/main/streams/plain_wrapper.c index 6ddfc74a11..5e9e5c7ace 100644 --- a/main/streams/plain_wrapper.c +++ b/main/streams/plain_wrapper.c @@ -482,7 +482,7 @@ static int php_stdiop_seek(php_stream *stream, off_t offset, int whence, off_t * static int php_stdiop_cast(php_stream *stream, int castas, void **ret TSRMLS_DC) { - int fd; + php_socket_t fd; php_stdio_stream_data *data = (php_stdio_stream_data*) stream->abstract; assert(data != NULL); @@ -506,31 +506,31 @@ static int php_stdiop_cast(php_stream *stream, int castas, void **ret TSRMLS_DC) } *(FILE**)ret = data->file; - data->fd = -1; + data->fd = SOCK_ERR; } return SUCCESS; case PHP_STREAM_AS_FD_FOR_SELECT: PHP_STDIOP_GET_FD(fd, data); - if (fd < 0) { + if (SOCK_ERR == fd) { return FAILURE; } if (ret) { - *(int*)ret = fd; + *(php_socket_t *)ret = fd; } return SUCCESS; case PHP_STREAM_AS_FD: PHP_STDIOP_GET_FD(fd, data); - if (fd < 0) { + if (SOCK_ERR == fd) { return FAILURE; } if (data->file) { fflush(data->file); } if (ret) { - *(int*)ret = fd; + *(php_socket_t *)ret = fd; } return SUCCESS; default: diff --git a/main/streams/streams.c b/main/streams/streams.c index 7ab74c7c08..0889bd57a7 100644 --- a/main/streams/streams.c +++ b/main/streams/streams.c @@ -728,6 +728,10 @@ PHPAPI size_t _php_stream_read(php_stream *stream, char *buf, size_t size TSRMLS if (!stream->readfilters.head && (stream->flags & PHP_STREAM_FLAG_NO_BUFFER || stream->chunk_size == 1)) { toread = stream->ops->read(stream, buf, size TSRMLS_CC); + if (toread == (size_t) -1) { + /* e.g. underlying read(2) returned -1 */ + break; + } } else { php_stream_fill_read_buffer(stream, size TSRMLS_CC); @@ -1393,11 +1397,16 @@ PHPAPI size_t _php_stream_passthru(php_stream * stream STREAMS_DC TSRMLS_DC) p = php_stream_mmap_range(stream, php_stream_tell(stream), PHP_STREAM_MMAP_ALL, PHP_STREAM_MAP_MODE_SHARED_READONLY, &mapped); if (p) { - PHPWRITE(p, mapped); + do { + /* output functions return int, so pass in int max */ + if (0 < (b = PHPWRITE(p, MIN(mapped - bcount, INT_MAX)))) { + bcount += b; + } + } while (b > 0 && mapped > bcount); php_stream_mmap_unmap_ex(stream, mapped); - return mapped; + return bcount; } } @@ -1912,16 +1921,18 @@ PHPAPI int _php_stream_stat_path(const char *path, int flags, php_stream_statbuf const char *path_to_open = path; int ret; - /* Try to hit the cache first */ - if (flags & PHP_STREAM_URL_STAT_LINK) { - if (BG(CurrentLStatFile) && strcmp(path, BG(CurrentLStatFile)) == 0) { - memcpy(ssb, &BG(lssb), sizeof(php_stream_statbuf)); - return 0; - } - } else { - if (BG(CurrentStatFile) && strcmp(path, BG(CurrentStatFile)) == 0) { - memcpy(ssb, &BG(ssb), sizeof(php_stream_statbuf)); - return 0; + if (!(flags & PHP_STREAM_URL_STAT_NOCACHE)) { + /* Try to hit the cache first */ + if (flags & PHP_STREAM_URL_STAT_LINK) { + if (BG(CurrentLStatFile) && strcmp(path, BG(CurrentLStatFile)) == 0) { + memcpy(ssb, &BG(lssb), sizeof(php_stream_statbuf)); + return 0; + } + } else { + if (BG(CurrentStatFile) && strcmp(path, BG(CurrentStatFile)) == 0) { + memcpy(ssb, &BG(ssb), sizeof(php_stream_statbuf)); + return 0; + } } } @@ -1929,19 +1940,21 @@ PHPAPI int _php_stream_stat_path(const char *path, int flags, php_stream_statbuf if (wrapper && wrapper->wops->url_stat) { ret = wrapper->wops->url_stat(wrapper, path_to_open, flags, ssb, context TSRMLS_CC); if (ret == 0) { - /* Drop into cache */ - if (flags & PHP_STREAM_URL_STAT_LINK) { - if (BG(CurrentLStatFile)) { - efree(BG(CurrentLStatFile)); - } - BG(CurrentLStatFile) = estrdup(path); - memcpy(&BG(lssb), ssb, sizeof(php_stream_statbuf)); - } else { - if (BG(CurrentStatFile)) { - efree(BG(CurrentStatFile)); + if (!(flags & PHP_STREAM_URL_STAT_NOCACHE)) { + /* Drop into cache */ + if (flags & PHP_STREAM_URL_STAT_LINK) { + if (BG(CurrentLStatFile)) { + efree(BG(CurrentLStatFile)); + } + BG(CurrentLStatFile) = estrdup(path); + memcpy(&BG(lssb), ssb, sizeof(php_stream_statbuf)); + } else { + if (BG(CurrentStatFile)) { + efree(BG(CurrentStatFile)); + } + BG(CurrentStatFile) = estrdup(path); + memcpy(&BG(ssb), ssb, sizeof(php_stream_statbuf)); } - BG(CurrentStatFile) = estrdup(path); - memcpy(&BG(ssb), ssb, sizeof(php_stream_statbuf)); } } return ret; diff --git a/main/streams/xp_socket.c b/main/streams/xp_socket.c index 0f2e530aa7..9e1521b537 100644 --- a/main/streams/xp_socket.c +++ b/main/streams/xp_socket.c @@ -588,7 +588,8 @@ static inline int php_tcp_sockop_bind(php_stream *stream, php_netstream_data_t * parse_unix_address(xparam, &unix_addr TSRMLS_CC); - return bind(sock->socket, (struct sockaddr *)&unix_addr, sizeof(unix_addr)); + return bind(sock->socket, (const struct sockaddr *)&unix_addr, + (socklen_t) XtOffsetOf(struct sockaddr_un, sun_path) + xparam->inputs.namelen); } #endif |