Эх сурвалжийг харах

Fixed crash bug and moved initialization into init method.

Joshua Haberman 6 жил өмнө
parent
commit
671c2459fc

+ 9 - 12
ruby/ext/google/protobuf_c/message.c

@@ -62,26 +62,19 @@ VALUE Message_alloc(VALUE klass) {
   Descriptor* desc = ruby_to_Descriptor(descriptor);
   MessageHeader* msg;
   VALUE ret;
+  size_t size;
 
   if (desc->layout == NULL) {
     create_layout(desc);
   }
 
-  msg = (MessageHeader*)ALLOC_N(uint8_t,
-                                sizeof(MessageHeader) + desc->layout->size);
-
-  // Required in case a GC happens before layout_init().
-  memset(msg, 0, desc->layout->size);
-
-  // We wrap first so that everything in the message object is GC-rooted in case
-  // a collection happens during object creation in layout_init().
-  ret = TypedData_Wrap_Struct(klass, &Message_type, msg);
+  msg = ALLOC_N(uint8_t, sizeof(MessageHeader) + desc->layout->size);
   msg->descriptor = desc;
-  rb_ivar_set(ret, descriptor_instancevar_interned, descriptor);
-
   msg->unknown_fields = NULL;
+  memcpy(Message_data(msg), desc->layout->empty_template, desc->layout->size);
 
-  layout_init(desc->layout, Message_data(msg));
+  ret = TypedData_Wrap_Struct(klass, &Message_type, msg);
+  rb_ivar_set(ret, descriptor_instancevar_interned, descriptor);
 
   return ret;
 }
@@ -473,7 +466,11 @@ int Message_initialize_kwarg(VALUE key, VALUE val, VALUE _self) {
  * Message class are provided on each concrete message class.
  */
 VALUE Message_initialize(int argc, VALUE* argv, VALUE _self) {
+  MessageHeader* self;
   VALUE hash_args;
+  TypedData_Get_Struct(_self, MessageHeader, &Message_type, self);
+
+  layout_init(self->descriptor->layout, Message_data(self));
 
   if (argc == 0) {
     return Qnil;

+ 0 - 2
ruby/ext/google/protobuf_c/storage.c

@@ -947,8 +947,6 @@ void layout_init(MessageLayout* layout, void* storage) {
   VALUE* value = (VALUE*)CHARPTR_AT(storage, layout->value_offset);
   int i;
 
-  memcpy(storage, layout->empty_template, layout->size);
-
   for (i = 0; i < layout->repeated_count; i++, value++) {
     *value = RepeatedField_new_this_type(*value);
   }