Annotation of embedaddon/php/ext/standard/link.c, revision 1.1.1.3

1.1       misho       1: /*
                      2:    +----------------------------------------------------------------------+
                      3:    | PHP Version 5                                                        |
                      4:    +----------------------------------------------------------------------+
1.1.1.3 ! misho       5:    | Copyright (c) 1997-2013 The PHP Group                                |
1.1       misho       6:    +----------------------------------------------------------------------+
                      7:    | This source file is subject to version 3.01 of the PHP license,      |
                      8:    | that is bundled with this package in the file LICENSE, and is        |
                      9:    | available through the world-wide-web at the following url:           |
                     10:    | http://www.php.net/license/3_01.txt                                  |
                     11:    | If you did not receive a copy of the PHP license and are unable to   |
                     12:    | obtain it through the world-wide-web, please send a note to          |
                     13:    | license@php.net so we can mail you a copy immediately.               |
                     14:    +----------------------------------------------------------------------+
                     15:    | Author:                                                              |
                     16:    +----------------------------------------------------------------------+
                     17:  */
                     18: 
1.1.1.2   misho      19: /* $Id$ */
1.1       misho      20: 
                     21: #include "php.h"
                     22: #include "php_filestat.h"
                     23: #include "php_globals.h"
                     24: 
                     25: #ifdef HAVE_SYMLINK
                     26: 
                     27: #include <stdlib.h>
                     28: #if HAVE_UNISTD_H
                     29: #include <unistd.h>
                     30: #endif
                     31: #include <sys/stat.h>
                     32: #include <string.h>
                     33: #if HAVE_PWD_H
                     34: #ifdef PHP_WIN32
                     35: #include "win32/pwd.h"
                     36: #else
                     37: #include <pwd.h>
                     38: #endif
                     39: #endif
                     40: #if HAVE_GRP_H
                     41: #ifdef PHP_WIN32
                     42: #include "win32/grp.h"
                     43: #else
                     44: #include <grp.h>
                     45: #endif
                     46: #endif
                     47: #include <errno.h>
                     48: #include <ctype.h>
                     49: 
                     50: #include "php_link.h"
                     51: #include "php_string.h"
                     52: 
                     53: /* {{{ proto string readlink(string filename)
                     54:    Return the target of a symbolic link */
                     55: PHP_FUNCTION(readlink)
                     56: {
                     57:        char *link;
                     58:        int link_len;
                     59:        char buff[MAXPATHLEN];
                     60:        int ret;
                     61: 
                     62:        if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &link, &link_len) == FAILURE) {
                     63:                return;
                     64:        }
                     65: 
                     66:        if (php_check_open_basedir(link TSRMLS_CC)) {
                     67:                RETURN_FALSE;
                     68:        }
                     69: 
                     70:        ret = php_sys_readlink(link, buff, MAXPATHLEN-1);
                     71: 
                     72:        if (ret == -1) {
                     73:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "%s", strerror(errno));
                     74:                RETURN_FALSE;
                     75:        }
                     76:        /* Append NULL to the end of the string */
                     77:        buff[ret] = '\0';
                     78: 
                     79:        RETURN_STRING(buff, 1);
                     80: }
                     81: /* }}} */
                     82: 
                     83: /* {{{ proto int linkinfo(string filename)
                     84:    Returns the st_dev field of the UNIX C stat structure describing the link */
                     85: PHP_FUNCTION(linkinfo)
                     86: {
                     87:        char *link;
1.1.1.2   misho      88:        char *dirname;
                     89:        int link_len, dir_len;
1.1       misho      90:        struct stat sb;
                     91:        int ret;
                     92: 
1.1.1.2   misho      93:        if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "p", &link, &link_len) == FAILURE) {
1.1       misho      94:                return;
                     95:        }
                     96: 
1.1.1.2   misho      97:        dirname = estrndup(link, link_len);
                     98:        dir_len = php_dirname(dirname, link_len);
                     99: 
                    100:        if (php_check_open_basedir(dirname TSRMLS_CC)) {
                    101:                efree(dirname);
                    102:                RETURN_FALSE;
                    103:        }
                    104: 
1.1       misho     105:        ret = VCWD_LSTAT(link, &sb);
                    106:        if (ret == -1) {
                    107:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "%s", strerror(errno));
1.1.1.2   misho     108:                efree(dirname);
1.1       misho     109:                RETURN_LONG(-1L);
                    110:        }
                    111: 
1.1.1.2   misho     112:        efree(dirname);
1.1       misho     113:        RETURN_LONG((long) sb.st_dev);
                    114: }
                    115: /* }}} */
                    116: 
                    117: /* {{{ proto int symlink(string target, string link)
                    118:    Create a symbolic link */
                    119: PHP_FUNCTION(symlink)
                    120: {
                    121:        char *topath, *frompath;
                    122:        int topath_len, frompath_len;
                    123:        int ret;
                    124:        char source_p[MAXPATHLEN];
                    125:        char dest_p[MAXPATHLEN];
                    126:        char dirname[MAXPATHLEN];
                    127:        size_t len;
                    128: 
1.1.1.2   misho     129:        if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "pp", &topath, &topath_len, &frompath, &frompath_len) == FAILURE) {
1.1       misho     130:                return;
                    131:        }
                    132:        
                    133:        if (!expand_filepath(frompath, source_p TSRMLS_CC)) {
                    134:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "No such file or directory");
                    135:                RETURN_FALSE;
                    136:        }
                    137: 
                    138:        memcpy(dirname, source_p, sizeof(source_p));
                    139:        len = php_dirname(dirname, strlen(dirname));
                    140: 
                    141:        if (!expand_filepath_ex(topath, dest_p, dirname, len TSRMLS_CC)) {
                    142:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "No such file or directory");
                    143:                RETURN_FALSE;
                    144:        }
                    145: 
                    146:        if (php_stream_locate_url_wrapper(source_p, NULL, STREAM_LOCATE_WRAPPERS_ONLY TSRMLS_CC) ||
                    147:                php_stream_locate_url_wrapper(dest_p, NULL, STREAM_LOCATE_WRAPPERS_ONLY TSRMLS_CC) ) 
                    148:        {
                    149:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Unable to symlink to a URL");
                    150:                RETURN_FALSE;
                    151:        }
                    152: 
                    153:        if (php_check_open_basedir(dest_p TSRMLS_CC)) {
                    154:                RETURN_FALSE;
                    155:        }
                    156: 
                    157:        if (php_check_open_basedir(source_p TSRMLS_CC)) {
                    158:                RETURN_FALSE;
                    159:        }
                    160: 
                    161:        /* For the source, an expanded path must be used (in ZTS an other thread could have changed the CWD).
                    162:         * For the target the exact string given by the user must be used, relative or not, existing or not.
                    163:         * The target is relative to the link itself, not to the CWD. */
                    164:        ret = symlink(topath, source_p);
                    165: 
                    166:        if (ret == -1) {
                    167:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "%s", strerror(errno));
                    168:                RETURN_FALSE;
                    169:        }
                    170: 
                    171:        RETURN_TRUE;
                    172: }
                    173: /* }}} */
                    174: 
                    175: /* {{{ proto int link(string target, string link)
                    176:    Create a hard link */
                    177: PHP_FUNCTION(link)
                    178: {
                    179:        char *topath, *frompath;
                    180:        int topath_len, frompath_len;
                    181:        int ret;
                    182:        char source_p[MAXPATHLEN];
                    183:        char dest_p[MAXPATHLEN];
                    184: 
1.1.1.2   misho     185:        if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "pp", &topath, &topath_len, &frompath, &frompath_len) == FAILURE) {
1.1       misho     186:                return;
                    187:        }
                    188: 
                    189:        if (!expand_filepath(frompath, source_p TSRMLS_CC) || !expand_filepath(topath, dest_p TSRMLS_CC)) {
                    190:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "No such file or directory");
                    191:                RETURN_FALSE;
                    192:        }
                    193: 
                    194:        if (php_stream_locate_url_wrapper(source_p, NULL, STREAM_LOCATE_WRAPPERS_ONLY TSRMLS_CC) ||
                    195:                php_stream_locate_url_wrapper(dest_p, NULL, STREAM_LOCATE_WRAPPERS_ONLY TSRMLS_CC) ) 
                    196:        {
                    197:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Unable to link to a URL");
                    198:                RETURN_FALSE;
                    199:        }
                    200: 
                    201:        if (php_check_open_basedir(dest_p TSRMLS_CC)) {
                    202:                RETURN_FALSE;
                    203:        }
                    204: 
                    205:        if (php_check_open_basedir(source_p TSRMLS_CC)) {
                    206:                RETURN_FALSE;
                    207:        }
                    208: 
                    209: #ifndef ZTS
                    210:        ret = link(topath, frompath);
                    211: #else 
                    212:        ret = link(dest_p, source_p);   
                    213: #endif 
                    214:        if (ret == -1) {
                    215:                php_error_docref(NULL TSRMLS_CC, E_WARNING, "%s", strerror(errno));
                    216:                RETURN_FALSE;
                    217:        }
                    218: 
                    219:        RETURN_TRUE;
                    220: }
                    221: /* }}} */
                    222: 
                    223: #endif
                    224: 
                    225: /*
                    226:  * Local variables:
                    227:  * tab-width: 4
                    228:  * c-basic-offset: 4
                    229:  * End:
                    230:  * vim600: noet sw=4 ts=4 fdm=marker
                    231:  * vim<600: noet sw=4 ts=4
                    232:  */

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>