]> granicus.if.org Git - php/commitdiff
Fixed bug #77945
authorNikita Popov <nikita.ppv@gmail.com>
Mon, 29 Apr 2019 11:51:26 +0000 (13:51 +0200)
committerNikita Popov <nikita.ppv@gmail.com>
Mon, 29 Apr 2019 11:52:18 +0000 (13:52 +0200)
Make sure that we proper distinguish between empty string key and
no key during SDL serialization.

NEWS
ext/soap/php_sdl.c
ext/soap/tests/bugs/bug29236.wsdl
ext/soap/tests/bugs/bug77945.phpt [new file with mode: 0644]

diff --git a/NEWS b/NEWS
index a91cf9360a26ef26de4981b3638999132a384034..3024c268ef07b34855150ec9bb4d109d5b7545bb 100644 (file)
--- a/NEWS
+++ b/NEWS
@@ -58,6 +58,10 @@ PHP                                                                        NEWS
   . Fixed bug #77772 (ReflectionClass::getMethods(null) doesn't work). (Nikita)
   . Fixed bug #77882 (Different behavior: always calls destructor). (Nikita)
 
+- SOAP:
+  . Fixed bug #77945 (Segmentation fault when constructing SoapClient with
+    WSDL_CACHE_BOTH). (Nikita)
+
 - Standard:
   . Fixed bug #77680 (recursive mkdir on ftp stream wrapper is incorrect).
     (Vlad Temian)
index 2485ef2fd806b5df8ae1dcc1d527e50d1d099ca0..d16056e4a38bc6f097fdf8fd22bb7bb70c61aea7 100644 (file)
@@ -1174,7 +1174,7 @@ static sdlPtr load_wsdl(zval *this_ptr, char *struri)
        return ctx.sdl;
 }
 
-#define WSDL_CACHE_VERSION 0x0f
+#define WSDL_CACHE_VERSION 0x10
 
 #define WSDL_CACHE_GET(ret,type,buf)   memcpy(&ret,*buf,sizeof(type)); *buf += sizeof(type);
 #define WSDL_CACHE_GET_INT(ret,buf)    ret = ((unsigned char)(*buf)[0])|((unsigned char)(*buf)[1]<<8)|((unsigned char)(*buf)[2]<<16)|((int)(*buf)[3]<<24); *buf += 4;
@@ -1189,13 +1189,15 @@ static sdlPtr load_wsdl(zval *this_ptr, char *struri)
 #define WSDL_CACHE_PUT_1(val,buf)      smart_str_appendc(buf,val);
 #define WSDL_CACHE_PUT_N(val,n,buf)    smart_str_appendl(buf,(char*)val,n);
 
+#define WSDL_NO_STRING_MARKER 0x7fffffff
+
 static char* sdl_deserialize_string(char **in)
 {
        char *s;
        int len;
 
        WSDL_CACHE_GET_INT(len, in);
-       if (len == 0x7fffffff) {
+       if (len == WSDL_NO_STRING_MARKER) {
                return NULL;
        } else {
                s = emalloc(len+1);
@@ -1210,7 +1212,7 @@ static void sdl_deserialize_key(HashTable* ht, void* data, char **in)
        int len;
 
        WSDL_CACHE_GET_INT(len, in);
-       if (len == 0) {
+       if (len == WSDL_NO_STRING_MARKER) {
                zend_hash_next_index_insert_ptr(ht, data);
        } else {
                zend_hash_str_add_ptr(ht, *in, len, data);
@@ -1778,16 +1780,14 @@ static sdlPtr get_sdl_from_cache(const char *fn, const char *uri, time_t t, time
 
 static void sdl_serialize_string(const char *str, smart_str *out)
 {
-       int i;
-
        if (str) {
-               i = strlen(str);
+               int i = strlen(str);
                WSDL_CACHE_PUT_INT(i, out);
                if (i > 0) {
                        WSDL_CACHE_PUT_N(str, i, out);
                }
        } else {
-               WSDL_CACHE_PUT_INT(0x7fffffff, out);
+               WSDL_CACHE_PUT_INT(WSDL_NO_STRING_MARKER, out);
        }
 }
 
@@ -1798,7 +1798,7 @@ static void sdl_serialize_key(zend_string *key, smart_str *out)
                WSDL_CACHE_PUT_INT(ZSTR_LEN(key), out);
                WSDL_CACHE_PUT_N(ZSTR_VAL(key), ZSTR_LEN(key), out);
        } else {
-               WSDL_CACHE_PUT_INT(0, out);
+               WSDL_CACHE_PUT_INT(WSDL_NO_STRING_MARKER, out);
        }
 }
 
index d60a4871d42824b8a0947016c32c17a27eab1f9e..40e764583df4f5c92cc8098c4fa31b0570db6164 100644 (file)
@@ -75,6 +75,7 @@
           <s:enumeration value="TemporarilySuspended" />\r
           <s:enumeration value="PasswordResetRequired" />\r
           <s:enumeration value="InvalidID" />\r
+          <s:enumeration value="" /> <!-- For bug #77945 -->\r
         </s:restriction>\r
       </s:simpleType>\r
       <s:simpleType name="SessionStatus">\r
       <http:address location="http://isisdev1.tig.ucla.edu/iws/v4.asmx" />\r
     </port>\r
   </service>\r
-</definitions>
\ No newline at end of file
+</definitions>\r
diff --git a/ext/soap/tests/bugs/bug77945.phpt b/ext/soap/tests/bugs/bug77945.phpt
new file mode 100644 (file)
index 0000000..5800330
--- /dev/null
@@ -0,0 +1,18 @@
+--TEST--
+Bug #77945: Segmentation fault when constructing SoapClient with WSDL_CACHE_BOTH
+--SKIPIF--
+<?php
+if (!extension_loaded('soap')) die('skip soap extension not available');
+?>
+--FILE--
+<?php
+
+// The important part is to have a restriction enumeration with value="".
+$client = new SoapClient(__DIR__ . '/bug29236.wsdl', [
+    'cache_wsdl' => WSDL_CACHE_BOTH
+]);
+
+?>
+===DONE===
+--EXPECT--
+===DONE===