aboutsummaryrefslogtreecommitdiffstats
path: root/src/modules/m_spanningtree/nickcollide.cpp
diff options
context:
space:
mode:
authorGravatar danieldg2009-03-06 20:39:02 +0000
committerGravatar danieldg2009-03-06 20:39:02 +0000
commiteacd707421be4f2612df9bde4517649061bb062e (patch)
treebfde92659d07a50783279a24cdbfcc3b274eea4a /src/modules/m_spanningtree/nickcollide.cpp
parentDrop channel keys if they are identical to the already-set key (fix for bug #... (diff)
downloadinspircd++-eacd707421be4f2612df9bde4517649061bb062e.tar.gz
inspircd++-eacd707421be4f2612df9bde4517649061bb062e.tar.bz2
inspircd++-eacd707421be4f2612df9bde4517649061bb062e.zip
Send SVSNICKs during nick collision to prevent servers that do not fully implement collisions from killing users
git-svn-id: http://svn.inspircd.org/repository/trunk/inspircd@11179 e03df62e-2008-0410-955e-edbf42e46eb7
Diffstat (limited to 'src/modules/m_spanningtree/nickcollide.cpp')
-rw-r--r--src/modules/m_spanningtree/nickcollide.cpp49
1 files changed, 30 insertions, 19 deletions
diff --git a/src/modules/m_spanningtree/nickcollide.cpp b/src/modules/m_spanningtree/nickcollide.cpp
index 6c4a837a5..9656f9af3 100644
--- a/src/modules/m_spanningtree/nickcollide.cpp
+++ b/src/modules/m_spanningtree/nickcollide.cpp
@@ -30,8 +30,8 @@
int TreeSocket::DoCollision(User *u, time_t remotets, const std::string &remoteident, const std::string &remoteip, const std::string &remoteuid)
{
/*
- * Under old protocol rules, we would have had to kill both clients.
- * Really, this sucks.
+ * Under old protocol rules, we would have had to kill both clients.
+ * Really, this sucks.
* These days, we have UID. And, so what we do is, force nick change client(s)
* involved according to timestamp rules.
*
@@ -84,9 +84,30 @@ int TreeSocket::DoCollision(User *u, time_t remotets, const std::string &remotei
}
}
+ /*
+ * Cheat a little here. Instead of a dedicated command to change UID,
+ * use SVSNICK and accept the losing client with its UID (as we know the SVSNICK will
+ * not fail under any circumstances -- UIDs are netwide exclusive).
+ *
+ * This means that each side of a collide will generate one extra NICK back to where
+ * they have just linked (and where it got the SVSNICK from), however, it will
+ * be dropped harmlessly as it will come in as :928AAAB NICK 928AAAB, and we already
+ * have 928AAAB's nick set to that.
+ * -- w00t
+ */
if (bChangeLocal)
{
+ /*
+ * Local-side nick needs to change. Just in case we are hub, and
+ * this "local" nick is actually behind us, send an SVSNICK out.
+ */
+ std::deque<std::string> params;
+ params.push_back(u->uuid);
+ params.push_back(u->uuid);
+ params.push_back(ConvToStr(u->age));
+ Utils->DoOneToMany(ServerInstance->Config->GetSID(),"SVSNICK",params);
+
u->ForceNickChange(u->uuid.c_str());
if (!bChangeRemote)
@@ -94,28 +115,18 @@ int TreeSocket::DoCollision(User *u, time_t remotets, const std::string &remotei
}
if (bChangeRemote)
{
+ User *remote = this->ServerInstance->FindUUID(remoteuid);
/*
- * Cheat a little here. Instead of a dedicated command to change UID,
- * use SVSNICK and accept their client with it's UID (as we know the SVSNICK will
- * not fail under any circumstances -- UIDs are netwide exclusive).
- *
- * This means that each side of a collide will generate one extra NICK back to where
- * they have just linked (and where it got the SVSNICK from), however, it will
- * be dropped harmlessly as it will come in as :928AAAB NICK 928AAAB, and we already
- * have 928AAAB's nick set to that.
- * -- w00t
+ * remote side needs to change. If this happens, we will modify
+ * the UID or halt the propagation of the nick change command,
+ * so other servers don't need to see the SVSNICK
*/
- User *remote = this->ServerInstance->FindUUID(remoteuid);
+ WriteLine(std::string(":")+ServerInstance->Config->GetSID()+" SVSNICK "+remoteuid+" " + remoteuid + " " + ConvToStr(remotets));
if (remote)
{
- /* buh.. nick change collide. force change their nick. */
- remote->ForceNickChange(remote->uuid.c_str());
- }
- else
- {
- /* user has not been introduced yet, just inform their server */
- this->WriteLine(std::string(":")+this->ServerInstance->Config->GetSID()+" SVSNICK "+remoteuid+" " + remoteuid + " " + ConvToStr(remotets));
+ /* nick change collide. Force change their nick. */
+ remote->ForceNickChange(remoteuid.c_str());
}
if (!bChangeLocal)