-
Notifications
You must be signed in to change notification settings - Fork 2.2k
[BUG]: Segmentation fault on Windows with abstract classss #3217
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
The problem appears to be that Knob is getting deallocated before it is returned by def GetKnob(self):
return MyKnob() Setting a global def GetKnob(self):
return MYKNOB works. |
I tried the return value policies but it's a little tricky here, since the passing by reference means the C++ can't take ownership of the knob and python will always destroy the object if it is returned without referencing it elsewhere. The above hack actually works fairly well for my purposes. Feel free to close this if there is no better resolution. btw the classes page of the documentation should maybe link to the return value policies page. |
I get:
|
Also, this looks very problematic to me. You are returning a reference to an object you've created, but how does C++ know when to remove that object, and how does it know the object is actually larger than the reference you have (slicing issue)? If you can use smart pointers, I think this would be much simpler and easier. If not, I'd try to use move, not references. Expecting a user to remember to add a In general, no references to virtual classes in C++. They get sliced. Always use (smart) pointers. |
Try allocating the knob in the class MyDoor(pybind_test.Door):
def __init__(self, name):
pybind_test.Door.__init__(self)
self.name = name
self.knob = MyKnob()
def Name(self):
return self.name
def GetKnob(self):
return self.knob Then at least you're not returning a temporary. |
@laramiel yes that works but isn't the behavior I want. Pretend it's called "Knob factory" instead ;-). Also I tried shared_pointers and return value policies and couldn't get it to stop deallocating on return. The failure of shared_pointer really surprised me. |
I've already said - you can't return a reference to a temporary object with a virtual class. It doesn't work. The compiler slices off part of your object. It's UB. Using shared pointers should be just fine. Do you have the shared pointer version to look at? |
Thanks for your help. Replace all |
The cause of the issue is described here:
It would be great if pybind could keep the python instance around when there is a shared pointer to it. |
Required prerequisites
Problem description
A have two abstract C++ class: Door and Knob. Door returns a Knob with Door::GetKnob. The knob can be pulled with Knob::Pull(). Door successfully calls Door::GetKnob and gets a non-null knob, but the code crashes when Knob::Pull is called.
Reproducible example code
C++
Python
Output
Program crashes at this point. (while calling
knob.Pull();
)The text was updated successfully, but these errors were encountered: