diff options
author | danieldg <danieldg@e03df62e-2008-0410-955e-edbf42e46eb7> | 2009-06-01 00:25:32 +0000 |
---|---|---|
committer | danieldg <danieldg@e03df62e-2008-0410-955e-edbf42e46eb7> | 2009-06-01 00:25:32 +0000 |
commit | eba6c0fb9126d51b42deda79c6c4a43e15f8923f (patch) | |
tree | 08bf589e949256679508b73700c7d998a3369e65 | |
parent | bc56f3dc975f4e3a3261cb16d8d7eec78553aade (diff) |
Fix unsafe iteration pattern in m_timedbans - vector::erase invalidates all iterators following the elements to be erased.
git-svn-id: http://svn.inspircd.org/repository/trunk/inspircd@11392 e03df62e-2008-0410-955e-edbf42e46eb7
-rw-r--r-- | src/modules/m_timedbans.cpp | 35 |
1 files changed, 13 insertions, 22 deletions
diff --git a/src/modules/m_timedbans.cpp b/src/modules/m_timedbans.cpp index 39c05add9..e18bca6a5 100644 --- a/src/modules/m_timedbans.cpp +++ b/src/modules/m_timedbans.cpp @@ -149,46 +149,37 @@ class ModuleTimedBans : public Module virtual void OnBackgroundTimer(time_t curtime) { - timedbans::iterator safei; for (timedbans::iterator i = TimedBanList.begin(); i != TimedBanList.end();) { - /* Safe copy of iterator, so we can erase as we iterate */ - safei = i; - ++i; - - if (curtime > safei->expire) + if (curtime > i->expire) { - Channel* cr = ServerInstance->FindChan(safei->channel); + std::string chan = i->mask; + std::string mask = i->mask; + Channel* cr = ServerInstance->FindChan(chan); + i = TimedBanList.erase(i); if (cr) { - std::string mask = safei->mask; std::vector<std::string> setban; setban.push_back(safei->channel); setban.push_back("-b"); setban.push_back(mask); CUList empty; - cr->WriteAllExcept(ServerInstance->FakeClient, true, '@', empty, "NOTICE %s :*** Timed ban on %s expired.", cr->name.c_str(), safei->mask.c_str()); - ServerInstance->PI->SendChannelNotice(cr, '@', "*** Timed ban on " + safei->mask + " expired."); + std::string expiry = "*** Timed ban on " + safei->mask + " expired."; + cr->WriteChannelWithServ(ServerInstance->FakeClient, true, '@', empty, "NOTICE %s :%s", cr->name.c_str(), expiry.c_str()); + ServerInstance->PI->SendChannelNotice(cr, '@', expiry); if (ServerInstance->Config->AllowHalfop) { - cr->WriteAllExcept(ServerInstance->FakeClient, true, '%', empty, "NOTICE %s :*** Timed ban on %s expired.", cr->name.c_str(), safei->mask.c_str()); - ServerInstance->PI->SendChannelNotice(cr, '%', "*** Timed ban on " + safei->mask + " expired."); + cr->WriteAllExcept(ServerInstance->FakeClient, true, '%', empty, "NOTICE %s :%s", cr->name.c_str(), expiry.c_str()); + ServerInstance->PI->SendChannelNotice(cr, '%', expiry); } - /* Removes the ban item for us, no ::erase() needed */ - ServerInstance->PI->SendModeStr(safei->channel, std::string("-b ") + setban[2]); ServerInstance->SendMode(setban, ServerInstance->FakeClient); - - if (ServerInstance->Modes->GetLastParse().empty()) - TimedBanList.erase(safei); - } - else - { - /* Where the hell did our channel go?! */ - TimedBanList.erase(safei); + ServerInstance->PI->SendMode(chan, ServerInstance->Modes->GetLastParseParams(), ServerInstance->Modes->GetLastParseTranslate()); } } + else + ++i; } } |