From: William Djaja Tjokroaminata Date: 2002-08-15T23:34:47+09:00 Subject: Re: Data_Make_Struct Considered Dangerous? Hi, After examining the code further, our inconsistency happened because I did not give exactly the correct example. Instead of just struct/class inside another struct/class, it is struct/class inside a struct inside a struct/class. Therefore, in the outer struct/class there is a pointer. I allocate memory for this pointer. When I try to initialize this newly allocated memory, the gc gets invoked. So I guess both of us are actually correct: 1) In Data_Make_Struct Ruby fills the resulting struct with zeros. 2) Because Data_Make_Struct (or even Data_Wrap_Struct) may invoke gc, when we initialize struct members with Data_Make_Struct, we have to do "double initialization". Actually the problem is much more general than this. Before we call any Ruby function that may invoke gc (such as the innocent looking rb_str_new2 ()), we have to make sure that all our data are initialized properly. This was tricky because it occured inside my initialization function itself. What I mean is, in C usually I do this: ptr = (my_type*) malloc (sizeof (my_type)); ptr->data1 = val; ptr->data2 = rb_str_new2 (...); ... Now, in Ruby, I have to change my habit to ptr = (type*) malloc (sizeof (type)); /* Fill in with some generic, default values */ ptr->data1 = 0; ptr->data2 = Qfalse; ... /* Fill in with the actual data */ ptr->data1 = val; ptr->data2 = rb_str_new2 (...); /* may invoke gc */ ... Well, I guess so far the codes that I have dealt with are not as convoluted as the gc concept. On the other hand, this supports my assertion that ALLOC () is much more dangerous than malloc (). In ALLOC, we have to make sure that all data are already proper; in malloc () there is no possibility of jumping around at that point. Finally, because Data_Make_Struct really calls ALLOC, then Data_Make_Struct is indeed dangerous. Regards, Bill ============================================================================ nobu.nokada@softhome.net wrote: >> --------------------------------------------------- >> > It sounds strange. Data_Make_Struct() fills the allocated >> > structure with 0 and rb_gc_mark() ignores 0 which is equal to >> > Qfalse. >> --------------------------------------------------- >> I think this can only happen when we have a struct/class inside >> another struct/class. What I observed is, while we are creating the >> inner struct/class, gc gets called and try to mark the outer >> struct/class. Are you saying that even in this case it is safe >> because the outer struct/class should all be filled with zeros? > Yes, I guess so. >> Based on your response above, are you saying that this >> "double-initializing" is actually not needed? (in which case, the >> error is actually generated somewhere else?) > It should be in Data_Make_Struct().