pollita         Thu Apr  6 19:39:11 2006 UTC

  Modified files:              
    /php-src/main/streams       streams.c 
  Log:
  Do runtime conversions (with an E_NOTICE) on writing unicode data to a binary 
stream.  Take the WTF out of the equation
  
http://cvs.php.net/viewcvs.cgi/php-src/main/streams/streams.c?r1=1.118&r2=1.119&diff_format=u
Index: php-src/main/streams/streams.c
diff -u php-src/main/streams/streams.c:1.118 
php-src/main/streams/streams.c:1.119
--- php-src/main/streams/streams.c:1.118        Fri Mar 31 22:51:37 2006
+++ php-src/main/streams/streams.c      Thu Apr  6 19:39:11 2006
@@ -19,7 +19,7 @@
    +----------------------------------------------------------------------+
  */
 
-/* $Id: streams.c,v 1.118 2006/03/31 22:51:37 pollita Exp $ */
+/* $Id: streams.c,v 1.119 2006/04/06 19:39:11 pollita Exp $ */
 
 #define _GNU_SOURCE
 #include "php.h"
@@ -1201,6 +1201,8 @@
 {
        size_t didwrite = 0, towrite, justwrote, shouldwrite;
        char *freeme = NULL;
+       void *buf_orig = buf.v;
+       int buflen_orig = buflen, conv_err = 0;
 
        /* if we have a seekable stream we need to ensure that data is written 
at the
         * current stream->position. This means invalidating the read buffer 
and then
@@ -1211,9 +1213,26 @@
                stream->ops->seek(stream, stream->position, SEEK_SET, 
&stream->position TSRMLS_CC);
        }
 
-       /* Sloppy handling, make it a binary buffer */
        if (buf_type == IS_UNICODE) {
-               buflen = UBYTES(buflen);
+               int len, num_conv, ulen = u_countChar32(buf.u, buflen);
+               char *str;
+               UErrorCode status = U_ZERO_ERROR;
+
+               /* Use runtime_encoding to map to binary */
+               num_conv = 
zend_convert_from_unicode(ZEND_U_CONVERTER(UG(runtime_encoding_conv)), &str, 
&len, buf.u, buflen, &status);
+               if (U_FAILURE(status)) {
+                       zend_raise_conversion_error_ex("Unable to convert data 
to be writen", ZEND_U_CONVERTER(UG(runtime_encoding_conv)),
+                                                                       
ZEND_FROM_UNICODE, num_conv, (UG(from_error_mode) & ZEND_CONV_ERROR_EXCEPTION) 
TSRMLS_CC);
+               } else {
+                       php_error_docref(NULL TSRMLS_CC, E_NOTICE, "%d 
character unicode buffer downcoded for binary stream runtime_encoding", ulen);
+               }
+
+               if (num_conv < buflen) {
+                       conv_err = 1;
+               }
+
+               freeme = buf.s = str;
+               buflen = len;
        }
 
        shouldwrite = buflen;
@@ -1243,8 +1262,23 @@
        }
 
        if (buf_type == IS_UNICODE) {
-               /* Was slopily converted */
-               didwrite /= UBYTES(1);
+               /* Map bytes written back to UChars written */
+
+               if (shouldwrite == didwrite && !conv_err) {
+                       /* wrote it all */
+                       didwrite = buflen_orig;
+               } else {
+                       /* Figure out how didwrite corresponds to the input 
buffer */
+                       char *tmp = emalloc(didwrite + 1), *t = tmp;
+                       UChar *s = buf_orig;
+                       UErrorCode status = U_ZERO_ERROR;
+
+                       
ucnv_resetFromUnicode(ZEND_U_CONVERTER(UG(runtime_encoding_conv)));
+                       
ucnv_fromUnicode(ZEND_U_CONVERTER(UG(runtime_encoding_conv)), &t, t + didwrite, 
&s, s + buflen_orig, NULL, TRUE, &status);
+
+                       didwrite = s - ((UChar*)buf_orig);
+                       efree(tmp);
+               }
        }
 
        if (freeme) {

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

Reply via email to