瀏覽代碼

Merge pull request #4291 from google/3.5.x

Merge 3.5.x to master
Jisi Liu 7 年之前
父節點
當前提交
bb40c0c0c4

+ 3 - 2
php/ext/google/protobuf/encode_decode.c

@@ -484,11 +484,11 @@ static void map_slot_init(void* memory, upb_fieldtype_t type, zval* cache) {
       // Store zval** in memory in order to be consistent with the layout of
       // Store zval** in memory in order to be consistent with the layout of
       // singular fields.
       // singular fields.
       zval** holder = ALLOC(zval*);
       zval** holder = ALLOC(zval*);
+      *(zval***)memory = holder;
       zval* tmp;
       zval* tmp;
       MAKE_STD_ZVAL(tmp);
       MAKE_STD_ZVAL(tmp);
       PHP_PROTO_ZVAL_STRINGL(tmp, "", 0, 1);
       PHP_PROTO_ZVAL_STRINGL(tmp, "", 0, 1);
       *holder = tmp;
       *holder = tmp;
-      *(zval***)memory = holder;
 #else
 #else
       *(zval**)memory = cache;
       *(zval**)memory = cache;
       PHP_PROTO_ZVAL_STRINGL(*(zval**)memory, "", 0, 1);
       PHP_PROTO_ZVAL_STRINGL(*(zval**)memory, "", 0, 1);
@@ -521,7 +521,7 @@ static void map_slot_uninit(void* memory, upb_fieldtype_t type) {
     case UPB_TYPE_BYTES: {
     case UPB_TYPE_BYTES: {
 #if PHP_MAJOR_VERSION < 7
 #if PHP_MAJOR_VERSION < 7
       zval** holder = *(zval***)memory;
       zval** holder = *(zval***)memory;
-      php_proto_zval_ptr_dtor(*holder);
+      zval_ptr_dtor(holder);
       FREE(holder);
       FREE(holder);
 #else
 #else
       php_proto_zval_ptr_dtor(*(zval**)memory);
       php_proto_zval_ptr_dtor(*(zval**)memory);
@@ -1621,6 +1621,7 @@ static void discard_unknown_fields(MessageHeader* msg) {
   stringsink* unknown = DEREF(message_data(msg), 0, stringsink*);
   stringsink* unknown = DEREF(message_data(msg), 0, stringsink*);
   if (unknown != NULL) {
   if (unknown != NULL) {
     stringsink_uninit(unknown);
     stringsink_uninit(unknown);
+    FREE(unknown);
     DEREF(message_data(msg), 0, stringsink*) = NULL;
     DEREF(message_data(msg), 0, stringsink*) = NULL;
   }
   }
 
 

+ 36 - 8
php/ext/google/protobuf/map.c

@@ -293,13 +293,46 @@ static bool map_field_read_dimension(zval *object, zval *key, int type,
   }
   }
 }
 }
 
 
+static bool map_index_unset(Map *intern, const char* keyval, int length) {
+  upb_value old_value;
+  if (upb_strtable_remove2(&intern->table, keyval, length, &old_value)) {
+    switch (intern->value_type) {
+      case UPB_TYPE_MESSAGE: {
+#if PHP_MAJOR_VERSION < 7
+        zval_ptr_dtor(upb_value_memory(&old_value));
+#else
+        zend_object* object = *(zend_object**)upb_value_memory(&old_value);
+        if(--GC_REFCOUNT(object) == 0) {
+          zend_objects_store_del(object);
+        }
+#endif
+        break;
+      }
+      case UPB_TYPE_STRING:
+      case UPB_TYPE_BYTES: {
+#if PHP_MAJOR_VERSION < 7
+        zval_ptr_dtor(upb_value_memory(&old_value));
+#else
+        zend_string* object = *(zend_string**)upb_value_memory(&old_value);
+        zend_string_release(object);
+#endif
+        break;
+      }
+      default:
+        break;
+    }
+  }
+}
+
 bool map_index_set(Map *intern, const char* keyval, int length, upb_value v) {
 bool map_index_set(Map *intern, const char* keyval, int length, upb_value v) {
   // Replace any existing value by issuing a 'remove' operation first.
   // Replace any existing value by issuing a 'remove' operation first.
-  upb_strtable_remove2(&intern->table, keyval, length, NULL);
+  map_index_unset(intern, keyval, length);
+
   if (!upb_strtable_insert2(&intern->table, keyval, length, v)) {
   if (!upb_strtable_insert2(&intern->table, keyval, length, v)) {
     zend_error(E_USER_ERROR, "Could not insert into table");
     zend_error(E_USER_ERROR, "Could not insert into table");
     return false;
     return false;
   }
   }
+
   return true;
   return true;
 }
 }
 
 
@@ -326,12 +359,7 @@ static void map_field_write_dimension(zval *object, zval *key,
   v.ctype = UPB_CTYPE_UINT64;
   v.ctype = UPB_CTYPE_UINT64;
 #endif
 #endif
 
 
-  // Replace any existing value by issuing a 'remove' operation first.
-  upb_strtable_remove2(&intern->table, keyval, length, NULL);
-  if (!upb_strtable_insert2(&intern->table, keyval, length, v)) {
-    zend_error(E_USER_ERROR, "Could not insert into table");
-    return;
-  }
+  map_index_set(intern, keyval, length, v);
 }
 }
 
 
 static bool map_field_unset_dimension(zval *object, zval *key TSRMLS_DC) {
 static bool map_field_unset_dimension(zval *object, zval *key TSRMLS_DC) {
@@ -348,7 +376,7 @@ static bool map_field_unset_dimension(zval *object, zval *key TSRMLS_DC) {
   v.ctype = UPB_CTYPE_UINT64;
   v.ctype = UPB_CTYPE_UINT64;
 #endif
 #endif
 
 
-  upb_strtable_remove2(&intern->table, keyval, length, &v);
+  map_index_unset(intern, keyval, length);
 
 
   return true;
   return true;
 }
 }

+ 29 - 30
php/ext/google/protobuf/message.c

@@ -292,7 +292,9 @@ PHP_METHOD(Message, clear) {
   Descriptor* desc = msg->descriptor;
   Descriptor* desc = msg->descriptor;
   zend_class_entry* ce = desc->klass;
   zend_class_entry* ce = desc->klass;
 
 
+  zend_object_std_dtor(&msg->std TSRMLS_CC);
   object_properties_init(&msg->std, ce);
   object_properties_init(&msg->std, ce);
+
   layout_init(desc->layout, message_data(msg), &msg->std TSRMLS_CC);
   layout_init(desc->layout, message_data(msg), &msg->std TSRMLS_CC);
 }
 }
 
 
@@ -445,8 +447,7 @@ static void init_file_wrappers(TSRMLS_D);
 
 
 // Define file init functions
 // Define file init functions
 static void init_file_any(TSRMLS_D) {
 static void init_file_any(TSRMLS_D) {
-  static bool is_initialized = false;
-  if (is_initialized) return;
+  if (is_inited_file_any) return;
   init_generated_pool_once(TSRMLS_C);
   init_generated_pool_once(TSRMLS_C);
   const char* generated_file =
   const char* generated_file =
       "0acd010a19676f6f676c652f70726f746f6275662f616e792e70726f746f"
       "0acd010a19676f6f676c652f70726f746f6275662f616e792e70726f746f"
@@ -461,12 +462,11 @@ static void init_file_any(TSRMLS_D) {
   hex_to_binary(generated_file, &binary, &binary_len);
   hex_to_binary(generated_file, &binary, &binary_len);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   FREE(binary);
   FREE(binary);
-  is_initialized = true;
+  is_inited_file_any = true;
 }
 }
 
 
 static void init_file_api(TSRMLS_D) {
 static void init_file_api(TSRMLS_D) {
-  static bool is_initialized = false;
-  if (is_initialized) return;
+  if (is_inited_file_api) return;
   init_file_source_context(TSRMLS_C);
   init_file_source_context(TSRMLS_C);
   init_file_type(TSRMLS_C);
   init_file_type(TSRMLS_C);
   init_generated_pool_once(TSRMLS_C);
   init_generated_pool_once(TSRMLS_C);
@@ -502,12 +502,11 @@ static void init_file_api(TSRMLS_D) {
   hex_to_binary(generated_file, &binary, &binary_len);
   hex_to_binary(generated_file, &binary, &binary_len);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   FREE(binary);
   FREE(binary);
-  is_initialized = true;
+  is_inited_file_api = true;
 }
 }
 
 
 static void init_file_duration(TSRMLS_D) {
 static void init_file_duration(TSRMLS_D) {
-  static bool is_initialized = false;
-  if (is_initialized) return;
+  if (is_inited_file_duration) return;
   init_generated_pool_once(TSRMLS_C);
   init_generated_pool_once(TSRMLS_C);
   const char* generated_file =
   const char* generated_file =
       "0ae3010a1e676f6f676c652f70726f746f6275662f6475726174696f6e2e"
       "0ae3010a1e676f6f676c652f70726f746f6275662f6475726174696f6e2e"
@@ -523,12 +522,11 @@ static void init_file_duration(TSRMLS_D) {
   hex_to_binary(generated_file, &binary, &binary_len);
   hex_to_binary(generated_file, &binary, &binary_len);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   FREE(binary);
   FREE(binary);
-  is_initialized = true;
+  is_inited_file_duration = true;
 }
 }
 
 
 static void init_file_field_mask(TSRMLS_D) {
 static void init_file_field_mask(TSRMLS_D) {
-  static bool is_initialized = false;
-  if (is_initialized) return;
+  if (is_inited_file_field_mask) return;
   init_generated_pool_once(TSRMLS_C);
   init_generated_pool_once(TSRMLS_C);
   const char* generated_file =
   const char* generated_file =
       "0ae3010a20676f6f676c652f70726f746f6275662f6669656c645f6d6173"
       "0ae3010a20676f6f676c652f70726f746f6275662f6669656c645f6d6173"
@@ -544,12 +542,11 @@ static void init_file_field_mask(TSRMLS_D) {
   hex_to_binary(generated_file, &binary, &binary_len);
   hex_to_binary(generated_file, &binary, &binary_len);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   FREE(binary);
   FREE(binary);
-  is_initialized = true;
+  is_inited_file_field_mask = true;
 }
 }
 
 
 static void init_file_empty(TSRMLS_D) {
 static void init_file_empty(TSRMLS_D) {
-  static bool is_initialized = false;
-  if (is_initialized) return;
+  if (is_inited_file_empty) return;
   init_generated_pool_once(TSRMLS_C);
   init_generated_pool_once(TSRMLS_C);
   const char* generated_file =
   const char* generated_file =
       "0ab7010a1b676f6f676c652f70726f746f6275662f656d7074792e70726f"
       "0ab7010a1b676f6f676c652f70726f746f6275662f656d7074792e70726f"
@@ -564,12 +561,11 @@ static void init_file_empty(TSRMLS_D) {
   hex_to_binary(generated_file, &binary, &binary_len);
   hex_to_binary(generated_file, &binary, &binary_len);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   FREE(binary);
   FREE(binary);
-  is_initialized = true;
+  is_inited_file_empty = true;
 }
 }
 
 
 static void init_file_source_context(TSRMLS_D) {
 static void init_file_source_context(TSRMLS_D) {
-  static bool is_initialized = false;
-  if (is_initialized) return;
+  if (is_inited_file_source_context) return;
   init_generated_pool_once(TSRMLS_C);
   init_generated_pool_once(TSRMLS_C);
   const char* generated_file =
   const char* generated_file =
       "0afb010a24676f6f676c652f70726f746f6275662f736f757263655f636f"
       "0afb010a24676f6f676c652f70726f746f6275662f736f757263655f636f"
@@ -586,12 +582,11 @@ static void init_file_source_context(TSRMLS_D) {
   hex_to_binary(generated_file, &binary, &binary_len);
   hex_to_binary(generated_file, &binary, &binary_len);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   FREE(binary);
   FREE(binary);
-  is_initialized = true;
+  is_inited_file_source_context = true;
 }
 }
 
 
 static void init_file_struct(TSRMLS_D) {
 static void init_file_struct(TSRMLS_D) {
-  static bool is_initialized = false;
-  if (is_initialized) return;
+  if (is_inited_file_struct) return;
   init_generated_pool_once(TSRMLS_C);
   init_generated_pool_once(TSRMLS_C);
   const char* generated_file =
   const char* generated_file =
       "0a81050a1c676f6f676c652f70726f746f6275662f7374727563742e7072"
       "0a81050a1c676f6f676c652f70726f746f6275662f7374727563742e7072"
@@ -621,12 +616,11 @@ static void init_file_struct(TSRMLS_D) {
   hex_to_binary(generated_file, &binary, &binary_len);
   hex_to_binary(generated_file, &binary, &binary_len);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   FREE(binary);
   FREE(binary);
-  is_initialized = true;
+  is_inited_file_struct = true;
 }
 }
 
 
 static void init_file_timestamp(TSRMLS_D) {
 static void init_file_timestamp(TSRMLS_D) {
-  static bool is_initialized = false;
-  if (is_initialized) return;
+  if (is_inited_file_timestamp) return;
   init_generated_pool_once(TSRMLS_C);
   init_generated_pool_once(TSRMLS_C);
   const char* generated_file =
   const char* generated_file =
       "0ae7010a1f676f6f676c652f70726f746f6275662f74696d657374616d70"
       "0ae7010a1f676f6f676c652f70726f746f6275662f74696d657374616d70"
@@ -642,12 +636,11 @@ static void init_file_timestamp(TSRMLS_D) {
   hex_to_binary(generated_file, &binary, &binary_len);
   hex_to_binary(generated_file, &binary, &binary_len);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   FREE(binary);
   FREE(binary);
-  is_initialized = true;
+  is_inited_file_timestamp = true;
 }
 }
 
 
 static void init_file_type(TSRMLS_D) {
 static void init_file_type(TSRMLS_D) {
-  static bool is_initialized = false;
-  if (is_initialized) return;
+  if (is_inited_file_type) return;
   init_file_any(TSRMLS_C);
   init_file_any(TSRMLS_C);
   init_file_source_context(TSRMLS_C);
   init_file_source_context(TSRMLS_C);
   init_generated_pool_once(TSRMLS_C);
   init_generated_pool_once(TSRMLS_C);
@@ -711,12 +704,11 @@ static void init_file_type(TSRMLS_D) {
   hex_to_binary(generated_file, &binary, &binary_len);
   hex_to_binary(generated_file, &binary, &binary_len);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   FREE(binary);
   FREE(binary);
-  is_initialized = true;
+  is_inited_file_type = true;
 }
 }
 
 
 static void init_file_wrappers(TSRMLS_D) {
 static void init_file_wrappers(TSRMLS_D) {
-  static bool is_initialized = false;
-  if (is_initialized) return;
+  if (is_inited_file_wrappers) return;
   init_generated_pool_once(TSRMLS_C);
   init_generated_pool_once(TSRMLS_C);
   const char* generated_file =
   const char* generated_file =
       "0abf030a1e676f6f676c652f70726f746f6275662f77726170706572732e"
       "0abf030a1e676f6f676c652f70726f746f6275662f77726170706572732e"
@@ -739,7 +731,7 @@ static void init_file_wrappers(TSRMLS_D) {
   hex_to_binary(generated_file, &binary, &binary_len);
   hex_to_binary(generated_file, &binary, &binary_len);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   internal_add_generated_file(binary, binary_len, generated_pool TSRMLS_CC);
   FREE(binary);
   FREE(binary);
-  is_initialized = true;
+  is_inited_file_wrappers = true;
 }
 }
 
 
 // -----------------------------------------------------------------------------
 // -----------------------------------------------------------------------------
@@ -928,6 +920,7 @@ PHP_METHOD(Any, unpack) {
   PHP_PROTO_FAKE_SCOPE_BEGIN(any_type);
   PHP_PROTO_FAKE_SCOPE_BEGIN(any_type);
   zval* type_url_php = php_proto_message_read_property(
   zval* type_url_php = php_proto_message_read_property(
       getThis(), &type_url_member PHP_PROTO_TSRMLS_CC);
       getThis(), &type_url_member PHP_PROTO_TSRMLS_CC);
+  zval_dtor(&type_url_member);
   PHP_PROTO_FAKE_SCOPE_END;
   PHP_PROTO_FAKE_SCOPE_END;
 
 
   // Get fully-qualified name from type url.
   // Get fully-qualified name from type url.
@@ -963,6 +956,7 @@ PHP_METHOD(Any, unpack) {
   PHP_PROTO_FAKE_SCOPE_RESTART(any_type);
   PHP_PROTO_FAKE_SCOPE_RESTART(any_type);
   zval* value = php_proto_message_read_property(
   zval* value = php_proto_message_read_property(
       getThis(), &value_member PHP_PROTO_TSRMLS_CC);
       getThis(), &value_member PHP_PROTO_TSRMLS_CC);
+  zval_dtor(&value_member);
   PHP_PROTO_FAKE_SCOPE_END;
   PHP_PROTO_FAKE_SCOPE_END;
 
 
   merge_from_string(Z_STRVAL_P(value), Z_STRLEN_P(value), desc, msg);
   merge_from_string(Z_STRVAL_P(value), Z_STRLEN_P(value), desc, msg);
@@ -991,6 +985,8 @@ PHP_METHOD(Any, pack) {
   PHP_PROTO_FAKE_SCOPE_BEGIN(any_type);
   PHP_PROTO_FAKE_SCOPE_BEGIN(any_type);
   message_handlers->write_property(getThis(), &member, &data,
   message_handlers->write_property(getThis(), &member, &data,
                                    NULL PHP_PROTO_TSRMLS_CC);
                                    NULL PHP_PROTO_TSRMLS_CC);
+  zval_dtor(&data);
+  zval_dtor(&member);
   PHP_PROTO_FAKE_SCOPE_END;
   PHP_PROTO_FAKE_SCOPE_END;
 
 
   // Set type url.
   // Set type url.
@@ -1008,6 +1004,8 @@ PHP_METHOD(Any, pack) {
   PHP_PROTO_FAKE_SCOPE_RESTART(any_type);
   PHP_PROTO_FAKE_SCOPE_RESTART(any_type);
   message_handlers->write_property(getThis(), &member, &type_url_php,
   message_handlers->write_property(getThis(), &member, &type_url_php,
                                    NULL PHP_PROTO_TSRMLS_CC);
                                    NULL PHP_PROTO_TSRMLS_CC);
+  zval_dtor(&type_url_php);
+  zval_dtor(&member);
   PHP_PROTO_FAKE_SCOPE_END;
   PHP_PROTO_FAKE_SCOPE_END;
   FREE(type_url);
   FREE(type_url);
 }
 }
@@ -1040,6 +1038,7 @@ PHP_METHOD(Any, is) {
   PHP_PROTO_FAKE_SCOPE_BEGIN(any_type);
   PHP_PROTO_FAKE_SCOPE_BEGIN(any_type);
   zval* value =
   zval* value =
       php_proto_message_read_property(getThis(), &member PHP_PROTO_TSRMLS_CC);
       php_proto_message_read_property(getThis(), &member PHP_PROTO_TSRMLS_CC);
+  zval_dtor(&member);
   PHP_PROTO_FAKE_SCOPE_END;
   PHP_PROTO_FAKE_SCOPE_END;
 
 
   // Compare two type url.
   // Compare two type url.

+ 37 - 0
php/ext/google/protobuf/protobuf.c

@@ -144,6 +144,21 @@ PHP_PROTO_HASHTABLE_VALUE get_proto_obj(const char* proto) {
                                                       proto, strlen(proto));
                                                       proto, strlen(proto));
 }
 }
 
 
+// -----------------------------------------------------------------------------
+// Well Known Types.
+// -----------------------------------------------------------------------------
+
+bool is_inited_file_any;
+bool is_inited_file_api;
+bool is_inited_file_duration;
+bool is_inited_file_field_mask;
+bool is_inited_file_empty;
+bool is_inited_file_source_context;
+bool is_inited_file_struct;
+bool is_inited_file_timestamp;
+bool is_inited_file_type;
+bool is_inited_file_wrappers;
+
 // -----------------------------------------------------------------------------
 // -----------------------------------------------------------------------------
 // Reserved Name.
 // Reserved Name.
 // -----------------------------------------------------------------------------
 // -----------------------------------------------------------------------------
@@ -250,6 +265,17 @@ static PHP_RINIT_FUNCTION(protobuf) {
   generated_pool_php = NULL;
   generated_pool_php = NULL;
   internal_generated_pool_php = NULL;
   internal_generated_pool_php = NULL;
 
 
+  is_inited_file_any = false;
+  is_inited_file_api = false;
+  is_inited_file_duration = false;
+  is_inited_file_field_mask = false;
+  is_inited_file_empty = false;
+  is_inited_file_source_context = false;
+  is_inited_file_struct = false;
+  is_inited_file_timestamp = false;
+  is_inited_file_type = false;
+  is_inited_file_wrappers = false;
+
   return 0;
   return 0;
 }
 }
 
 
@@ -288,6 +314,17 @@ static PHP_RSHUTDOWN_FUNCTION(protobuf) {
   }
   }
 #endif
 #endif
 
 
+  is_inited_file_any = true;
+  is_inited_file_api = true;
+  is_inited_file_duration = true;
+  is_inited_file_field_mask = true;
+  is_inited_file_empty = true;
+  is_inited_file_source_context = true;
+  is_inited_file_struct = true;
+  is_inited_file_timestamp = true;
+  is_inited_file_type = true;
+  is_inited_file_wrappers = true;
+
   return 0;
   return 0;
 }
 }
 
 

+ 11 - 0
php/ext/google/protobuf/protobuf.h

@@ -1172,6 +1172,17 @@ extern zend_class_entry* oneof_descriptor_type;
 // Well Known Type.
 // Well Known Type.
 // -----------------------------------------------------------------------------
 // -----------------------------------------------------------------------------
 
 
+extern bool is_inited_file_any;
+extern bool is_inited_file_api;
+extern bool is_inited_file_duration;
+extern bool is_inited_file_field_mask;
+extern bool is_inited_file_empty;
+extern bool is_inited_file_source_context;
+extern bool is_inited_file_struct;
+extern bool is_inited_file_timestamp;
+extern bool is_inited_file_type;
+extern bool is_inited_file_wrappers;
+
 PHP_METHOD(GPBMetadata_Any, initOnce);
 PHP_METHOD(GPBMetadata_Any, initOnce);
 PHP_METHOD(GPBMetadata_Api, initOnce);
 PHP_METHOD(GPBMetadata_Api, initOnce);
 PHP_METHOD(GPBMetadata_Duration, initOnce);
 PHP_METHOD(GPBMetadata_Duration, initOnce);

+ 10 - 2
php/tests/gdb_test.sh

@@ -1,10 +1,18 @@
 #!/bin/bash
 #!/bin/bash
 
 
+VERSION=$1
+
+export PATH=/usr/local/php-$VERSION/bin:$PATH
+export C_INCLUDE_PATH=/usr/local/php-$VERSION/include/php/main:/usr/local/php-$VERSION/include/php:$C_INCLUDE_PATH
+export CPLUS_INCLUDE_PATH=/usr/local/php-$VERSION/include/php/main:/usr/local/php-$VERSION/include/php:$CPLUS_INCLUDE_PATH
+
+php -i | grep "Configuration"
+
 # gdb --args php -dextension=../ext/google/protobuf/modules/protobuf.so `which
 # gdb --args php -dextension=../ext/google/protobuf/modules/protobuf.so `which
 # phpunit` --bootstrap autoload.php tmp_test.php
 # phpunit` --bootstrap autoload.php tmp_test.php
 #
 #
-gdb --args php -dextension=../ext/google/protobuf/modules/protobuf.so `which phpunit` --bootstrap autoload.php encode_decode_test.php
+# gdb --args php -dextension=../ext/google/protobuf/modules/protobuf.so `which phpunit` --bootstrap autoload.php encode_decode_test.php
 #
 #
-# gdb --args php -dextension=../ext/google/protobuf/modules/protobuf.so memory_leak_test.php
+gdb --args php -dextension=../ext/google/protobuf/modules/protobuf.so memory_leak_test.php
 #
 #
 # USE_ZEND_ALLOC=0 valgrind --leak-check=yes php -dextension=../ext/google/protobuf/modules/protobuf.so memory_leak_test.php
 # USE_ZEND_ALLOC=0 valgrind --leak-check=yes php -dextension=../ext/google/protobuf/modules/protobuf.so memory_leak_test.php

+ 32 - 6
php/tests/memory_leak_test.php

@@ -50,6 +50,13 @@ $to->mergeFromString($data);
 
 
 TestUtil::assertTestMessage($to);
 TestUtil::assertTestMessage($to);
 
 
+$from = new TestMessage();
+TestUtil::setTestMessage2($from);
+
+$data = $from->serializeToString();
+
+$to->mergeFromString($data);
+
 // TODO(teboring): This causes following tests fail in php7.
 // TODO(teboring): This causes following tests fail in php7.
 # $from->setRecursive($from);
 # $from->setRecursive($from);
 
 
@@ -104,7 +111,7 @@ assert(1 === $n->getOneofMessage()->getA());
 
 
 $m = new TestMessage();
 $m = new TestMessage();
 $m->mergeFromString(hex2bin('F80601'));
 $m->mergeFromString(hex2bin('F80601'));
-assert('F80601', bin2hex($m->serializeToString()));
+assert('f80601' === bin2hex($m->serializeToString()));
 
 
 // Test create repeated field via array.
 // Test create repeated field via array.
 $str_arr = array("abc");
 $str_arr = array("abc");
@@ -142,13 +149,32 @@ $from = new \Google\Protobuf\Value();
 $from->setNumberValue(1);
 $from->setNumberValue(1);
 assert(1, $from->getNumberValue());
 assert(1, $from->getNumberValue());
 
 
+// Test discard unknown in message.
+$m = new TestMessage();
+$from = hex2bin('F80601');
+$m->mergeFromString($from);
+$m->discardUnknownFields();
+$to = $m->serializeToString();
+assert("" === bin2hex($to));
+
+// Test clear
+$m = new TestMessage();
+TestUtil::setTestMessage($m);
+$m->clear();
+
+// Test unset map element
+$m = new TestMessage();
+$map = $m->getMapStringString();
+$map[1] = 1;
+unset($map[1]);
+
 // Test descriptor
 // Test descriptor
 $pool = \Google\Protobuf\DescriptorPool::getGeneratedPool();
 $pool = \Google\Protobuf\DescriptorPool::getGeneratedPool();
 $desc = $pool->getDescriptorByClassName("\Foo\TestMessage");
 $desc = $pool->getDescriptorByClassName("\Foo\TestMessage");
 $field = $desc->getField(1);
 $field = $desc->getField(1);
 
 
-# $from = new TestMessage();
-# $to = new TestMessage();
-# TestUtil::setTestMessage($from);
-# $to->mergeFrom($from);
-# TestUtil::assertTestMessage($to);
+$from = new TestMessage();
+$to = new TestMessage();
+TestUtil::setTestMessage($from);
+$to->mergeFrom($from);
+TestUtil::assertTestMessage($to);

+ 19 - 1
php/tests/test.sh

@@ -1,5 +1,11 @@
 #!/bin/bash
 #!/bin/bash
 
 
+VERSION=$1
+
+export PATH=/usr/local/php-$VERSION/bin:$PATH
+export C_INCLUDE_PATH=/usr/local/php-$VERSION/include/php/main:/usr/local/php-$VERSION/include/php:$C_INCLUDE_PATH
+export CPLUS_INCLUDE_PATH=/usr/local/php-$VERSION/include/php/main:/usr/local/php-$VERSION/include/php:$CPLUS_INCLUDE_PATH
+
 # Compile c extension
 # Compile c extension
 pushd ../ext/google/protobuf/
 pushd ../ext/google/protobuf/
 make clean || true
 make clean || true
@@ -15,7 +21,7 @@ do
   echo "****************************"
   echo "****************************"
   echo "* $t"
   echo "* $t"
   echo "****************************"
   echo "****************************"
-  php -dextension=../ext/google/protobuf/modules/protobuf.so `which phpunit` --bootstrap autoload.php $t
+  # php -dextension=../ext/google/protobuf/modules/protobuf.so `which phpunit` --bootstrap autoload.php $t
   echo ""
   echo ""
 done
 done
 
 
@@ -25,3 +31,15 @@ done
 export ZEND_DONT_UNLOAD_MODULES=1
 export ZEND_DONT_UNLOAD_MODULES=1
 export USE_ZEND_ALLOC=0
 export USE_ZEND_ALLOC=0
 valgrind --leak-check=yes php -dextension=../ext/google/protobuf/modules/protobuf.so memory_leak_test.php
 valgrind --leak-check=yes php -dextension=../ext/google/protobuf/modules/protobuf.so memory_leak_test.php
+
+# TODO(teboring): Only for debug (phpunit has memory leak which blocks this beging used by
+# regresssion test.)
+
+# for t in "${tests[@]}"
+# do
+#   echo "****************************"
+#   echo "* $t (memory leak)"
+#   echo "****************************"
+#   valgrind --leak-check=yes php -dextension=../ext/google/protobuf/modules/protobuf.so `which phpunit` --bootstrap autoload.php $t
+#   echo ""
+# done

+ 1 - 1
protoc-artifacts/pom.xml

@@ -10,7 +10,7 @@
   </parent>
   </parent>
   <groupId>com.google.protobuf</groupId>
   <groupId>com.google.protobuf</groupId>
   <artifactId>protoc</artifactId>
   <artifactId>protoc</artifactId>
-  <version>3.5.1</version>
+  <version>3.5.1-1</version>
   <packaging>pom</packaging>
   <packaging>pom</packaging>
   <name>Protobuf Compiler</name>
   <name>Protobuf Compiler</name>
   <description>
   <description>

+ 2 - 2
ruby/Rakefile

@@ -64,13 +64,13 @@ else
 
 
   task 'gem:windows' do
   task 'gem:windows' do
     require 'rake_compiler_dock'
     require 'rake_compiler_dock'
-    RakeCompilerDock.sh "bundle && IN_DOCKER=true rake cross native gem RUBY_CC_VERSION=2.4.0:2.3.0:2.2.2:2.1.5:2.0.0"
+    RakeCompilerDock.sh "bundle && IN_DOCKER=true rake cross native gem RUBY_CC_VERSION=2.5.0:2.4.0:2.3.0:2.2.2:2.1.6:2.0.0"
   end
   end
 
 
   if RUBY_PLATFORM =~ /darwin/
   if RUBY_PLATFORM =~ /darwin/
     task 'gem:native' do
     task 'gem:native' do
       system "rake genproto"
       system "rake genproto"
-      system "rake cross native gem RUBY_CC_VERSION=2.4.0:2.3.0:2.2.2:2.1.5:2.0.0"
+      system "rake cross native gem RUBY_CC_VERSION=2.5.0:2.4.0:2.3.0:2.2.2:2.1.6:2.0.0"
     end
     end
   else
   else
     task 'gem:native' => [:genproto, 'gem:windows']
     task 'gem:native' => [:genproto, 'gem:windows']

+ 1 - 1
ruby/google-protobuf.gemspec

@@ -1,6 +1,6 @@
 Gem::Specification.new do |s|
 Gem::Specification.new do |s|
   s.name        = "google-protobuf"
   s.name        = "google-protobuf"
-  s.version     = "3.5.1"
+  s.version     = "3.5.1.2"
   s.licenses    = ["BSD-3-Clause"]
   s.licenses    = ["BSD-3-Clause"]
   s.summary     = "Protocol Buffers"
   s.summary     = "Protocol Buffers"
   s.description = "Protocol Buffers are Google's data interchange format."
   s.description = "Protocol Buffers are Google's data interchange format."

+ 8 - 8
tests.sh

@@ -419,7 +419,7 @@ build_php5.5_c() {
   use_php 5.5
   use_php 5.5
   wget https://phar.phpunit.de/phpunit-4.8.0.phar -O /usr/bin/phpunit
   wget https://phar.phpunit.de/phpunit-4.8.0.phar -O /usr/bin/phpunit
   pushd php/tests
   pushd php/tests
-  /bin/bash ./test.sh
+  /bin/bash ./test.sh 5.5
   popd
   popd
   # TODO(teboring): Add it back
   # TODO(teboring): Add it back
   # pushd conformance
   # pushd conformance
@@ -430,7 +430,7 @@ build_php5.5_c() {
 build_php5.5_zts_c() {
 build_php5.5_zts_c() {
   use_php_zts 5.5
   use_php_zts 5.5
   wget https://phar.phpunit.de/phpunit-4.8.0.phar -O /usr/bin/phpunit
   wget https://phar.phpunit.de/phpunit-4.8.0.phar -O /usr/bin/phpunit
-  cd php/tests && /bin/bash ./test.sh && cd ../..
+  cd php/tests && /bin/bash ./test.sh 5.5-zts && cd ../..
   # TODO(teboring): Add it back
   # TODO(teboring): Add it back
   # pushd conformance
   # pushd conformance
   # make test_php_zts_c
   # make test_php_zts_c
@@ -453,7 +453,7 @@ build_php5.6() {
 build_php5.6_c() {
 build_php5.6_c() {
   use_php 5.6
   use_php 5.6
   wget https://phar.phpunit.de/phpunit-5.7.0.phar -O /usr/bin/phpunit
   wget https://phar.phpunit.de/phpunit-5.7.0.phar -O /usr/bin/phpunit
-  cd php/tests && /bin/bash ./test.sh && cd ../..
+  cd php/tests && /bin/bash ./test.sh 5.6 && cd ../..
   # TODO(teboring): Add it back
   # TODO(teboring): Add it back
   # pushd conformance
   # pushd conformance
   # make test_php_c
   # make test_php_c
@@ -463,7 +463,7 @@ build_php5.6_c() {
 build_php5.6_zts_c() {
 build_php5.6_zts_c() {
   use_php_zts 5.6
   use_php_zts 5.6
   wget https://phar.phpunit.de/phpunit-5.7.0.phar -O /usr/bin/phpunit
   wget https://phar.phpunit.de/phpunit-5.7.0.phar -O /usr/bin/phpunit
-  cd php/tests && /bin/bash ./test.sh && cd ../..
+  cd php/tests && /bin/bash ./test.sh 5.6-zts && cd ../..
   # TODO(teboring): Add it back
   # TODO(teboring): Add it back
   # pushd conformance
   # pushd conformance
   # make test_php_zts_c
   # make test_php_zts_c
@@ -511,7 +511,7 @@ build_php7.0() {
 build_php7.0_c() {
 build_php7.0_c() {
   use_php 7.0
   use_php 7.0
   wget https://phar.phpunit.de/phpunit-5.6.0.phar -O /usr/bin/phpunit
   wget https://phar.phpunit.de/phpunit-5.6.0.phar -O /usr/bin/phpunit
-  cd php/tests && /bin/bash ./test.sh && cd ../..
+  cd php/tests && /bin/bash ./test.sh 7.0 && cd ../..
   # TODO(teboring): Add it back
   # TODO(teboring): Add it back
   # pushd conformance
   # pushd conformance
   # make test_php_c
   # make test_php_c
@@ -521,7 +521,7 @@ build_php7.0_c() {
 build_php7.0_zts_c() {
 build_php7.0_zts_c() {
   use_php_zts 7.0
   use_php_zts 7.0
   wget https://phar.phpunit.de/phpunit-5.6.0.phar -O /usr/bin/phpunit
   wget https://phar.phpunit.de/phpunit-5.6.0.phar -O /usr/bin/phpunit
-  cd php/tests && /bin/bash ./test.sh && cd ../..
+  cd php/tests && /bin/bash ./test.sh 7.0-zts && cd ../..
   # TODO(teboring): Add it back.
   # TODO(teboring): Add it back.
   # pushd conformance
   # pushd conformance
   # make test_php_zts_c
   # make test_php_zts_c
@@ -575,7 +575,7 @@ build_php7.1() {
 build_php7.1_c() {
 build_php7.1_c() {
   use_php 7.1
   use_php 7.1
   wget https://phar.phpunit.de/phpunit-5.6.0.phar -O /usr/bin/phpunit
   wget https://phar.phpunit.de/phpunit-5.6.0.phar -O /usr/bin/phpunit
-  cd php/tests && /bin/bash ./test.sh && cd ../..
+  cd php/tests && /bin/bash ./test.sh 7.1 && cd ../..
   pushd conformance
   pushd conformance
   # make test_php_c
   # make test_php_c
   popd
   popd
@@ -584,7 +584,7 @@ build_php7.1_c() {
 build_php7.1_zts_c() {
 build_php7.1_zts_c() {
   use_php_zts 7.1
   use_php_zts 7.1
   wget https://phar.phpunit.de/phpunit-5.6.0.phar -O /usr/bin/phpunit
   wget https://phar.phpunit.de/phpunit-5.6.0.phar -O /usr/bin/phpunit
-  cd php/tests && /bin/bash ./test.sh && cd ../..
+  cd php/tests && /bin/bash ./test.sh 7.1-zts && cd ../..
   pushd conformance
   pushd conformance
   # make test_php_c
   # make test_php_c
   popd
   popd