# wiesel / src / base / wiesel / util / shared_object.h

 Christian Fische… b5d82b9 2012-04-18 Christian Fische… 08c1fdf 2012-04-11 Christian Fische… b5d82b9 2012-04-18 Christian Fische… 08c1fdf 2012-04-11 Christian Fische… 0c5cd71 2012-09-12 Christian Fische… 08c1fdf 2012-04-11 Christian Fische… f6b40d5 2012-04-30 Christian Fische… 08c1fdf 2012-04-11 Christian Fische… 65d000e 2012-07-01 Christian Fische… 08c1fdf 2012-04-11 Christian Fische… 0c5cd71 2012-09-12 Christian Fische… 08c1fdf 2012-04-11 Christian Fische… 22e033c 2012-04-11 Christian Fische… 08c1fdf 2012-04-11   1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 /** * Copyright (C) 2012 * Christian Fischer * * https://bitbucket.org/baldur/wiesel/ * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3 of the License, or (at your option) any later version. * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General * Public License along with this library; if not, write to the * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, * Boston, MA 02110-1301 USA */ #ifndef __WIESEL_UTIL_MANAGED_OBJECT_H__ #define __WIESEL_UTIL_MANAGED_OBJECT_H__ #include #include #include #include namespace wiesel { /** * @brief A base-class for any objects, which want to use reference-counting. * Usage: * Each time, a reference to a \ref SharedObject is referenced in a global object, * this object should call \ref retain() to increment the reference counter. * When the object is no longer required, \ref release() should be used to decrement * the reference counter. When the reference counter hits zero, the object will be deleted. * Objects which are never retained will be deleted next time, * when \ref SharedObject::purgeDeadObjects() is called. * * By design, this class should be used as a virtual base class only. */ class WIESEL_BASE_EXPORT SharedObject { protected: SharedObject(); public: virtual ~SharedObject(); // reference-counting public: /// An alias type for a list of managed objects. typedef std::vector List; /** * @brief increment the reference-counter. */ inline void retain() { ++references; } /** * @brief decrement the reference-counter. * When the reference-counter hits zero, * the object will be deleted immediately. */ inline void release() { // checks, if there are any references for this object. // when this condition fails, the object may be release()'d too often // or there's a retain() missing. assert(references > 0); if (--references <= 0) { delete this; } } /** * @brief get the current value of the reference counter. */ inline int getReferenceCount() const { return references; } // handling living / dead objects public: /** * @brief Provides a read-only list of all currently living objects. */ static inline const List *getLivingObjects() { return &living_objects; } /** * @brief Deletes all objects with a reference-count of 0. * This would be all objects, where the reference-counter never was increased. */ static void purgeDeadObjects(); private: static List living_objects; int references; }; /** * @brief Takes a pointer of a \ref SharedObject to retain it. * When the pointer is \ref NULL, nothing happens. */ inline void safe_retain(SharedObject* obj) { if (obj != NULL) { obj->retain(); } return; } /** * @brief Takes a pointer of a \ref SharedObject to release it. * When the pointer is \ref NULL, nothing happens. * The pointer will be set to \ref NULL after releasing the object. */ template inline void safe_release(OBJ*& obj) { if (obj != NULL) { obj->release(); obj = NULL; } return; } } /* namespace wiesel */ #endif /* __WIESEL_UTIL_MANAGED_OBJECT_H__ */