From 7358ef9b9f32db97725f68ec1605d29744b4c4dc Mon Sep 17 00:00:00 2001 From: wmayer Date: Sat, 22 Mar 2025 14:44:15 +0100 Subject: [PATCH] Base: Allow to also throw exception by given Python type --- src/Base/ExceptionFactory.cpp | 11 ++++++++--- src/Base/ExceptionFactory.h | 26 ++++++++++++++++++++++++++ src/Base/Interpreter.cpp | 8 +++----- 3 files changed, 37 insertions(+), 8 deletions(-) diff --git a/src/Base/ExceptionFactory.cpp b/src/Base/ExceptionFactory.cpp index d3816fef6d..ae0b1801c5 100644 --- a/src/Base/ExceptionFactory.cpp +++ b/src/Base/ExceptionFactory.cpp @@ -52,11 +52,16 @@ void ExceptionFactory::raiseException(PyObject* pydict) const if (edict.hasKey("sclassname")) { classname = static_cast(Py::String(edict.getItem("sclassname"))); - std::map::const_iterator pProd; - - pProd = _mpcProducers.find(classname); + auto pProd = _mpcProducers.find(classname); if (pProd != _mpcProducers.end()) { static_cast(pProd->second)->raiseException(pydict); } } } + +void ExceptionFactory::raiseExceptionByType(const PyExceptionData& data) const +{ + for (const auto& it : _mpcProducers) { + static_cast(it.second)->raiseExceptionByType(data); // NOLINT + } +} diff --git a/src/Base/ExceptionFactory.h b/src/Base/ExceptionFactory.h index 6cb32448df..06f8a7f119 100644 --- a/src/Base/ExceptionFactory.h +++ b/src/Base/ExceptionFactory.h @@ -26,6 +26,7 @@ #include "Factory.h" +#include #include // Python stuff @@ -34,6 +35,13 @@ using PyObject = struct _object; namespace Base { +struct PyExceptionData +{ + PyObject* pyexc {}; + std::string message; + bool reported {}; +}; + /// Abstract base class of all exception producers class BaseExport AbstractExceptionProducer: public AbstractProducer { @@ -45,6 +53,7 @@ public: return nullptr; } virtual void raiseException(PyObject* pydict) const = 0; + virtual void raiseExceptionByType(const PyExceptionData&) const = 0; }; // -------------------------------------------------------------------- @@ -57,6 +66,7 @@ public: static void Destruct(); void raiseException(PyObject* pydict) const; + void raiseExceptionByType(const PyExceptionData& data) const; private: static ExceptionFactory* _pcSingleton; // NOLINT @@ -72,6 +82,8 @@ class ExceptionProducer: public AbstractExceptionProducer public: ExceptionProducer() { + CLASS cls; + pyExcType = cls.getPyExceptionType(); ExceptionFactory::Instance().AddProducer(typeid(CLASS).name(), this); } @@ -82,6 +94,20 @@ public: throw cls; } + + void raiseExceptionByType(const PyExceptionData& data) const override + { + if (pyExcType == data.pyexc) { + CLASS cls; + cls.setMessage(data.message); + cls.setReported(data.reported); + + throw cls; + } + } + +private: + PyObject* pyExcType {}; }; } // namespace Base diff --git a/src/Base/Interpreter.cpp b/src/Base/Interpreter.cpp index ac2677dae3..1bd857fab7 100644 --- a/src/Base/Interpreter.cpp +++ b/src/Base/Interpreter.cpp @@ -114,12 +114,10 @@ void PyException::raiseException() Base::ExceptionFactory::Instance().raiseException(edict.ptr()); } - if (_exceptionType == PyExc_FC_FreeCADAbort) { - AbortException exc(getMessage()); - exc.setReported(getReported()); - throw exc; - } + PyExceptionData data {_exceptionType, getMessage(), getReported()}; + Base::ExceptionFactory::Instance().raiseExceptionByType(data); + // Fallback throw *this; }