andrei          Wed Aug 31 16:42:18 2005 EDT

  Modified files:              
    /php-src/main       rfc1867.c 
  Log:
  Further work on Unicode support in file uploads.
  
  
http://cvs.php.net/diff.php/php-src/main/rfc1867.c?r1=1.174&r2=1.175&ty=u
Index: php-src/main/rfc1867.c
diff -u php-src/main/rfc1867.c:1.174 php-src/main/rfc1867.c:1.175
--- php-src/main/rfc1867.c:1.174        Thu Aug 11 19:36:05 2005
+++ php-src/main/rfc1867.c      Wed Aug 31 16:42:14 2005
@@ -17,7 +17,7 @@
    +----------------------------------------------------------------------+
  */
 
-/* $Id: rfc1867.c,v 1.174 2005/08/11 23:36:05 andrei Exp $ */
+/* $Id: rfc1867.c,v 1.175 2005/08/31 20:42:14 andrei Exp $ */
 
 /*
  *  This product includes software developed by the Apache Group
@@ -273,6 +273,15 @@
 }
 
 
+static void add_u_protected_variable(UChar *varname TSRMLS_DC)
+{
+       int dummy=1;
+
+       normalize_u_protected_variable(varname TSRMLS_CC);
+       zend_u_hash_add(&PG(rfc1867_protected_variables), IS_UNICODE, varname, 
u_strlen(varname)+1, &dummy, sizeof(int), NULL);
+}
+
+
 static zend_bool is_protected_variable(char *varname TSRMLS_DC)
 {
        normalize_protected_variable(varname TSRMLS_CC);
@@ -311,6 +320,14 @@
 }
 
 
+static void safe_u_php_register_variable_ex(UChar *var, zval *val, zval 
*track_vars_array, zend_bool override_protection TSRMLS_DC)
+{
+       if (override_protection || !is_u_protected_variable(var TSRMLS_CC)) {
+               php_u_register_variable_ex(var, val, track_vars_array 
TSRMLS_CC);
+       }
+}
+
+
 static void register_http_post_files_variable(char *strvar, char *val, zval 
*http_post_files, zend_bool override_protection TSRMLS_DC)
 {
        int register_globals = PG(register_globals);
@@ -321,6 +338,16 @@
 }
 
 
+static void register_u_http_post_files_variable(UChar *strvar, UChar *val, 
int32_t val_len, zval *http_post_files, zend_bool override_protection TSRMLS_DC)
+{
+       int register_globals = PG(register_globals);
+
+       PG(register_globals) = 0;
+       safe_u_php_register_variable(strvar, val, val_len, http_post_files, 
override_protection TSRMLS_CC);
+       PG(register_globals) = register_globals;
+}
+
+
 static void register_http_post_files_variable_ex(char *var, zval *val, zval 
*http_post_files, zend_bool override_protection TSRMLS_DC)
 {
        int register_globals = PG(register_globals);
@@ -331,6 +358,16 @@
 }
 
 
+static void register_u_http_post_files_variable_ex(UChar *var, zval *val, zval 
*http_post_files, zend_bool override_protection TSRMLS_DC)
+{
+       int register_globals = PG(register_globals);
+
+       PG(register_globals) = 0;
+       safe_u_php_register_variable_ex(var, val, http_post_files, 
override_protection TSRMLS_CC);
+       PG(register_globals) = register_globals;
+}
+
+
 static int unlink_filename(char **filename TSRMLS_DC)
 {
        VCWD_UNLINK(*filename);
@@ -991,15 +1028,13 @@
 
 static SAPI_POST_HANDLER_FUNC(rfc1867_post_handler_unicode)
 {
-       char *boundary, *s=NULL, *boundary_end = NULL, *start_arr=NULL, 
*array_index=NULL;
-       char *temp_filename=NULL, *lbuf=NULL, *abuf=NULL;
+       char *boundary, *boundary_end = NULL;
+       UChar *temp_filename=NULL, *array_index = NULL, *lbuf = NULL, *abuf = 
NULL;
+       UChar *start_arr = NULL, *s = NULL;
+       char *ascii_temp_filename = NULL;
        int boundary_len=0, total_bytes=0, cancel_upload=0, is_arr_upload=0, 
array_len=0;
        int max_file_size=0, skip_upload=0, anonindex=0, is_anonymous;
        zval *http_post_files=NULL; HashTable *uploaded_files=NULL;
-#if HAVE_MBSTRING && !defined(COMPILE_DL_MBSTRING)
-       int str_len = 0, num_vars = 0, num_vars_max = 2*10, *len_list = NULL;
-       char **val_list = NULL;
-#endif
        zend_bool magic_quotes_gpc;
        multipart_buffer *mbuff;
        zval *array_ptr = (zval *) arg;
@@ -1060,12 +1095,6 @@
        INIT_PZVAL(http_post_files);
        PG(http_globals)[TRACK_VARS_FILES] = http_post_files;
 
-#if HAVE_MBSTRING && !defined(COMPILE_DL_MBSTRING)
-       if (php_mb_encoding_translation(TSRMLS_C)) {
-               val_list = (char **)ecalloc(num_vars_max+2, sizeof(char *));
-               len_list = (int *)ecalloc(num_vars_max+2, sizeof(int));
-       }
-#endif
        zend_llist_init(&header, sizeof(mime_header_entry), (llist_dtor_func_t) 
php_free_hdr_entry, 0);
 
        if (!did_string_init) {
@@ -1082,9 +1111,9 @@
        while (!multipart_buffer_eof(mbuff TSRMLS_CC))
        {
                char buff[FILLUNIT];
-               char *cd=NULL, *tmp=NULL;
+               char *cd=NULL;
                int blen=0, wlen=0;
-               UChar *param = NULL, *filename = NULL;
+               UChar *param = NULL, *filename = NULL, *tmp = NULL;
                int32_t param_len;
 
                zend_llist_clean(&header);
@@ -1096,19 +1125,20 @@
                if ((cd = php_mime_get_hdr_value(header, 
"Content-Disposition"))) {
                        UChar *pair = NULL;
                        UChar *ucd = NULL, *ucd_start = NULL;
+                       int32_t ucd_len;
                        int end=0;
 
                        while (isspace(*cd)) {
                                ++cd;
                        }
 
-                       ucd_start = php_ap_to_unicode(cd, strlen(cd), NULL 
TSRMLS_CC);
+                       ucd_start = php_ap_to_unicode(cd, strlen(cd), &ucd_len 
TSRMLS_CC);
                        if (!ucd) {
                                /* UTODO error condition */
                        }
                        ucd = ucd_start;
 
-                       while (*ucd && (pair = php_u_ap_getword(&ucd, ';' 
TSRMLS_CC)))
+                       while (*ucd && (pair = php_u_ap_getword(&ucd, 0x3b 
/*';'*/ TSRMLS_CC)))
                        {
                                UChar *key=NULL, *word = pair;
 
@@ -1117,7 +1147,7 @@
                                }
 
                                if (u_strchr(pair, '=')) {
-                                       key = php_u_ap_getword(&pair, '=' 
TSRMLS_CC);
+                                       key = php_u_ap_getword(&pair, 0x3d 
/*'='*/ TSRMLS_CC);
 
                                        if (!u_strcasecmp(key, name_key, 0)) {
                                                if (param) {
@@ -1226,11 +1256,12 @@
 
                        if (!skip_upload) {
                                /* Handle file */
-                               fp = 
php_open_temporary_file(PG(upload_tmp_dir), "php", &temp_filename TSRMLS_CC);
+                               fp = 
php_open_temporary_file(PG(upload_tmp_dir), "php", &ascii_temp_filename 
TSRMLS_CC);
                                if (!fp) {
                                        sapi_module.sapi_error(E_WARNING, "File 
upload error - unable to create a temporary file");
                                        cancel_upload = UPLOAD_ERROR_E;
                                }
+                               temp_filename = 
zend_ascii_to_unicode(ascii_temp_filename, strlen(ascii_temp_filename)+1 
ZEND_FILE_LINE_CC);
                        }
                        if (skip_upload) {
                                efree(param);
@@ -1276,13 +1307,13 @@
                        }
                        if (!cancel_upload && !end) {
 #if DEBUG_FILE_UPLOAD
-                               sapi_module.sapi_error(E_NOTICE, "Missing mime 
boundary at the end of the data for file %s", strlen(filename) > 0 ? filename : 
"");
+                               sapi_module.sapi_error(E_NOTICE, "Missing mime 
boundary at the end of the data for file %v", u_strlen(filename) > 0 ? filename 
: EMPTY_STR);
 #endif
                                cancel_upload = UPLOAD_ERROR_C;
                        }
 #if DEBUG_FILE_UPLOAD
-                       if(strlen(filename) > 0 && total_bytes == 0 && 
!cancel_upload) {
-                               sapi_module.sapi_error(E_WARNING, "Uploaded 
file size 0 - file [%s=%s] not saved", param, filename);
+                       if(u_strlen(filename) > 0 && total_bytes == 0 && 
!cancel_upload) {
+                               sapi_module.sapi_error(E_WARNING, "Uploaded 
file size 0 - file [%v=%v] not saved", param, filename);
                                cancel_upload = 5;
                        }
 #endif         
@@ -1290,163 +1321,146 @@
                        if (cancel_upload) {
                                if (temp_filename) {
                                        if (cancel_upload != UPLOAD_ERROR_E) { 
/* file creation failed */
-                                               unlink(temp_filename);
+                                               unlink(ascii_temp_filename);
                                        }
+                                       efree(ascii_temp_filename);
                                        efree(temp_filename);
                                }
-                               temp_filename="";
+                               temp_filename = EMPTY_STR;
                        } else {
-                               zend_hash_add(SG(rfc1867_uploaded_files), 
temp_filename, strlen(temp_filename) + 1, &temp_filename, sizeof(char *), NULL);
+                               zend_u_hash_add(SG(rfc1867_uploaded_files), 
IS_UNICODE, temp_filename, u_strlen(temp_filename) + 1, &temp_filename, 
sizeof(UChar *), NULL);
                        }
 
                        /* is_arr_upload is true when name of file upload field
                         * ends in [.*]
                         * start_arr is set to point to 1st [
                         */
-                       is_arr_upload = (start_arr = strchr(param,'[')) && 
(param[strlen(param)-1] == ']');
+                       is_arr_upload = (start_arr = u_strchr(param, 0x5b 
/*'['*/)) && (param[u_strlen(param)-1] == 0x5d /*']'*/);
 
                        if (is_arr_upload) {
-                               array_len = strlen(start_arr);
+                               array_len = u_strlen(start_arr);
                                if (array_index) {
                                        efree(array_index);
                                }
-                               array_index = estrndup(start_arr+1, 
array_len-2);   
+                               array_index = eustrndup(start_arr+1, 
array_len-2);   
                        }
 
                        /* Add $foo_name */
                        if (lbuf) {
                                efree(lbuf);
                        }
-                       lbuf = (char *) emalloc(strlen(param) + 
MAX_SIZE_OF_INDEX + 1);
+                       lbuf = eumalloc(u_strlen(param) + MAX_SIZE_OF_INDEX + 
1);
 
                        if (is_arr_upload) {
                                if (abuf) efree(abuf);
-                               abuf = estrndup(param, strlen(param)-array_len);
-                               sprintf(lbuf, "%s_name[%s]", abuf, array_index);
+                               abuf = eustrndup(param, 
u_strlen(param)-array_len);
+                               u_sprintf(lbuf, "%S_name[%S]", abuf, 
array_index);
                        } else {
-                               sprintf(lbuf, "%s_name", param);
+                               u_sprintf(lbuf, "%S_name", param);
                        }
 
-#if HAVE_MBSTRING && !defined(COMPILE_DL_MBSTRING)
-                       if (php_mb_encoding_translation(TSRMLS_C)) {
-                               if (num_vars>=num_vars_max){    
-                                       php_mb_gpc_realloc_buffer(&val_list, 
&len_list, &num_vars_max, 
-                                                                               
          1 TSRMLS_CC);
-                               }
-                               val_list[num_vars] = filename;
-                               len_list[num_vars] = strlen(filename);
-                               num_vars++;
-                               if(php_mb_gpc_encoding_detector(val_list, 
len_list, num_vars, NULL TSRMLS_CC) == SUCCESS) {
-                                       str_len = strlen(filename);
-                                       
php_mb_gpc_encoding_converter(&filename, &str_len, 1, NULL, NULL TSRMLS_CC);
-                               }
-                               s = php_mb_strrchr(filename, '\\' TSRMLS_CC);
-                               if ((tmp = php_mb_strrchr(filename, '/' 
TSRMLS_CC)) > s) {
-                                       s = tmp;
-                               }
-                               num_vars--;
-                               goto filedone;
-                       }
-#endif                 
                        /* The \ check should technically be needed for win32 
systems only where
                         * it is a valid path separator. However, IE in all 
it's wisdom always sends
                         * the full path of the file on the user's filesystem, 
which means that unless
                         * the user does basename() they get a bogus file name. 
Until IE's user base drops 
                         * to nill or problem is fixed this code must remain 
enabled for all systems.
                         */
-                       s = strrchr(filename, '\\');
-                       if ((tmp = strrchr(filename, '/')) > s) {
+                       s = u_strrchr(filename, '\\');
+                       if ((tmp = u_strrchr(filename, 0x2f /*'/'*/)) > s) {
                                s = tmp;
                        }
 #ifdef PHP_WIN32
                        if (PG(magic_quotes_gpc)) {
                                s = s ? s : filename;
-                               tmp = strrchr(s, '\'');
+                               tmp = u_strrchr(s, 0x27 /*'\''*/);
                                s = tmp > s ? tmp : s;
-                               tmp = strrchr(s, '"');
+                               tmp = u_strrchr(s, 0x22 /*'"'*/);
                                s = tmp > s ? tmp : s;
                        }
 #endif
 
-#if HAVE_MBSTRING && !defined(COMPILE_DL_MBSTRING)
-filedone:                      
-#endif
-
                        if (!is_anonymous) {
                                if (s && s > filename) {
-                                       safe_php_register_variable(lbuf, s+1, 
NULL, 0 TSRMLS_CC);
+                                       safe_u_php_register_variable(lbuf, s+1, 
u_strlen(s+1), NULL, 0 TSRMLS_CC);
                                } else {
-                                       safe_php_register_variable(lbuf, 
filename, NULL, 0 TSRMLS_CC);
+                                       safe_u_php_register_variable(lbuf, 
filename, u_strlen(filename), NULL, 0 TSRMLS_CC);
                                }
                        }
 
                        /* Add $foo[name] */
                        if (is_arr_upload) {
-                               sprintf(lbuf, "%s[name][%s]", abuf, 
array_index);
+                               u_sprintf(lbuf, "%S[name][%S]", abuf, 
array_index);
                        } else {
-                               sprintf(lbuf, "%s[name]", param);
+                               u_sprintf(lbuf, "%S[name]", param);
                        }
                        if (s && s > filename) {
-                               register_http_post_files_variable(lbuf, s+1, 
http_post_files, 0 TSRMLS_CC);
+                               register_u_http_post_files_variable(lbuf, s+1, 
u_strlen(s+1), http_post_files, 0 TSRMLS_CC);
                        } else {
-                               register_http_post_files_variable(lbuf, 
filename, http_post_files, 0 TSRMLS_CC);
+                               register_u_http_post_files_variable(lbuf, 
filename, u_strlen(filename), http_post_files, 0 TSRMLS_CC);
                        }
                        efree(filename);
                        s = NULL;
 
                        /* Possible Content-Type: */
                        if (cancel_upload || !(cd = 
php_mime_get_hdr_value(header, "Content-Type"))) {
-                               cd = "";
+                               ucd = EMPTY_STR;
+                               ucd_len = 0;
                        } else { 
+                               ucd = php_ap_to_unicode(cd, strlen(cd), 
&ucd_len TSRMLS_CC);
+                               if (!ucd) {
+                                       /* UTODO error condition */
+                               }
                                /* fix for Opera 6.01 */
-                               s = strchr(cd, ';');
+                               s = u_strchr(ucd, 0x3b /*';'*/);
                                if (s != NULL) {
-                                       *s = '\0';
+                                       *s = 0;
                                }
                        }
 
                        /* Add $foo_type */
                        if (is_arr_upload) {
-                               sprintf(lbuf, "%s_type[%s]", abuf, array_index);
+                               u_sprintf(lbuf, "%S_type[%S]", abuf, 
array_index);
                        } else {
-                               sprintf(lbuf, "%s_type", param);
+                               u_sprintf(lbuf, "%S_type", param);
                        }
                        if (!is_anonymous) {
-                               safe_php_register_variable(lbuf, cd, NULL, 0 
TSRMLS_CC);
+                               safe_u_php_register_variable(lbuf, ucd, 
ucd_len, NULL, 0 TSRMLS_CC);
                        }
 
                        /* Add $foo[type] */
                        if (is_arr_upload) {
-                               sprintf(lbuf, "%s[type][%s]", abuf, 
array_index);
+                               u_sprintf(lbuf, "%S[type][%S]", abuf, 
array_index);
                        } else {
-                               sprintf(lbuf, "%s[type]", param);
+                               u_sprintf(lbuf, "%S[type]", param);
                        }
-                       register_http_post_files_variable(lbuf, cd, 
http_post_files, 0 TSRMLS_CC);
+                       register_u_http_post_files_variable(lbuf, ucd, ucd_len, 
http_post_files, 0 TSRMLS_CC);
+
+                       efree(ucd);
 
                        /* Restore Content-Type Header */
                        if (s != NULL) {
-                               *s = ';';
+                               *s = 0x3b /*';'*/;
                        }
-                       s = "";
+                       s = EMPTY_STR;
 
                        /* Initialize variables */
-                       add_protected_variable(param TSRMLS_CC);
+                       add_u_protected_variable(param TSRMLS_CC);
 
                        magic_quotes_gpc = PG(magic_quotes_gpc);
                        PG(magic_quotes_gpc) = 0;
                        /* if param is of form xxx[.*] this will cut it to xxx 
*/
                        if (!is_anonymous) {
-                               safe_php_register_variable(param, 
temp_filename, NULL, 1 TSRMLS_CC);
+                               safe_u_php_register_variable(param, 
temp_filename, u_strlen(temp_filename), NULL, 1 TSRMLS_CC);
                        }
 
                        /* Add $foo[tmp_name] */
                        if (is_arr_upload) {
-                               sprintf(lbuf, "%s[tmp_name][%s]", abuf, 
array_index);
+                               u_sprintf(lbuf, "%S[tmp_name][%S]", abuf, 
array_index);
                        } else {
-                               sprintf(lbuf, "%s[tmp_name]", param);
+                               u_sprintf(lbuf, "%S[tmp_name]", param);
                        }
-                       add_protected_variable(lbuf TSRMLS_CC);
-                       register_http_post_files_variable(lbuf, temp_filename, 
http_post_files, 1 TSRMLS_CC);
+                       add_u_protected_variable(lbuf TSRMLS_CC);
+                       register_u_http_post_files_variable(lbuf, 
temp_filename, u_strlen(temp_filename), http_post_files, 1 TSRMLS_CC);
 
                        PG(magic_quotes_gpc) = magic_quotes_gpc;
 
@@ -1466,31 +1480,32 @@
                                }       
 
                                if (is_arr_upload) {
-                                       sprintf(lbuf, "%s[error][%s]", abuf, 
array_index);
+                                       u_sprintf(lbuf, "%S[error][%S]", abuf, 
array_index);
                                } else {
-                                       sprintf(lbuf, "%s[error]", param);
+                                       u_sprintf(lbuf, "%S[error]", param);
                                }
-                               register_http_post_files_variable_ex(lbuf, 
&error_type, http_post_files, 0 TSRMLS_CC);
+                               register_u_http_post_files_variable_ex(lbuf, 
&error_type, http_post_files, 0 TSRMLS_CC);
 
                                /* Add $foo_size */
                                if (is_arr_upload) {
-                                       sprintf(lbuf, "%s_size[%s]", abuf, 
array_index);
+                                       u_sprintf(lbuf, "%S_size[%S]", abuf, 
array_index);
                                } else {
-                                       sprintf(lbuf, "%s_size", param);
+                                       u_sprintf(lbuf, "%S_size", param);
                                }
                                if (!is_anonymous) {
-                                       safe_php_register_variable_ex(lbuf, 
&file_size, NULL, 0 TSRMLS_CC);
+                                       safe_u_php_register_variable_ex(lbuf, 
&file_size, NULL, 0 TSRMLS_CC);
                                }       
 
                                /* Add $foo[size] */
                                if (is_arr_upload) {
-                                       sprintf(lbuf, "%s[size][%s]", abuf, 
array_index);
+                                       u_sprintf(lbuf, "%S[size][%S]", abuf, 
array_index);
                                } else {
-                                       sprintf(lbuf, "%s[size]", param);
+                                       u_sprintf(lbuf, "%S[size]", param);
                                }
-                               register_http_post_files_variable_ex(lbuf, 
&file_size, http_post_files, 0 TSRMLS_CC);
+                               register_u_http_post_files_variable_ex(lbuf, 
&file_size, http_post_files, 0 TSRMLS_CC);
                        }
                        efree(param);
+                       efree(filename);
                }
        }
 

-- 
PHP CVS Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php

Reply via email to