From 42443b4c2e23c2bed2b53208ea7ccb5683a8f254 Mon Sep 17 00:00:00 2001 From: David Carlier Date: Sat, 20 Apr 2024 15:40:01 +0100 Subject: [PATCH] ext/session: fix _read/_write buffer limit. MSDN pages mention the buffer size upper limit is INT_MAX not UINT_MAX. inspired by GH-13205. Close GH-14017 --- NEWS | 1 + ext/session/mod_files.c | 9 +++++---- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/NEWS b/NEWS index 4b1a4aa8fe8..9a6bf178e8d 100644 --- a/NEWS +++ b/NEWS @@ -58,6 +58,7 @@ PHP NEWS ext/session/mod_files.c). (nielsdos) . Fixed bug GH-13891 (memleak and segfault when using ini_set with session.trans_sid_hosts). (nielsdos, kamil-tekiela) + . Fixed buffer _read/_write size limit on windows for the file mode. (David Carlier) - Streams: . Fixed file_get_contents() on Windows fails with "errno=22 Invalid diff --git a/ext/session/mod_files.c b/ext/session/mod_files.c index e640f96f932..9396f16b935 100644 --- a/ext/session/mod_files.c +++ b/ext/session/mod_files.c @@ -86,6 +86,7 @@ # ifndef O_NOFOLLOW # define O_NOFOLLOW 0 # endif +#define SESS_FILE_BUF_SIZE(sz) ((unsigned int)(sz > INT_MAX ? INT_MAX : (unsigned int)sz)) #endif typedef struct { @@ -246,7 +247,7 @@ static zend_result ps_files_write(ps_files *data, zend_string *key, zend_string lseek(data->fd, 0, SEEK_SET); #ifdef PHP_WIN32 { - unsigned int to_write = ZSTR_LEN(val) > UINT_MAX ? UINT_MAX : (unsigned int)ZSTR_LEN(val); + unsigned int to_write = SESS_FILE_BUF_SIZE(ZSTR_LEN(val)); char *buf = ZSTR_VAL(val); int wrote; @@ -255,7 +256,7 @@ static zend_result ps_files_write(ps_files *data, zend_string *key, zend_string n += wrote; buf = wrote > -1 ? buf + wrote : 0; - to_write = wrote > -1 ? (ZSTR_LEN(val) - n > UINT_MAX ? UINT_MAX : (unsigned int)(ZSTR_LEN(val) - n)): 0; + to_write = wrote > -1 ? SESS_FILE_BUF_SIZE(ZSTR_LEN(val) - n) : 0; } while(wrote > 0); } @@ -493,7 +494,7 @@ PS_READ_FUNC(files) lseek(data->fd, 0, SEEK_SET); #ifdef PHP_WIN32 { - unsigned int to_read = ZSTR_LEN(*val) > UINT_MAX ? UINT_MAX : (unsigned int)ZSTR_LEN(*val); + unsigned int to_read = SESS_FILE_BUF_SIZE(ZSTR_LEN(*val)); char *buf = ZSTR_VAL(*val); int read_in; @@ -502,7 +503,7 @@ PS_READ_FUNC(files) n += read_in; buf = read_in > -1 ? buf + read_in : 0; - to_read = read_in > -1 ? (ZSTR_LEN(*val) - n > UINT_MAX ? UINT_MAX : (unsigned int)(ZSTR_LEN(*val) - n)): 0; + to_read = read_in > -1 ? SESS_FILE_BUF_SIZE(ZSTR_LEN(*val) - n) : 0; } while(read_in > 0);