ruby-rice / rice

Ruby Interface for C++ Extensions
http://ruby-rice.github.io/
Other
378 stars 63 forks source link

How to prevent double free error #124

Closed ankane closed 4 years ago

ankane commented 4 years ago

Hey @jasonroelofs, I'm running into a SignalException: SIGABRT error in or-tools when Ruby exits after a specific method is called that returns an instance of a class wrapped by Rice.

On Linux: double free or corruption (fasttop) On Mac: pointer being freed was not allocated

When the method runs but doesn't return the instance (like returning its address in memory instead), there isn't an error.

.define_method(
  "num_var",
  *[](MPSolver& self, double lb, double ub, const std::string& name) {
    // MPVariable is wrapped with:
    // define_class_under<MPVariable>(rb_mORTools, "MPVariable");
    MPVariable* var = self.MakeNumVar(lb, ub, name);

    // return var; // error
    return (uint64) &var; // no error
  })

This leads me to suspect that Ruby and the library are both freeing the object. Is there a way to tell Rice not to do this? I think this may be related to https://github.com/jasonroelofs/rice/issues/96.

ankane commented 4 years ago

Spoke too soon. Figured it out in https://github.com/ankane/or-tools/commit/2511996e624a21161c6868ec5a536b513ab91f11 based on #96.

Sorry for the bother!

jasonroelofs commented 4 years ago

Gotcha, glad you were able to track that down. Managing ownership of objects across C++ / Ruby boundaries is not trivial. Might be something worth making clearer in the documentation.