-
Notifications
You must be signed in to change notification settings - Fork 2.2k
ctor of object wrapper should propagate possible python exceptions #2195
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
This seems like a possibility, yes. Quite a corner case because this shouldn't really happen anyway, but fair enough, it would be better. Do you have time to make a PR of the places where you found this? We'd also need to check if every time a |
This is the collection of all things
To elaborate:
|
I recently found that the problem cannot solved by simply
|
That should be fine. You're describing what already is happening in
I understand what you would like to achieve here, but I'm not sure we can. At least not without breaking a ton of code, as the pybind docs say that any exception propagating from python will propagate as try {
pyf(); // May reach into C++ through python
} catch( py::error_already_set ) { // No reason to catch anything else
}
That may be possible, but first we need to agree what is the critical path. Does import logic of extension modules count as critical? What about importing an embedded module? In both cases |
Thanks for the overview, @bstaletic! Great job, for reference :-)
I agree here. Also, there's a mapping defined from C++ exceptions into Python, but this is not a bijective one. So it's an additional difficulty to remember that a At any rate, I would argue that this is a reasonably easy addition if needed in custom code: surround calls to Python with a catch statement for |
Not quite. If you catch one thing, only to throw another, you're losing context of where that other exception came from. That original context is more important than the type. |
#2112 would allow users to chain exceptions. I'm using this like so in some C callbacks: try {
// some pybind code
} catch (py::error_already_set &e) {
e.caused(SomeExceptionType, "something");
// do something with the error... pick your poison depending on your goals
e.restore();
PyErr_Print();
} Yields a nice error/traceback with both messages in it. |
Seems you guys already got a good solution, I am closing the issue since I am not active on this project. |
Issue description
In the ctor of every pybind object wrapper, if
PyXXX_New
returns nullptr, pybind will invokepybind11_fail
which throwsstd::runtime_error
, which doesn't propagate the already set pythonMemoryError
pybind should throw a
std::bad_alloc
or at leastpy::error_already_set
if it detects a python exception is setpy::tuple as a example
Some other places in the code also not propagating MemoryError, like pybind11.hpp#340
Reproducible example code
calling
make_huge_tuple_pybind
in python gotRuntimeError
calling
make_buge_tuple_cpy
in python gotMemoryError
The text was updated successfully, but these errors were encountered: