]> git.netwichtig.de Git - user/henk/code/inspircd.git/commitdiff
Make classbase and refcountbase uncopyable; expand comments on their indended uses
authordanieldg <danieldg@e03df62e-2008-0410-955e-edbf42e46eb7>
Sat, 17 Oct 2009 18:52:39 +0000 (18:52 +0000)
committerdanieldg <danieldg@e03df62e-2008-0410-955e-edbf42e46eb7>
Sat, 17 Oct 2009 18:52:39 +0000 (18:52 +0000)
git-svn-id: http://svn.inspircd.org/repository/trunk/inspircd@11888 e03df62e-2008-0410-955e-edbf42e46eb7

31 files changed:
include/base.h
include/channels.h
include/dns.h
include/extensible.h
include/hashcomp.h
include/inspsocket.h
include/mode.h
include/modules.h
include/users.h
src/base.cpp
src/cull_list.cpp
src/inspsocket.cpp
src/mode.cpp
src/modules.cpp
src/modules/m_alias.cpp
src/modules/m_banredirect.cpp
src/modules/m_cgiirc.cpp
src/modules/m_dccallow.cpp
src/modules/m_filter.cpp
src/modules/m_httpd_acl.cpp
src/modules/m_httpd_stats.cpp
src/modules/m_spanningtree/main.cpp
src/modules/m_spanningtree/main.h
src/modules/m_spanningtree/treesocket.h
src/modules/m_spanningtree/treesocket1.cpp
src/modules/m_spanningtree/utils.cpp
src/modules/m_spanningtree/utils.h
src/modules/m_sqlv2.h
src/modules/m_timedbans.cpp
src/modules/u_listmode.h
src/users.cpp

index ed03eeac5313c45e15d975005ffc8b8e72e3e9df..624e2174ff137c8b891ba6f66bc959ea0ccc3fca 100644 (file)
 #include <deque>
 #include <string>
 
-/** The base class for all inspircd classes.
- * Wherever possible, all classes you create should inherit from this,
- * giving them the ability to be passed to various core functions
- * as 'anonymous' classes.
-*/
+/** Dummy class to help enforce culls being parent-called up to classbase */
+class CullResult
+{
+       CullResult();
+       friend class classbase;
+};
+
+/** The base class for all inspircd classes with a well-defined lifetime.
+ * Classes that inherit from this may be destroyed through GlobalCulls,
+ * and may rely on cull() being called prior to their deletion.
+ */
 class CoreExport classbase
 {
  public:
@@ -33,23 +39,39 @@ class CoreExport classbase
         *
         * @return true to allow the delete, or false to halt the delete
         */
-       virtual bool cull();
+       virtual CullResult cull();
        virtual ~classbase();
+ private:
+       // uncopyable
+       classbase(const classbase&);
+       void operator=(const classbase&);
 };
 
 /** The base class for inspircd classes that support reference counting.
  * Any objects that do not have a well-defined lifetime should inherit from
- * this
+ * this, and should be assigned to a reference<type> object to establish their
+ * lifetime.
+ *
+ * Reference objects should not hold circular references back to themselves,
+ * even indirectly; this will cause a memory leak because the count will never
+ * drop to zero.
+ *
+ * Using a normal pointer for the object is recommended if you can assure that
+ * at least one reference<> will remain as long as that pointer is used; this
+ * will avoid the slight overhead of changing the reference count.
  */
-class CoreExport refcountbase : public classbase
+class CoreExport refcountbase
 {
        unsigned int refcount;
  public:
        refcountbase();
-       virtual bool cull();
        virtual ~refcountbase();
        inline unsigned int GetReferenceCount() const { return refcount; }
        friend class reference_base;
+ private:
+       // uncopyable
+       refcountbase(const refcountbase&);
+       void operator=(const refcountbase&);
 };
 
 class CoreExport reference_base
@@ -81,7 +103,7 @@ class reference : public reference_base
                if (value)
                {
                        int rc = dec(value);
-                       if (rc == 0 && value->cull())
+                       if (rc == 0)
                                delete value;
                }
        }
index 1ded25a736fc0d8ca2bf799569a879987401ebfe..7728bb55b16935b0b5bd1efd76d68c6320b16704 100644 (file)
@@ -36,7 +36,7 @@ struct ModResult;
 /** Holds an entry for a ban list, exemption list, or invite list.
  * This class contains a single element in a channel list, such as a banlist.
  */
-class HostItem : public classbase
+class HostItem
 {
  public:
        /** Time the item was added
index 76a69b6e453043b51b25331ae0acdd392e6b6f7e..1b9ce59a4f7e4db5604afd0a2acaa6261c46ef59 100644 (file)
@@ -40,7 +40,7 @@ class Module;
 /**
  * Result status, used internally
  */
-class CoreExport DNSResult : public classbase
+class CoreExport DNSResult
 {
  public:
        /** Result ID
@@ -72,7 +72,7 @@ typedef std::pair<unsigned char*, std::string> DNSInfo;
 
 /** Cached item stored in the query cache.
  */
-class CoreExport CachedQuery : public classbase
+class CoreExport CachedQuery
 {
  public:
        /** The cached result data, an IP or hostname
@@ -181,7 +181,7 @@ enum ForceProtocol
  * can occur by calling virtual methods, one is a success situation, and the other
  * an error situation.
  */
-class CoreExport Resolver : public Extensible
+class CoreExport Resolver
 {
  protected:
        /**
index ff7bce477b767ea1aa2af98ed97b172c524d6f2c..ca9c44546d2a88323a621965e6c72ddc73247d8e 100644 (file)
@@ -72,6 +72,7 @@ class CoreExport Extensible : public classbase
         */
        inline const ExtensibleStore& GetExtList() const { return extensions; }
 
+       virtual CullResult cull();
        virtual ~Extensible();
        void doUnhookExtensions(const std::vector<ExtensionItem*>& toRemove);
 };
index 6cbc14850d00b6474f4ec2752b6917f925b8fc67..5392c6ae5d94e26126ea05846520a971b6ebd999 100644 (file)
@@ -204,7 +204,7 @@ namespace irc
         * std::string, or a const char* const* array, using overloaded
         * constructors.
         */
-       class CoreExport stringjoiner : public classbase
+       class CoreExport stringjoiner
        {
         private:
 
@@ -248,7 +248,7 @@ namespace irc
         * It can then reproduce this list, clamped to a maximum of MAXMODES
         * values per line.
         */
-       class CoreExport modestacker : public classbase
+       class CoreExport modestacker
        {
         private:
                /** The mode sequence and its parameters
@@ -335,7 +335,7 @@ namespace irc
         * list will be ":item". This is to allow for parsing 'source' fields
         * from data.
         */
-       class CoreExport tokenstream : public classbase
+       class CoreExport tokenstream
        {
         private:
 
@@ -394,7 +394,7 @@ namespace irc
         * the next token, until none remain, at which point the method returns
         * an empty string.
         */
-       class CoreExport sepstream : public classbase
+       class CoreExport sepstream
        {
         private:
                /** Original string.
@@ -467,7 +467,7 @@ namespace irc
         * start or end < 0) then GetToken() will return the first element
         * of the pair of numbers.
         */
-       class CoreExport portparser : public classbase
+       class CoreExport portparser
        {
         private:
 
index 84716eae67ee0691b7597f0a3eb1775472b58ca3..3e5c752356458122b11b2ca6e70958cfa8931857 100644 (file)
@@ -146,7 +146,7 @@ class CoreExport StreamSocket : public EventHandler
         */
        virtual void Close();
        /** This ensures that close is called prior to destructor */
-       virtual bool cull();
+       virtual CullResult cull();
 };
 /**
  * BufferedSocket is an extendable socket class which modules
index 81858a823897496ddf1c2cb968003f50a9da6e70..b63e5e6a91116f3cc860a3db789745255f7621fe 100644 (file)
@@ -172,7 +172,7 @@ class CoreExport ModeHandler : public classbase
         * @param type Type of the mode (MODETYPE_USER or MODETYPE_CHANNEL)
         */
        ModeHandler(Module* me, const std::string& name, char modeletter, ParamSpec params, ModeType type);
-       virtual bool cull();
+       virtual CullResult cull();
        virtual ~ModeHandler();
        /**
         * Returns true if the mode is a list mode
index ef6f5c25177d038b9560cbd3dd6494b6a479b837..96506f5982f48562917e07ffa1e2dbd42e74bbc7 100644 (file)
@@ -230,7 +230,7 @@ do { \
  * error when attempting to load a module compiled against a different API_VERSION.
  */
 template<int api>
-class CoreExport VersionBase : public classbase
+class CoreExport VersionBase
 {
  public:
        /** Module description
@@ -349,7 +349,7 @@ class ConfigReader;
  *  its methods will be called when irc server events occur. class inherited from module must be
  *  instantiated by the ModuleFactory class (see relevent section) for the module to be initialised.
  */
-class CoreExport Module : public Extensible
+class CoreExport Module : public classbase
 {
  public:
        /** File that this module was loaded from
@@ -369,7 +369,7 @@ class CoreExport Module : public Extensible
        /** Clean up prior to destruction
         * If you override, you must call this AFTER your module's cleanup
         */
-       virtual bool cull();
+       virtual CullResult cull();
 
        /** Default destructor.
         * destroys a module class
index ed672450ee00839611cf6f7e0d005fc2a54b53bd..0ce9f59ab681639b7f0ec801f31b321bb9d2fcbd 100644 (file)
@@ -848,7 +848,7 @@ class CoreExport User : public StreamSocket
        /** Default destructor
         */
        virtual ~User();
-       virtual bool cull();
+       virtual CullResult cull();
 };
 
 /** Derived from Resolver, and performs user forward/reverse lookups.
index 1b01da70710ab1948ea5c25dd834474c1e39eab4..2e2dbfb287d365c78e3022e8c5c5089dca02884d 100644 (file)
@@ -22,22 +22,21 @@ classbase::classbase()
 {
 }
 
-bool classbase::cull()
+CullResult classbase::cull()
 {
-       return true;
+       return CullResult();
 }
 
 classbase::~classbase()
 {
 }
 
-refcountbase::refcountbase() : refcount(0)
+CullResult::CullResult()
 {
 }
 
-bool refcountbase::cull()
+refcountbase::refcountbase() : refcount(0)
 {
-       return (refcount == 0);
 }
 
 refcountbase::~refcountbase()
@@ -129,12 +128,17 @@ void Extensible::doUnhookExtensions(const std::vector<ExtensionItem*>& toRemove)
        }
 }
 
-Extensible::~Extensible()
+CullResult Extensible::cull()
 {
        for(ExtensibleStore::iterator i = extensions.begin(); i != extensions.end(); ++i)
        {
                i->first->free(i->second);      
        }
+       return classbase::cull();
+}
+
+Extensible::~Extensible()
+{
 }
 
 LocalExtItem::LocalExtItem(const std::string& Key, Module* mod) : ExtensionItem(Key, mod)
index 6033ec695a126de15698520cfbbc838f0438833e..1ce6dfae104fff5a9988298b8c18a73d1287e789 100644 (file)
@@ -26,8 +26,8 @@ void CullList::Apply()
                {
                        ServerInstance->Logs->Log("CULLLIST", DEBUG, "Deleting %s @%p", typeid(*c).name(),
                                (void*)c);
-                       if (c->cull())
-                               queue.push_back(c);
+                       c->cull();
+                       queue.push_back(c);
                }
                else
                {
index 37335c855d1d1f9be4edd8552ec0a195683eab45..fc8bc142f9df2dfeb7ef54f4294e9fdb9dc7b8a9 100644 (file)
@@ -145,10 +145,10 @@ void StreamSocket::Close()
        errno = save;
 }
 
-bool StreamSocket::cull()
+CullResult StreamSocket::cull()
 {
        Close();
-       return true;
+       return EventHandler::cull();
 }
 
 bool StreamSocket::GetNextLine(std::string& line, char delim)
index 144ddee727e713a1c9e93e16d48ac462165552de..47553f238294278fa8ebc4f166044943a9e87d7c 100644 (file)
@@ -53,10 +53,10 @@ ModeHandler::ModeHandler(Module* Creator, const std::string& Name, char modelett
 {
 }
 
-bool ModeHandler::cull()
+CullResult ModeHandler::cull()
 {
        ServerInstance->Modes->DelMode(this);
-       return true;
+       return classbase::cull();
 }
 
 ModeHandler::~ModeHandler()
@@ -1027,6 +1027,9 @@ ModeParser::ModeParser()
 ModeParser::~ModeParser()
 {
        ModeHandler* mh = ServerInstance->Modes->FindMode('h', MODETYPE_CHANNEL);
-       if (mh && mh->cull())
+       if (mh)
+       {
+               mh->cull();
                delete mh;
+       }
 }
index 913293e1357e87e8a5f863242d7daf7c68682378..2dafc88643565cf3729469dc59c4b6db4b61e567 100644 (file)
@@ -52,9 +52,9 @@ void Event::Send()
 // These declarations define the behavours of the base class Module (which does nothing at all)
 
 Module::Module() { }
-bool Module::cull()
+CullResult Module::cull()
 {
-       return true;
+       return classbase::cull();
 }
 Module::~Module() { }
 
index 6aa1f6c3611c0d99b409e0eee851865d5656dffd..62c02396a1dfd362cb8018400232b95aeae61c22 100644 (file)
@@ -17,7 +17,7 @@
 
 /** An alias definition
  */
-class Alias : public classbase
+class Alias
 {
  public:
        /** The text of the alias command */
index fdc5b122047858b72f499fc16f2f89ddab3066cf..cf6c278282509b2be1c6409330cce3c312cae26b 100644 (file)
@@ -20,7 +20,7 @@
 /* Originally written by Om, January 2009
  */
 
-class BanRedirectEntry : public classbase
+class BanRedirectEntry
 {
  public:
        std::string targetchan;
index 04e35adcb1d6c08156109b8b2df8674d6f88240e..53c761b3eaace24faa0f8cc7600c5163dd87c336 100644 (file)
@@ -26,7 +26,7 @@ enum CGItype { INVALID, PASS, IDENT, PASSFIRST, IDENTFIRST, WEBIRC };
 
 /** Holds a CGI site's details
  */
-class CGIhost : public classbase
+class CGIhost
 {
 public:
        std::string hostmask;
index c202a97b43f9c9878d74f65e45adf3e59fec0b06..d4be35cebb62d9f30685e98bdf2c6cd12ad7beb6 100644 (file)
 
 static ConfigReader *Conf;
 
-class BannedFileList : public classbase
+class BannedFileList
 {
  public:
        std::string filemask;
        std::string action;
 };
 
-class DCCAllow : public classbase
+class DCCAllow
 {
  public:
        std::string nickname;
index a9187098b760114e1b2e60a2ce010107770b3fdb..0220a3a44eedeb1e4b7d3260f5c4b67a40623db4 100644 (file)
@@ -28,7 +28,7 @@ enum FilterFlags
        FLAG_NOTICE = 16
 };
 
-class FilterResult : public classbase
+class FilterResult
 {
  public:
        std::string freeform;
index dd6f5a8bbffb7a578ead302e59ba98df2fc1404c..85ec4b6cd3289f8bd753636c09f4f873f3c5e379 100644 (file)
@@ -16,9 +16,8 @@
 #include "protocol.h"
 
 /* $ModDesc: Provides access control lists (passwording of resources, ip restrictions etc) to m_httpd.so dependent modules */
-/* $ModDep: httpd.h */
 
-class HTTPACL : public Extensible
+class HTTPACL
 {
  public:
        std::string path;
index a075bc59c978265178f425ed1510ea565dbd31d7..a451f6af99d039051888fbab74c61c94f1258526 100644 (file)
@@ -69,7 +69,7 @@ class ModuleHttpStats : public Module
        void DumpMeta(std::stringstream& data, Extensible* ext)
        {
                data << "<metadata>";
-               for(ExtensibleStore::const_iterator i = ext->GetExtList().begin(); i != ext->GetExtList().end(); i++)
+               for(Extensible::ExtensibleStore::const_iterator i = ext->GetExtList().begin(); i != ext->GetExtList().end(); i++)
                {
                        ExtensionItem* item = i->first;
                        std::string value = item->serialize(FORMAT_USER, ext, i->second);
index afd40e0c9dda48fee653bc0c0ae055239ff0d8fe..e46c2d320188b8bb7e2262b49c9b77ed247ab20c 100644 (file)
@@ -944,7 +944,7 @@ void ModuleSpanningTree::ProtoSendMetaData(void* opaque, Extensible* target, con
                s->WriteLine(std::string(":")+ServerInstance->Config->GetSID()+" METADATA * "+extname+" :"+extdata);
 }
 
-bool ModuleSpanningTree::cull()
+CullResult ModuleSpanningTree::cull()
 {
        Utils->cull();
        ServerInstance->Timers->DelTimer(RefreshTimer);
index be9c460d9166fc9ba7c48c7eac6ef12ee636546c..69244259882ad1b2f91c6929802b80f899ac6066 100644 (file)
@@ -190,7 +190,7 @@ class ModuleSpanningTree : public Module
        void ProtoSendMetaData(void* opaque, Extensible* target, const std::string &extname, const std::string &extdata);
        void OnLoadModule(Module* mod);
        void OnUnloadModule(Module* mod);
-       bool cull();
+       CullResult cull();
        ~ModuleSpanningTree();
        Version GetVersion();
        void Prioritize();
index a0f0e5d88e05622c921fb8ae901869f972f82544..b5f97c30f55b49ea84737a7ec75ae466392ed2bc 100644 (file)
@@ -133,7 +133,7 @@ class TreeSocket : public BufferedSocket
         */
        void CleanNegotiationInfo();
 
-       bool cull();
+       CullResult cull();
        /** Destructor
         */
        ~TreeSocket();
index d99d8d6c9d55021faae8bd54e112623a63194a50..f6f237529cf45bbb3baaeb44a2daa812c7b20579 100644 (file)
@@ -103,7 +103,7 @@ void TreeSocket::CleanNegotiationInfo()
        OutboundPass.clear();
 }
 
-bool TreeSocket::cull()
+CullResult TreeSocket::cull()
 {
        Utils->timeoutlist.erase(this);
        if (myautoconnect)
index 09333fdd24043a8fe7f26a738ec405a3df562fd6..024605a7918d0d009348ea051d90f966537c7679 100644 (file)
@@ -151,7 +151,7 @@ SpanningTreeUtilities::SpanningTreeUtilities(ModuleSpanningTree* C) : Creator(C)
        this->ReadConfiguration(true);
 }
 
-bool SpanningTreeUtilities::cull()
+CullResult SpanningTreeUtilities::cull()
 {
        for (unsigned int i = 0; i < ServerInstance->ports.size(); i++)
        {
@@ -171,9 +171,9 @@ bool SpanningTreeUtilities::cull()
        }
 
        ServerUser->uuid = TreeRoot->GetID();
-       if (ServerUser->cull())
-               delete ServerUser;
-       return true;
+       ServerUser->cull();
+       delete ServerUser;
+       return classbase::cull();
 }
 
 SpanningTreeUtilities::~SpanningTreeUtilities()
index 48677e57d0a94211e77409136c634924051098e1..2fc7304af7e4df3102bd8f52361063a905f78c6a 100644 (file)
@@ -133,7 +133,7 @@ class SpanningTreeUtilities : public classbase
 
        /** Prepare for class destruction
         */
-       bool cull();
+       CullResult cull();
 
        /** Destroy class and free listeners etc
         */
index bcdcb6546fe6e2b3a7e018c32379e84aef158855..05079a8e602f63be218bae9a8614226c65bfb9b3 100644 (file)
@@ -61,7 +61,7 @@ public:
  * The error string varies from database software to database software
  * and should be used to display informational error messages to users.
  */
-class SQLerror : public classbase
+class SQLerror
 {
        /** The error id
         */
@@ -149,7 +149,7 @@ public:
  *
  * SQLrequest foo = SQLrequest(this, target, "databaseid", (SQLquery("SELECT.. ?"), parameter, parameter));
  */
-class SQLquery : public classbase
+class SQLquery
 {
 public:
        /** The query 'format string'
@@ -242,6 +242,11 @@ public:
        {
        }
 
+       // Copy constructor - XXX probably shouldn't be needed
+       SQLrequest(const SQLrequest& o)
+               : Request(o.source, o.dest, SQLREQID), query(o.query), dbid(o.dbid), pri(o.pri), cancel(o.cancel),
+               id(o.id), error(o.error) {}
+
        /** Set the priority of a request.
         */
        void Priority(bool p = true)
@@ -489,7 +494,7 @@ bool operator!= (const SQLhost& l, const SQLhost& r)
  * until pop() is called.
  */
 
-class QueryQueue : public classbase
+class QueryQueue
 {
 private:
        typedef std::deque<SQLrequest*> ReqDeque;
index 02e687b2d439b9c9081a6ac30c0f336ab16f8a43..94301bb7b6735572826e8b29b0db28871251af6d 100644 (file)
@@ -17,7 +17,7 @@
 
 /** Holds a timed ban
  */
-class TimedBan : public classbase
+class TimedBan
 {
  public:
        std::string channel;
index 1516b724cc9606205db51c7ef5bd5ece1f097f01..0ca44547fbbabf4dc8a55ff3a23cb9a91f9d6505 100644 (file)
@@ -25,7 +25,7 @@ inline std::string stringtime()
 
 /** An item in a listmode's list
  */
-class ListItem : public classbase
+class ListItem
 {
 public:
        std::string nick;
@@ -35,7 +35,7 @@ public:
 
 /** The number of items a listmode's list may contain
  */
-class ListLimit : public classbase
+class ListLimit
 {
 public:
        std::string mask;
index 657225069823aadb95832ff26b1fd4c857722dd6..542a6e565c57751c0c315a91e2ac1df340f4a8eb 100644 (file)
@@ -583,14 +583,14 @@ void User::OnError(BufferedSocketError)
        ServerInstance->Users->QuitUser(this, getError());
 }
 
-bool User::cull()
+CullResult User::cull()
 {
        if (!quitting)
                ServerInstance->Users->QuitUser(this, "Culled without QuitUser");
        if (uuid.empty())
        {
                ServerInstance->Logs->Log("USERS", DEBUG, "User culled twice? UUID empty");
-               return true;
+               return Extensible::cull();
        }
        PurgeEmptyChannels();
        if (IS_LOCAL(this))
@@ -625,7 +625,7 @@ bool User::cull()
 
        ServerInstance->Users->uuidlist->erase(uuid);
        uuid.clear();
-       return true;
+       return Extensible::cull();
 }
 
 void User::Oper(const std::string &opertype, const std::string &opername)