pollita Fri Nov 28 18:25:29 2003 EDT Modified files: /php-src/ext/libxml libxml.c /php-src/ext/standard basic_functions.h filestat.c ftp_fopen_wrapper.c /php-src/main php_streams.h /php-src/main/streams plain_wrapper.c streams.c /php-src NEWS Log: Route php_stat() via streams/url_stat API (php_stream_stat_path). This enables fopen-wrappers support on stat() and related family calls.
Index: php-src/ext/libxml/libxml.c diff -u php-src/ext/libxml/libxml.c:1.8 php-src/ext/libxml/libxml.c:1.9 --- php-src/ext/libxml/libxml.c:1.8 Fri Nov 7 14:12:46 2003 +++ php-src/ext/libxml/libxml.c Fri Nov 28 18:25:25 2003 @@ -17,7 +17,7 @@ +----------------------------------------------------------------------+ */ -/* $Id: libxml.c,v 1.8 2003/11/07 19:12:46 iliaa Exp $ */ +/* $Id: libxml.c,v 1.9 2003/11/28 23:25:25 pollita Exp $ */ #define IS_EXT_MODULE @@ -253,7 +253,7 @@ in xml processing (eg. DTD files) */ wrapper = php_stream_locate_url_wrapper(resolved_path, &path_to_open, ENFORCE_SAFE_MODE TSRMLS_CC); if (wrapper && wrapper->wops->url_stat) { - if (wrapper->wops->url_stat(wrapper, path_to_open, &ssbuf TSRMLS_CC) == -1) { + if (wrapper->wops->url_stat(wrapper, path_to_open, 0, &ssbuf, NULL TSRMLS_CC) == -1) { return NULL; } } Index: php-src/ext/standard/basic_functions.h diff -u php-src/ext/standard/basic_functions.h:1.129 php-src/ext/standard/basic_functions.h:1.130 --- php-src/ext/standard/basic_functions.h:1.129 Sun Nov 23 20:17:27 2003 +++ php-src/ext/standard/basic_functions.h Fri Nov 28 18:25:26 2003 @@ -17,7 +17,7 @@ +----------------------------------------------------------------------+ */ -/* $Id: basic_functions.h,v 1.129 2003/11/24 01:17:27 iliaa Exp $ */ +/* $Id: basic_functions.h,v 1.130 2003/11/28 23:25:26 pollita Exp $ */ #ifndef BASIC_FUNCTIONS_H #define BASIC_FUNCTIONS_H @@ -170,11 +170,9 @@ long page_inode; long page_mtime; - /* filestat.c */ - char *CurrentStatFile; - php_stat_len CurrentStatLength; - struct stat sb; - struct stat lsb; + /* filestat.c && main/streams/streams.c */ + char *CurrentStatFile, *CurrentLStatFile; + php_stream_statbuf *ssb, *lssb; /* rand.c */ php_uint32 state[MT_N+1]; /* state vector + 1 extra to not violate ANSI C */ Index: php-src/ext/standard/filestat.c diff -u php-src/ext/standard/filestat.c:1.127 php-src/ext/standard/filestat.c:1.128 --- php-src/ext/standard/filestat.c:1.127 Fri Nov 7 04:16:16 2003 +++ php-src/ext/standard/filestat.c Fri Nov 28 18:25:26 2003 @@ -16,7 +16,7 @@ +----------------------------------------------------------------------+ */ -/* $Id: filestat.c,v 1.127 2003/11/07 09:16:16 helly Exp $ */ +/* $Id: filestat.c,v 1.128 2003/11/28 23:25:26 pollita Exp $ */ #include "php.h" #include "safe_mode.h" @@ -99,7 +99,7 @@ PHP_RINIT_FUNCTION(filestat) { BG(CurrentStatFile)=NULL; - BG(CurrentStatLength)=0; + BG(CurrentLStatFile)=NULL; return SUCCESS; } @@ -108,6 +108,9 @@ if (BG(CurrentStatFile)) { efree (BG(CurrentStatFile)); } + if (BG(CurrentLStatFile)) { + efree (BG(CurrentLStatFile)); + } return SUCCESS; } @@ -526,11 +529,16 @@ efree(BG(CurrentStatFile)); BG(CurrentStatFile) = NULL; } + if (BG(CurrentLStatFile)) { + efree(BG(CurrentLStatFile)); + BG(CurrentLStatFile) = NULL; + } } /* }}} */ #define IS_LINK_OPERATION(__t) ((__t) == FS_TYPE || (__t) == FS_IS_LINK || (__t) == FS_LSTAT) #define IS_EXISTS_CHECK(__t) ((__t) == FS_EXISTS || (__t) == FS_IS_W || (__t) == FS_IS_R || (__t) == FS_IS_X || (__t) == FS_IS_FILE || (__t) == FS_IS_DIR || (__t) == FS_IS_LINK) +#define IS_ABLE_CHECK(__t) ((__t) == FS_IS_R || (__t) == FS_IS_W || (__t) == FS_IS_X) /* {{{ php_stat */ @@ -543,6 +551,7 @@ #else struct stat *stat_sb; #endif + php_stream_statbuf ssb; int rmask=S_IROTH, wmask=S_IWOTH, xmask=S_IXOTH; /* access rights defaults to other */ char *stat_sb_names[13]={"dev", "ino", "mode", "nlink", "uid", "gid", "rdev", "size", "atime", "mtime", "ctime", "blksize", "blocks"}; @@ -559,65 +568,25 @@ RETURN_FALSE; } - switch (type) { - case FS_IS_W: - RETURN_BOOL (!VCWD_ACCESS(filename, W_OK)); - case FS_IS_R: - RETURN_BOOL (!VCWD_ACCESS(filename, R_OK)); - case FS_IS_X: - RETURN_BOOL (!VCWD_ACCESS(filename, X_OK)); - case FS_EXISTS: - RETURN_BOOL (!VCWD_ACCESS(filename, F_OK)); - } - - stat_sb = &BG(sb); - - if (!BG(CurrentStatFile) || strcmp(filename, BG(CurrentStatFile))) { - if (!BG(CurrentStatFile) || filename_length > BG(CurrentStatLength)) { - if (BG(CurrentStatFile)) { - efree(BG(CurrentStatFile)); - } - BG(CurrentStatLength) = filename_length; - BG(CurrentStatFile) = estrndup(filename, filename_length); - } else { - memcpy(BG(CurrentStatFile), filename, filename_length+1); - } -#if HAVE_SYMLINK - BG(lsb).st_mode = 0; /* mark lstat buf invalid */ -#endif - if (VCWD_STAT(BG(CurrentStatFile), &BG(sb)) == -1) { - if (!IS_LINK_OPERATION(type) && (!IS_EXISTS_CHECK(type) || (errno != ENOENT && errno != ENOTDIR))) { /* fileexists() test must print no error */ - php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Stat failed for %s (errno=%d - %s)", BG(CurrentStatFile), errno, strerror(errno)); - } - efree(BG(CurrentStatFile)); - BG(CurrentStatFile) = NULL; -#if HAVE_SYMLINK - if (!IS_LINK_OPERATION(type)) /* Don't require success for link operation */ -#endif - RETURN_FALSE; - } - } -#if HAVE_SYMLINK - if (IS_LINK_OPERATION(type) && !BG(lsb).st_mode) { - /* do lstat if the buffer is empty */ - if (VCWD_LSTAT(filename, &BG(lsb)) == -1) { - if (!IS_EXISTS_CHECK(type) || (errno != ENOENT && errno != ENOTDIR)) { /* fileexists() test must print no error */ - php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Lstat failed for %s (errno=%d - %s)", BG(CurrentStatFile), errno, strerror(errno)); - } - RETURN_FALSE; + if (php_stream_stat_path_ex((char *)filename, (IS_LINK_OPERATION(type) ? PHP_STREAM_URL_STAT_LINK : 0), &ssb, NULL)) { + /* Error Occured */ + if (!IS_EXISTS_CHECK(type)) { + php_error_docref(NULL TSRMLS_CC, E_WARNING, "%sstat failed for %s", IS_LINK_OPERATION(type) ? "L" : "", filename); } + RETURN_FALSE; } -#endif + + stat_sb = &ssb.sb; #ifndef NETWARE if (type >= FS_IS_W && type <= FS_IS_X) { - if(BG(sb).st_uid==getuid()) { + if(ssb.sb.st_uid==getuid()) { rmask=S_IRUSR; wmask=S_IWUSR; xmask=S_IXUSR; - } else if(BG(sb).st_gid==getgid()) { + } else if(ssb.sb.st_gid==getgid()) { rmask=S_IRGRP; wmask=S_IWGRP; xmask=S_IXGRP; @@ -630,7 +599,7 @@ gids=(gid_t *)safe_emalloc(groups, sizeof(gid_t), 0); n=getgroups(groups, gids); for(i=0;i<n;i++){ - if(BG(sb).st_gid==gids[i]) { + if(ssb.sb.st_gid==gids[i]) { rmask=S_IRGRP; wmask=S_IWGRP; xmask=S_IXGRP; @@ -643,46 +612,61 @@ } #endif +#ifndef NETWARE + if (IS_ABLE_CHECK(type) && getuid() == 0) { + /* root has special perms on plain_wrapper + But we don't know about root under Netware */ + php_stream_wrapper *wrapper; + + wrapper = php_stream_locate_url_wrapper(filename, NULL, 0 TSRMLS_CC); + if (wrapper && wrapper->wops && wrapper->wops->label && strcmp(wrapper->wops->label, "plainfile") == 0) { + if (type == FS_IS_X) { + xmask = S_IXROOT; + } else { + RETURN_TRUE; + } + } + } +#endif + switch (type) { case FS_PERMS: - RETURN_LONG((long)BG(sb).st_mode); + RETURN_LONG((long)ssb.sb.st_mode); case FS_INODE: - RETURN_LONG((long)BG(sb).st_ino); + RETURN_LONG((long)ssb.sb.st_ino); case FS_SIZE: #if defined(NETWARE) && defined(NEW_LIBC) RETURN_LONG((long)(stat_sb->st_size)); #else - RETURN_LONG((long)BG(sb).st_size); + RETURN_LONG((long)ssb.sb.st_size); #endif case FS_OWNER: - RETURN_LONG((long)BG(sb).st_uid); + RETURN_LONG((long)ssb.sb.st_uid); case FS_GROUP: - RETURN_LONG((long)BG(sb).st_gid); + RETURN_LONG((long)ssb.sb.st_gid); case FS_ATIME: #if defined(NETWARE) && defined(NEW_LIBC) RETURN_LONG((long)((stat_sb->st_atime).tv_sec)); #else - RETURN_LONG((long)BG(sb).st_atime); + RETURN_LONG((long)ssb.sb.st_atime); #endif case FS_MTIME: #if defined(NETWARE) && defined(NEW_LIBC) RETURN_LONG((long)((stat_sb->st_mtime).tv_sec)); #else - RETURN_LONG((long)BG(sb).st_mtime); + RETURN_LONG((long)ssb.sb.st_mtime); #endif case FS_CTIME: #if defined(NETWARE) && defined(NEW_LIBC) RETURN_LONG((long)((stat_sb->st_ctime).tv_sec)); #else - RETURN_LONG((long)BG(sb).st_ctime); + RETURN_LONG((long)ssb.sb.st_ctime); #endif case FS_TYPE: -#if HAVE_SYMLINK - if (S_ISLNK(BG(lsb).st_mode)) { + if (S_ISLNK(ssb.sb.st_mode)) { RETURN_STRING("link", 1); } -#endif - switch(BG(sb).st_mode&S_IFMT) { + switch(ssb.sb.st_mode & S_IFMT) { case S_IFIFO: RETURN_STRING("fifo", 1); case S_IFCHR: RETURN_STRING("char", 1); case S_IFDIR: RETURN_STRING("dir", 1); @@ -692,45 +676,23 @@ case S_IFSOCK: RETURN_STRING("socket", 1); #endif } - php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Unknown file type (%d)", BG(sb).st_mode&S_IFMT); + php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Unknown file type (%d)", ssb.sb.st_mode&S_IFMT); RETURN_STRING("unknown", 1); case FS_IS_W: -#ifndef NETWARE /* getuid is not available on NetWare */ - if (getuid()==0) { - RETURN_TRUE; /* root */ - } -#endif /* NETWARE */ - RETURN_BOOL((BG(sb).st_mode & wmask) != 0); + RETURN_BOOL((ssb.sb.st_mode & wmask) != 0); case FS_IS_R: -#ifndef NETWARE /* getuid is not available on NetWare */ - if (getuid()==0) { - RETURN_TRUE; /* root */ - } -#endif /* NETWARE */ - RETURN_BOOL((BG(sb).st_mode&rmask)!=0); + RETURN_BOOL((ssb.sb.st_mode&rmask)!=0); case FS_IS_X: -#ifndef NETWARE /* getuid is not available on NetWare */ - if (getuid()==0) { - xmask = S_IXROOT; /* root */ - } -#endif /* NETWARE */ - RETURN_BOOL((BG(sb).st_mode&xmask)!=0 && !S_ISDIR(BG(sb).st_mode)); + RETURN_BOOL((ssb.sb.st_mode&xmask)!=0 && !S_ISDIR(ssb.sb.st_mode)); case FS_IS_FILE: - RETURN_BOOL(S_ISREG(BG(sb).st_mode)); + RETURN_BOOL(S_ISREG(ssb.sb.st_mode)); case FS_IS_DIR: - RETURN_BOOL(S_ISDIR(BG(sb).st_mode)); + RETURN_BOOL(S_ISDIR(ssb.sb.st_mode)); case FS_IS_LINK: -#if HAVE_SYMLINK - RETURN_BOOL(S_ISLNK(BG(lsb).st_mode)); -#else - RETURN_FALSE; -#endif + RETURN_BOOL(S_ISLNK(ssb.sb.st_mode)); case FS_EXISTS: RETURN_TRUE; /* the false case was done earlier */ case FS_LSTAT: -#if HAVE_SYMLINK - stat_sb = &BG(lsb); -#endif /* FALLTHROUGH */ case FS_STAT: array_init(return_value); Index: php-src/ext/standard/ftp_fopen_wrapper.c diff -u php-src/ext/standard/ftp_fopen_wrapper.c:1.63 php-src/ext/standard/ftp_fopen_wrapper.c:1.64 --- php-src/ext/standard/ftp_fopen_wrapper.c:1.63 Fri Sep 26 04:09:55 2003 +++ php-src/ext/standard/ftp_fopen_wrapper.c Fri Nov 28 18:25:26 2003 @@ -18,7 +18,7 @@ | Sara Golemon <[EMAIL PROTECTED]> | +----------------------------------------------------------------------+ */ -/* $Id: ftp_fopen_wrapper.c,v 1.63 2003/09/26 08:09:55 hholzgra Exp $ */ +/* $Id: ftp_fopen_wrapper.c,v 1.64 2003/11/28 23:25:26 pollita Exp $ */ #include "php.h" #include "php_globals.h" @@ -712,7 +712,7 @@ /* {{{ php_stream_ftp_url_stat */ -static int php_stream_ftp_url_stat(php_stream_wrapper *wrapper, char *url, php_stream_statbuf *ssb TSRMLS_DC) +static int php_stream_ftp_url_stat(php_stream_wrapper *wrapper, char *url, int flags, php_stream_statbuf *ssb, php_stream_context *context TSRMLS_DC) { php_stream *stream = NULL; php_url *resource = NULL; @@ -723,7 +723,7 @@ if (!ssb) return -1; memset(ssb, 0, sizeof(php_stream_statbuf)); - stream = php_ftp_fopen_connect(wrapper, url, "r", 0, NULL, NULL, NULL, &resource, NULL, NULL TSRMLS_CC); + stream = php_ftp_fopen_connect(wrapper, url, "r", 0, NULL, NULL, context, &resource, NULL, NULL TSRMLS_CC); if (!stream) { goto stat_errexit; } Index: php-src/main/php_streams.h diff -u php-src/main/php_streams.h:1.85 php-src/main/php_streams.h:1.86 --- php-src/main/php_streams.h:1.85 Thu Nov 27 12:39:01 2003 +++ php-src/main/php_streams.h Fri Nov 28 18:25:26 2003 @@ -16,7 +16,7 @@ +----------------------------------------------------------------------+ */ -/* $Id: php_streams.h,v 1.85 2003/11/27 17:39:01 wez Exp $ */ +/* $Id: php_streams.h,v 1.86 2003/11/28 23:25:26 pollita Exp $ */ #ifndef PHP_STREAMS_H #define PHP_STREAMS_H @@ -139,7 +139,7 @@ /* stat a wrapped stream */ int (*stream_stat)(php_stream_wrapper *wrapper, php_stream *stream, php_stream_statbuf *ssb TSRMLS_DC); /* stat a URL */ - int (*url_stat)(php_stream_wrapper *wrapper, char *url, php_stream_statbuf *ssb TSRMLS_DC); + int (*url_stat)(php_stream_wrapper *wrapper, char *url, int flags, php_stream_statbuf *ssb, php_stream_context *context TSRMLS_DC); /* open a "directory" stream */ php_stream *(*dir_opener)(php_stream_wrapper *wrapper, char *filename, char *mode, int options, char **opened_path, php_stream_context *context STREAMS_DC TSRMLS_DC); @@ -301,8 +301,9 @@ PHPAPI int _php_stream_stat(php_stream *stream, php_stream_statbuf *ssb TSRMLS_DC); #define php_stream_stat(stream, ssb) _php_stream_stat((stream), (ssb) TSRMLS_CC) -PHPAPI int _php_stream_stat_path(char *path, php_stream_statbuf *ssb TSRMLS_DC); -#define php_stream_stat_path(path, ssb) _php_stream_stat_path((path), (ssb) TSRMLS_CC) +PHPAPI int _php_stream_stat_path(char *path, int flags, php_stream_statbuf *ssb, php_stream_context *context TSRMLS_DC); +#define php_stream_stat_path(path, ssb) _php_stream_stat_path((path), 0, (ssb), NULL TSRMLS_CC) +#define php_stream_stat_path_ex(path, flags, ssb, context) _php_stream_stat_path((path), (flags), (ssb), (context) TSRMLS_CC) PHPAPI php_stream *_php_stream_opendir(char *path, int options, php_stream_context *context STREAMS_DC TSRMLS_DC); #define php_stream_opendir(path, options, context) _php_stream_opendir((path), (options), (context) STREAMS_CC TSRMLS_CC) @@ -316,6 +317,9 @@ #define php_stream_set_chunk_size(stream, size) _php_stream_set_option((stream), PHP_STREAM_OPTION_SET_CHUNK_SIZE, (size), NULL TSRMLS_CC) +/* Flags for url_stat method in wrapper ops */ +#define PHP_STREAM_URL_STAT_LINK 1 + /* change the blocking mode of stream: value == 1 => blocking, value == 0 => non-blocking. */ #define PHP_STREAM_OPTION_BLOCKING 1 Index: php-src/main/streams/plain_wrapper.c diff -u php-src/main/streams/plain_wrapper.c:1.27 php-src/main/streams/plain_wrapper.c:1.28 --- php-src/main/streams/plain_wrapper.c:1.27 Sun Oct 19 17:19:54 2003 +++ php-src/main/streams/plain_wrapper.c Fri Nov 28 18:25:27 2003 @@ -16,7 +16,7 @@ +----------------------------------------------------------------------+ */ -/* $Id: plain_wrapper.c,v 1.27 2003/10/19 21:19:54 shane Exp $ */ +/* $Id: plain_wrapper.c,v 1.28 2003/11/28 23:25:27 pollita Exp $ */ #include "php.h" #include "php_globals.h" @@ -896,9 +896,14 @@ return php_stream_fopen_rel(path, mode, opened_path, options); } -static int php_plain_files_url_stater(php_stream_wrapper *wrapper, char *url, php_stream_statbuf *ssb TSRMLS_DC) +static int php_plain_files_url_stater(php_stream_wrapper *wrapper, char *url, int flags, php_stream_statbuf *ssb, php_stream_context *context TSRMLS_DC) { - return VCWD_STAT(url, &ssb->sb); +#ifdef HAVE_SYMLINK + if (flags & PHP_STREAM_URL_STAT_LINK) { + return VCWD_LSTAT(url, &ssb->sb); + } else +#endif + return VCWD_STAT(url, &ssb->sb); } static int php_plain_files_unlink(php_stream_wrapper *wrapper, char *url, int options, php_stream_context *context TSRMLS_DC) Index: php-src/main/streams/streams.c diff -u php-src/main/streams/streams.c:1.42 php-src/main/streams/streams.c:1.43 --- php-src/main/streams/streams.c:1.42 Fri Nov 28 18:20:23 2003 +++ php-src/main/streams/streams.c Fri Nov 28 18:25:27 2003 @@ -19,7 +19,7 @@ +----------------------------------------------------------------------+ */ -/* $Id: streams.c,v 1.42 2003/11/28 23:20:23 wez Exp $ */ +/* $Id: streams.c,v 1.43 2003/11/28 23:25:27 pollita Exp $ */ #define _GNU_SOURCE #include "php.h" @@ -1458,14 +1458,45 @@ /* }}} */ /* {{{ _php_stream_stat_path */ -PHPAPI int _php_stream_stat_path(char *path, php_stream_statbuf *ssb TSRMLS_DC) +PHPAPI int _php_stream_stat_path(char *path, int flags, php_stream_statbuf *ssb, php_stream_context *context TSRMLS_DC) { php_stream_wrapper *wrapper = NULL; 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; + } + } wrapper = php_stream_locate_url_wrapper(path, &path_to_open, ENFORCE_SAFE_MODE TSRMLS_CC); if (wrapper && wrapper->wops->url_stat) { - return wrapper->wops->url_stat(wrapper, path_to_open, ssb TSRMLS_CC); + 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)); + } + BG(CurrentStatFile) = estrdup(path); + memcpy(&BG(ssb), ssb, sizeof(php_stream_statbuf)); + } + } + return ret; } return -1; } Index: php-src/NEWS diff -u php-src/NEWS:1.1505 php-src/NEWS:1.1506 --- php-src/NEWS:1.1505 Fri Nov 28 13:17:13 2003 +++ php-src/NEWS Fri Nov 28 18:25:28 2003 @@ -8,6 +8,7 @@ . php_strip_whitespace(). strip whitespace & comments from a script. (Ilia) . php_check_syntax(). check php script for parse errors. (Ilia) . image_type_to_extension(). return extension based on image type. (Ilia) +- Route stat() and family via streams API. (Sara) - Fixed __autoload() to preserve case of the passed class name. (Andi) - Fixed bug #26072 (--disable-libxml does not work). (Jani) - Fixed bug #26083 (Non-working write support in ext/dom). (Ilia)
-- PHP CVS Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php