diff options
-rw-r--r-- | generator/cppgenerator.cpp | 12 | ||||
-rw-r--r-- | libshiboken/basewrapper.cpp | 123 | ||||
-rw-r--r-- | libshiboken/basewrapper.h | 66 | ||||
-rw-r--r-- | libshiboken/basewrapper_p.h | 77 | ||||
-rw-r--r-- | libshiboken/bindingmanager.cpp | 24 | ||||
-rw-r--r-- | libshiboken/bindingmanager.h | 5 | ||||
-rw-r--r-- | libshiboken/conversions.h | 4 |
7 files changed, 182 insertions, 129 deletions
diff --git a/generator/cppgenerator.cpp b/generator/cppgenerator.cpp index e7f0e428..fe623953 100644 --- a/generator/cppgenerator.cpp +++ b/generator/cppgenerator.cpp @@ -779,13 +779,13 @@ void CppGenerator::writeMetaObjectMethod(QTextStream& s, const AbstractMetaClass { Indentation indentation(INDENT); s << INDENT << "PyObject *pySelf = BindingManager::instance().retrieveWrapper(this);\n" - << INDENT << "void *typeData = Shiboken::getTypeUserData(reinterpret_cast<Shiboken::SbkBaseWrapper*>(pySelf));" << endl + << INDENT << "void *typeData = Shiboken::getTypeUserData(reinterpret_cast<SbkBaseWrapper*>(pySelf));" << endl << INDENT << "if (!typeData) {" << endl; { Indentation indentation2(INDENT); s << INDENT << "m_metaObject = PySide::DynamicQMetaObject::createBasedOn(pySelf, pySelf->ob_type, &" << metaClass->qualifiedCppName() << "::staticMetaObject);" << endl - << INDENT << "Shiboken::setTypeUserData(reinterpret_cast<Shiboken::SbkBaseWrapper*>(pySelf), m_metaObject, PySide::deleteDynamicQMetaObject);" << endl; + << INDENT << "Shiboken::setTypeUserData(reinterpret_cast<SbkBaseWrapper*>(pySelf), m_metaObject, PySide::deleteDynamicQMetaObject);" << endl; } s << INDENT << "} else {" << endl; { @@ -927,13 +927,13 @@ void CppGenerator::writeConstructorWrapper(QTextStream& s, const AbstractMetaFun s << endl; } - s << INDENT << "sbkSelf->validCppObject = 1;" << endl; + s << INDENT << "Shiboken::Wrapper::setValidCpp(sbkSelf, true);" << endl; // If the created C++ object has a C++ wrapper the ownership is assigned to Python // (first "1") and the flag indicating that the Python wrapper holds an C++ wrapper // is marked as true (the second "1"). Otherwise the default values apply: // Python owns it and C++ wrapper is false. if (shouldGenerateCppWrapper(overloads.first()->ownerClass())) - s << INDENT << "sbkSelf->containsCppWrapper = 1;" << endl; + s << INDENT << "Shiboken::Wrapper::setHasCppWrapper(sbkSelf, true);" << endl; s << INDENT << "BindingManager::instance().registerWrapper(sbkSelf, cptr);" << endl; // Create metaObject and register signal/slot @@ -1843,7 +1843,7 @@ void CppGenerator::writeMethodCall(QTextStream& s, const AbstractMetaFunction* f } if (func->isAbstract()) { - s << INDENT << "if (SbkBaseWrapper_containsCppWrapper(self)) {\n"; + s << INDENT << "if (Shiboken::Wrapper::hasCppWrapper(reinterpret_cast<SbkBaseWrapper*>(self))) {\n"; { Indentation indent(INDENT); s << INDENT << "PyErr_SetString(PyExc_NotImplementedError, \"pure virtual method '"; @@ -2429,7 +2429,7 @@ void CppGenerator::writeClassDefinition(QTextStream& s, const AbstractMetaClass* s << INDENT << "PyObject_HEAD_INIT(&Shiboken::SbkBaseWrapperType_Type)" << endl; s << INDENT << "/*ob_size*/ 0," << endl; s << INDENT << "/*tp_name*/ \"" << metaClass->fullName() << "\"," << endl; - s << INDENT << "/*tp_basicsize*/ sizeof(Shiboken::SbkBaseWrapper)," << endl; + s << INDENT << "/*tp_basicsize*/ sizeof(SbkBaseWrapper)," << endl; s << INDENT << "/*tp_itemsize*/ 0," << endl; s << INDENT << "/*tp_dealloc*/ " << tp_dealloc << ',' << endl; s << INDENT << "/*tp_print*/ 0," << endl; diff --git a/libshiboken/basewrapper.cpp b/libshiboken/basewrapper.cpp index ae5b6dda..0e2e7871 100644 --- a/libshiboken/basewrapper.cpp +++ b/libshiboken/basewrapper.cpp @@ -165,11 +165,11 @@ SbkBaseWrapperType SbkBaseWrapper_Type = { { { void removeParent(SbkBaseWrapper* child) { - ParentInfo* pInfo = child->parentInfo; + ParentInfo* pInfo = child->d->parentInfo; if (!pInfo || !pInfo->parent) return; - ChildrenList& oldBrothers = pInfo->parent->parentInfo->children; + ChildrenList& oldBrothers = pInfo->parent->d->parentInfo->children; oldBrothers.remove(child); pInfo->parent = 0; @@ -205,15 +205,15 @@ void setParent(PyObject* parent, PyObject* child) SbkBaseWrapper* child_ = reinterpret_cast<SbkBaseWrapper*>(child); if (!parentIsNull) { - if (!parent_->parentInfo) - parent_->parentInfo = new ParentInfo; + if (!parent_->d->parentInfo) + parent_->d->parentInfo = new ParentInfo; // do not re-add a child - ChildrenList& children = parent_->parentInfo->children; + ChildrenList& children = parent_->d->parentInfo->children; if (std::find(children.begin(), children.end(), child_) != children.end()) return; } - ParentInfo* pInfo = child_->parentInfo; + ParentInfo* pInfo = child_->d->parentInfo; bool hasAnotherParent = pInfo && pInfo->parent && pInfo->parent != parent_; //Avoid destroy child during reparent operation @@ -224,12 +224,12 @@ void setParent(PyObject* parent, PyObject* child) removeParent(child_); // Add the child to the new parent - pInfo = child_->parentInfo; + pInfo = child_->d->parentInfo; if (!parentIsNull) { if (!pInfo) - pInfo = child_->parentInfo = new ParentInfo; + pInfo = child_->d->parentInfo = new ParentInfo; pInfo->parent = parent_; - parent_->parentInfo->children.push_back(child_); + parent_->d->parentInfo->children.push_back(child_); Py_INCREF(child_); } @@ -238,7 +238,7 @@ void setParent(PyObject* parent, PyObject* child) static void _destroyParentInfo(SbkBaseWrapper* obj, bool removeFromParent) { - ParentInfo* pInfo = obj->parentInfo; + ParentInfo* pInfo = obj->d->parentInfo; if (removeFromParent && pInfo && pInfo->parent) removeParent(obj); @@ -248,11 +248,9 @@ static void _destroyParentInfo(SbkBaseWrapper* obj, bool removeFromParent) SbkBaseWrapper*& child = *it; // keep this, the wrapper still alive - if (!SbkBaseWrapper_containsCppWrapper(obj) && - SbkBaseWrapper_containsCppWrapper(child) && - child->parentInfo) { - child->parentInfo->parent = 0; - child->parentInfo->hasWrapperRef = true; + if (!obj->d->containsCppWrapper && child->d->containsCppWrapper && child->d->parentInfo) { + child->d->parentInfo->parent = 0; + child->d->parentInfo->hasWrapperRef = true; SbkBaseWrapper_setOwnership(child, false); } else { _destroyParentInfo(child, false); @@ -260,7 +258,7 @@ static void _destroyParentInfo(SbkBaseWrapper* obj, bool removeFromParent) } } delete pInfo; - obj->parentInfo = 0; + obj->d->parentInfo = 0; } } @@ -288,9 +286,9 @@ PyObject* SbkBaseWrapper_New(SbkBaseWrapperType* instanceType, } SbkBaseWrapper* self = reinterpret_cast<SbkBaseWrapper*>(SbkBaseWrapper_TpNew(reinterpret_cast<PyTypeObject*>(instanceType), 0, 0)); - self->cptr[0] = cptr; - self->hasOwnership = hasOwnership; - self->validCppObject = 1; + self->d->cptr[0] = cptr; + self->d->hasOwnership = hasOwnership; + self->d->validCppObject = 1; BindingManager::instance().registerWrapper(self, cptr); return reinterpret_cast<PyObject*>(self); } @@ -319,18 +317,19 @@ void walkThroughClassHierarchy(PyTypeObject* currentType, HierarchyVisitor* visi PyObject* SbkBaseWrapper_TpNew(PyTypeObject* subtype, PyObject*, PyObject*) { SbkBaseWrapper* self = reinterpret_cast<SbkBaseWrapper*>(subtype->tp_alloc(subtype, 0)); + self->d = new SbkBaseWrapperPrivate; SbkBaseWrapperType* sbkType = reinterpret_cast<SbkBaseWrapperType*>(subtype); int numBases = sbkType->is_multicpp ? getNumberOfCppBaseClasses(subtype) : 1; - self->cptr = new void*[numBases]; - std::memset(self->cptr, 0, sizeof(void*)*numBases); - self->hasOwnership = 1; - self->containsCppWrapper = 0; - self->validCppObject = 0; - self->parentInfo = 0; + self->d->cptr = new void*[numBases]; + std::memset(self->d->cptr, 0, sizeof(void*)*numBases); + self->d->hasOwnership = 1; + self->d->containsCppWrapper = 0; + self->d->validCppObject = 0; + self->d->parentInfo = 0; self->ob_dict = 0; self->weakreflist = 0; - self->referredObjects = 0; + self->d->referredObjects = 0; return reinterpret_cast<PyObject*>(self); } @@ -340,7 +339,7 @@ void* getCppPointer(PyObject* wrapper, PyTypeObject* desiredType) int idx = 0; if (reinterpret_cast<SbkBaseWrapperType*>(type)->is_multicpp) idx = getTypeIndexOnHierarchy(type, desiredType); - return reinterpret_cast<Shiboken::SbkBaseWrapper*>(wrapper)->cptr[idx]; + return reinterpret_cast<SbkBaseWrapper*>(wrapper)->d->cptr[idx]; } bool setCppPointer(SbkBaseWrapper* wrapper, PyTypeObject* desiredType, void* cptr) @@ -349,11 +348,11 @@ bool setCppPointer(SbkBaseWrapper* wrapper, PyTypeObject* desiredType, void* cpt if (reinterpret_cast<SbkBaseWrapperType*>(wrapper->ob_type)->is_multicpp) idx = getTypeIndexOnHierarchy(wrapper->ob_type, desiredType); - bool alreadyInitialized = wrapper->cptr[idx]; + bool alreadyInitialized = wrapper->d->cptr[idx]; if (alreadyInitialized) PyErr_SetString(PyExc_RuntimeError, "You can't initialize an object twice!"); else - wrapper->cptr[idx] = cptr; + wrapper->d->cptr[idx] = cptr; return !alreadyInitialized; } @@ -362,7 +361,7 @@ bool cppObjectIsInvalid(PyObject* wrapper) { if (!wrapper || wrapper == Py_None || wrapper->ob_type->ob_type != &Shiboken::SbkBaseWrapperType_Type - || ((Shiboken::SbkBaseWrapper*)wrapper)->validCppObject) { + || ((SbkBaseWrapper*)wrapper)->d->validCppObject) { return false; } PyErr_SetString(PyExc_RuntimeError, "Internal C++ object already deleted."); @@ -399,10 +398,10 @@ void keepReference(SbkBaseWrapper* self, const char* key, PyObject* referredObje bool isNone = (!referredObject || (referredObject == Py_None)); - if (!self->referredObjects) - self->referredObjects = new Shiboken::RefCountMap; + if (!self->d->referredObjects) + self->d->referredObjects = new Shiboken::RefCountMap; - RefCountMap& refCountMap = *(self->referredObjects); + RefCountMap& refCountMap = *(self->d->referredObjects); if (!isNone) incRefPyObject(referredObject); @@ -423,15 +422,15 @@ void keepReference(SbkBaseWrapper* self, const char* key, PyObject* referredObje void clearReferences(SbkBaseWrapper* self) { - if (!self->referredObjects) + if (!self->d->referredObjects) return; - RefCountMap& refCountMap = *(self->referredObjects); + RefCountMap& refCountMap = *(self->d->referredObjects); RefCountMap::iterator iter; for (iter = refCountMap.begin(); iter != refCountMap.end(); ++iter) decRefPyObjectlist(iter->second); - delete self->referredObjects; - self->referredObjects = 0; + delete self->d->referredObjects; + self->d->referredObjects = 0; } bool importModule(const char* moduleName, PyTypeObject*** cppApiPtr) @@ -458,7 +457,7 @@ public: DtorCallerVisitor(SbkBaseWrapper* pyObj) : m_count(0), m_pyObj(pyObj) {} virtual void visit(SbkBaseWrapperType* node) { - node->cpp_dtor(m_pyObj->cptr[m_count]); + node->cpp_dtor(m_pyObj->d->cptr[m_count]); m_count++; } private: @@ -473,24 +472,25 @@ void deallocWrapper(PyObject* pyObj) PyObject_ClearWeakRefs(pyObj); BindingManager::instance().releaseWrapper(pyObj); - if (SbkBaseWrapper_hasOwnership(pyObj)) { + if (sbkObj->d->hasOwnership) { SbkBaseWrapperType* sbkType = reinterpret_cast<SbkBaseWrapperType*>(pyObj->ob_type); if (sbkType->is_multicpp) { DtorCallerVisitor visitor(sbkObj); walkThroughClassHierarchy(pyObj->ob_type, &visitor); } else { - sbkType->cpp_dtor(sbkObj->cptr[0]); + sbkType->cpp_dtor(sbkObj->d->cptr[0]); } } - if (SbkBaseWrapper_hasParentInfo(pyObj)) + if (sbkObj->d->parentInfo) destroyParentInfo(sbkObj); clearReferences(sbkObj); Py_XDECREF(sbkObj->ob_dict); - delete[] sbkObj->cptr; - sbkObj->cptr = 0; + delete[] sbkObj->d->cptr; + sbkObj->d->cptr = 0; + delete sbkObj->d; Py_TYPE(pyObj)->tp_free(pyObj); } @@ -645,7 +645,9 @@ std::list<PyObject*> splitPyObject(PyObject* pyObj) if (PySequence_Check(pyObj)) { AutoDecRef lst(PySequence_Fast(pyObj, "Invalid keep reference object.")); for(int i = 0, i_max = PySequence_Fast_GET_SIZE(lst.object()); i < i_max; i++) { - result.push_back(PySequence_Fast_GET_ITEM(lst.object(), i)); + PyObject* item = PySequence_Fast_GET_ITEM(lst.object(), i); + if (isShibokenType(item)) + result.push_back(item); } } else { result.push_back(pyObj); @@ -675,17 +677,40 @@ static void decRefPyObjectlist(const std::list<PyObject*> &lst) void SbkBaseWrapper_setOwnership(SbkBaseWrapper* pyobj, bool owner) { - pyobj->hasOwnership = owner; + pyobj->d->hasOwnership = owner; } void SbkBaseWrapper_setOwnership(PyObject* pyobj, bool owner) { - std::list<PyObject*> objs = splitPyObject(pyobj); - std::list<PyObject*>::const_iterator it; - for(it=objs.begin(); it != objs.end(); it++) - SbkBaseWrapper_setOwnership(reinterpret_cast<SbkBaseWrapper*>(*it), owner); + if (PySequence_Check(pyobj)) { + std::list<PyObject*> objs = splitPyObject(pyobj); + std::list<PyObject*>::const_iterator it; + for(it=objs.begin(); it != objs.end(); it++) + SbkBaseWrapper_setOwnership(reinterpret_cast<SbkBaseWrapper*>(*it), owner); + } else if (isShibokenType(pyobj)) { + SbkBaseWrapper_setOwnership(reinterpret_cast<SbkBaseWrapper*>(pyobj), owner); + } +} + +namespace Wrapper +{ + +void setValidCpp(SbkBaseWrapper* pyObj, bool value) +{ + pyObj->d->validCppObject = value; +} + +void setHasCppWrapper(SbkBaseWrapper* pyObj, bool value) +{ + pyObj->d->containsCppWrapper = value; +} + +bool hasCppWrapper(SbkBaseWrapper* pyObj) +{ + return pyObj->d->containsCppWrapper; } +} // namespace Wrapper } // namespace Shiboken diff --git a/libshiboken/basewrapper.h b/libshiboken/basewrapper.h index 2440a98c..75fa9040 100644 --- a/libshiboken/basewrapper.h +++ b/libshiboken/basewrapper.h @@ -30,14 +30,26 @@ #include <map> #include <string> -namespace Shiboken +extern "C" { -/** - * This mapping associates a method and argument of an wrapper object with the wrapper of - * said argument when it needs the binding to help manage its reference counting. - */ -typedef std::map<std::string, std::list<PyObject*> > RefCountMap; +struct SbkBaseWrapperPrivate; + +/// Base Python object for all the wrapped C++ classes. +struct LIBSHIBOKEN_API SbkBaseWrapper +{ + PyObject_HEAD + /// Instance dictionary. + PyObject* ob_dict; + /// List of weak references + PyObject* weakreflist; + SbkBaseWrapperPrivate* d; +}; + +} + +namespace Shiboken +{ extern "C" { @@ -90,30 +102,6 @@ struct LIBSHIBOKEN_API SbkBaseWrapperType DeleteUserDataFunc d_func; }; -struct ParentInfo; - -/// Base Python object for all the wrapped C++ classes. -struct LIBSHIBOKEN_API SbkBaseWrapper -{ - PyObject_HEAD - /// Pointer to the C++ class. - void** cptr; - /// Instance dictionary. - PyObject* ob_dict; - /// True when Python is responsible for freeing the used memory. - unsigned int hasOwnership : 1; - /// Is true when the C++ class of the wrapped object has a virtual destructor AND was created by Python. - unsigned int containsCppWrapper : 1; - /// Marked as false when the object is lost to C++ and the binding can not know if it was deleted or not. - unsigned int validCppObject : 1; - /// Information about the object parents and children, can be null. - ParentInfo* parentInfo; - /// List of weak references - PyObject* weakreflist; - /// Manage reference counting of objects that are referred but not owned. - RefCountMap* referredObjects; -}; - } // extern "C" /** @@ -187,14 +175,8 @@ LIBSHIBOKEN_API bool canCallConstructor(PyTypeObject* myType, PyTypeObject* ctor #define SbkBaseWrapper_Check(op) PyObject_TypeCheck(op, (PyTypeObject*)&Shiboken::SbkBaseWrapper_Type) #define SbkBaseWrapper_CheckExact(op) ((op)->ob_type == &Shiboken::SbkBaseWrapper_Type) -#define SbkBaseWrapper_instanceDict(pyobj) (((Shiboken::SbkBaseWrapper*)pyobj)->ob_dict) -#define SbkBaseWrapper_setInstanceDict(pyobj,d) (((Shiboken::SbkBaseWrapper*)pyobj)->ob_dict = d) -#define SbkBaseWrapper_hasOwnership(pyobj) (((Shiboken::SbkBaseWrapper*)pyobj)->hasOwnership) -#define SbkBaseWrapper_hasParentInfo(pyobj) (((Shiboken::SbkBaseWrapper*)pyobj)->parentInfo) -#define SbkBaseWrapper_containsCppWrapper(pyobj) (((Shiboken::SbkBaseWrapper*)pyobj)->containsCppWrapper) -#define SbkBaseWrapper_setContainsCppWrapper(pyobj,o)(((Shiboken::SbkBaseWrapper*)pyobj)->containsCppWrapper = o) -#define SbkBaseWrapper_validCppObject(pyobj) (((Shiboken::SbkBaseWrapper*)pyobj)->validCppObject) -#define SbkBaseWrapper_setValidCppObject(pyobj,v) (((Shiboken::SbkBaseWrapper*)pyobj)->validCppObject = v) +#define SbkBaseWrapper_instanceDict(pyobj) (((SbkBaseWrapper*)pyobj)->ob_dict) +#define SbkBaseWrapper_setInstanceDict(pyobj,d) (((SbkBaseWrapper*)pyobj)->ob_dict = d) LIBSHIBOKEN_API PyObject* SbkBaseWrapper_New(SbkBaseWrapperType* instanceType, @@ -241,6 +223,14 @@ LIBSHIBOKEN_API void setErrorAboutWrongArguments(PyObject* args, const char* fun LIBSHIBOKEN_API void SbkBaseWrapper_setOwnership(PyObject* pyobj, bool owner); LIBSHIBOKEN_API void SbkBaseWrapper_setOwnership(SbkBaseWrapper* pyobj, bool owner); +namespace Wrapper { + +LIBSHIBOKEN_API void setValidCpp(SbkBaseWrapper* pyObj, bool value); +LIBSHIBOKEN_API void setHasCppWrapper(SbkBaseWrapper* pyObj, bool value); +LIBSHIBOKEN_API bool hasCppWrapper(SbkBaseWrapper* pyObj); + +} // namespace Wrapper + } // namespace Shiboken #endif // BASEWRAPPER_H diff --git a/libshiboken/basewrapper_p.h b/libshiboken/basewrapper_p.h index 20476d3a..a07f5482 100644 --- a/libshiboken/basewrapper_p.h +++ b/libshiboken/basewrapper_p.h @@ -25,11 +25,66 @@ #include <Python.h> #include <list> +#include <map> + +struct SbkBaseWrapper; + +namespace Shiboken +{ +/** + * This mapping associates a method and argument of an wrapper object with the wrapper of + * said argument when it needs the binding to help manage its reference counting. + */ +typedef std::map<std::string, std::list<PyObject*> > RefCountMap; + + +/// Linked list of SbkBaseWrapper pointers +typedef std::list<SbkBaseWrapper*> ChildrenList; + +/// Struct used to store information about object parent and children. +struct ParentInfo +{ + /// Default ctor. + ParentInfo() : parent(0), hasWrapperRef(false) {} + /// Pointer to parent object. + SbkBaseWrapper* parent; + /// List of object children. + ChildrenList children; + /// has internal ref + bool hasWrapperRef; +}; + +} // namespace Shiboken + +extern "C" +{ + +/** + * \internal + * Private data for SbkBaseWrapper + */ +struct SbkBaseWrapperPrivate +{ + /// Pointer to the C++ class. + void** cptr; + /// True when Python is responsible for freeing the used memory. + unsigned int hasOwnership : 1; + /// Is true when the C++ class of the wrapped object has a virtual destructor AND was created by Python. + unsigned int containsCppWrapper : 1; + /// Marked as false when the object is lost to C++ and the binding can not know if it was deleted or not. + unsigned int validCppObject : 1; + /// Information about the object parents and children, can be null. + Shiboken::ParentInfo* parentInfo; + /// Manage reference counting of objects that are referred but not owned. + Shiboken::RefCountMap* referredObjects; +}; + +} // extern "C" namespace Shiboken { /** - * Utility function uset to transform PyObject which suppot sequence protocol in a std::list + * Utility function uset to transform PyObject which suppot sequence protocol in a std::list **/ std::list<PyObject*> splitPyObject(PyObject* pyObj); @@ -126,30 +181,12 @@ inline std::list<SbkBaseWrapperType*> getCppBaseClasses(PyTypeObject* baseType) return visitor.bases(); } -struct SbkBaseWrapper; - -/// Linked list of SbkBaseWrapper pointers -typedef std::list<SbkBaseWrapper*> ChildrenList; - -/// Struct used to store information about object parent and children. -struct ParentInfo -{ - /// Default ctor. - ParentInfo() : parent(0), hasWrapperRef(false) {} - /// Pointer to parent object. - SbkBaseWrapper* parent; - /// List of object children. - ChildrenList children; - /// has internal ref - bool hasWrapperRef; -}; - /** * Decrements the reference counters of every object referred by self. * \param self the wrapper instance that keeps references to other objects. */ void clearReferences(SbkBaseWrapper* self); -} +} // namespace Shiboken #endif diff --git a/libshiboken/bindingmanager.cpp b/libshiboken/bindingmanager.cpp index 38dc4eb8..22bfde74 100644 --- a/libshiboken/bindingmanager.cpp +++ b/libshiboken/bindingmanager.cpp @@ -184,7 +184,7 @@ void BindingManager::releaseWrapper(PyObject* wrapper) SbkBaseWrapperType* sbkType = reinterpret_cast<SbkBaseWrapperType*>(wrapper->ob_type); int numBases = sbkType->is_multicpp ? getNumberOfCppBaseClasses(wrapper->ob_type) : 1; - void** cptrs = reinterpret_cast<SbkBaseWrapper*>(wrapper)->cptr; + void** cptrs = reinterpret_cast<SbkBaseWrapper*>(wrapper)->d->cptr; for (int i = 0; i < numBases; ++i) { void* cptr = cptrs[i]; m_d->releaseWrapper(cptr); @@ -258,32 +258,32 @@ void BindingManager::invalidateWrapper(PyObject* pyobj) void BindingManager::invalidateWrapper(SbkBaseWrapper* wrapper) { - if (!wrapper || ((PyObject*)wrapper == Py_None) || !SbkBaseWrapper_validCppObject(wrapper)) + if (!wrapper || ((PyObject*)wrapper == Py_None) || !wrapper->d->validCppObject) return; GilState gil; // lock the gil to assure no one is changing the value of m_d->destroying // skip this if the object is a wrapper class and this is not a destructor call - if (SbkBaseWrapper_containsCppWrapper(wrapper) && !m_d->destroying) { - ParentInfo* pInfo = wrapper->parentInfo; + if (wrapper->d->containsCppWrapper && !m_d->destroying) { + ParentInfo* pInfo = wrapper->d->parentInfo; // this meaning the object has a extra ref and we will remove this now if (pInfo && pInfo->hasWrapperRef) { delete pInfo; - wrapper->parentInfo = 0; + wrapper->d->parentInfo = 0; Py_XDECREF((PyObject*) wrapper); } return; } - SbkBaseWrapper_setValidCppObject(wrapper, false); - SbkBaseWrapper_setOwnership(wrapper, false); + wrapper->d->validCppObject = false; + wrapper->d->hasOwnership = false; // If it is a parent invalidate all children. - if (SbkBaseWrapper_hasParentInfo(wrapper)) { - ChildrenList::iterator it = wrapper->parentInfo->children.begin(); + if (wrapper->d->parentInfo) { + ChildrenList::iterator it = wrapper->d->parentInfo->children.begin(); bool parentDestroying = m_d->destroying; m_d->destroying = false; - for (; it != wrapper->parentInfo->children.end(); ++it) + for (; it != wrapper->d->parentInfo->children.end(); ++it) invalidateWrapper(*it); m_d->destroying = parentDestroying; } @@ -323,10 +323,10 @@ void BindingManager::transferOwnershipToCpp(PyObject* wrapper) void BindingManager::transferOwnershipToCpp(SbkBaseWrapper* wrapper) { - if (wrapper->parentInfo) + if (wrapper->d->parentInfo) Shiboken::removeParent(wrapper); - if (SbkBaseWrapper_containsCppWrapper(wrapper)) + if (wrapper->d->containsCppWrapper) SbkBaseWrapper_setOwnership(wrapper, false); else invalidateWrapper(wrapper); diff --git a/libshiboken/bindingmanager.h b/libshiboken/bindingmanager.h index d7cec27b..b5bf43b6 100644 --- a/libshiboken/bindingmanager.h +++ b/libshiboken/bindingmanager.h @@ -27,10 +27,11 @@ #include <set> #include "shibokenmacros.h" +struct SbkBaseWrapper; + namespace Shiboken { -struct SbkBaseWrapper; struct SbkBaseWrapperType; class LIBSHIBOKEN_API BindingManager @@ -40,7 +41,7 @@ public: bool hasWrapper(const void *cptr); - void registerWrapper( Shiboken::SbkBaseWrapper* pyobj, void* cptr); + void registerWrapper(SbkBaseWrapper* pyobj, void* cptr); void releaseWrapper(PyObject* wrapper); PyObject* retrieveWrapper(const void* cptr); PyObject* getOverride(const void* cptr, const char* methodName); diff --git a/libshiboken/conversions.h b/libshiboken/conversions.h index 67e62792..b077e2f2 100644 --- a/libshiboken/conversions.h +++ b/libshiboken/conversions.h @@ -223,8 +223,8 @@ struct ValueTypeConverter static inline PyObject* toPython(void* cppobj) { return toPython(*reinterpret_cast<T*>(cppobj)); } static inline PyObject* toPython(const T& cppobj) { - PyObject* obj = createWrapper<T>(CppObjectCopier<T>::copy(cppobj), true, true); - SbkBaseWrapper_setContainsCppWrapper(obj, SbkTypeInfo<T>::isCppWrapper); + PyObject* obj = createWrapper<T>(new T(cppobj), true, true); +// SbkBaseWrapper_setContainsCppWrapper(obj, SbkTypeInfo<T>::isCppWrapper); return obj; } // Classes with implicit conversions are expected to reimplement 'toCpp' to build T from |