+}
+
+void User::WriteWallOps(const std::string &text)
+{
+ if (!IS_OPER(this) && IS_LOCAL(this))
+ return;
+
+ std::string wallop("WALLOPS :");
+ wallop.append(text);
+
+ for (std::vector<User*>::const_iterator i = ServerInstance->Users->local_users.begin(); i != ServerInstance->Users->local_users.end(); i++)
+ {
+ User* t = *i;
+ if (t->IsModeSet('w'))
+ this->WriteTo(t,wallop);
+ }
+}
+
+void User::WriteWallOps(const char* text, ...)
+{
+ char textbuffer[MAXBUF];
+ va_list argsPtr;
+
+ va_start(argsPtr, text);
+ vsnprintf(textbuffer, MAXBUF, text, argsPtr);
+ va_end(argsPtr);
+
+ this->WriteWallOps(std::string(textbuffer));
+}
+
+/* return 0 or 1 depending if users u and u2 share one or more common channels
+ * (used by QUIT, NICK etc which arent channel specific notices)
+ *
+ * The old algorithm in 1.0 for this was relatively inefficient, iterating over
+ * the first users channels then the second users channels within the outer loop,
+ * therefore it was a maximum of x*y iterations (upon returning 0 and checking
+ * all possible iterations). However this new function instead checks against the
+ * channel's userlist in the inner loop which is a std::map<User*,User*>
+ * and saves us time as we already know what pointer value we are after.
+ * Don't quote me on the maths as i am not a mathematician or computer scientist,
+ * but i believe this algorithm is now x+(log y) maximum iterations instead.
+ */
+bool User::SharesChannelWith(User *other)
+{
+ if ((!other) || (this->registered != REG_ALL) || (other->registered != REG_ALL))
+ return false;
+
+ /* Outer loop */
+ for (UCListIter i = this->chans.begin(); i != this->chans.end(); i++)
+ {
+ /* Eliminate the inner loop (which used to be ~equal in size to the outer loop)
+ * by replacing it with a map::find which *should* be more efficient
+ */
+ if (i->first->HasUser(other))
+ return true;
+ }
+ return false;
+}
+
+bool User::ChangeName(const char* gecos)
+{
+ if (!strcmp(gecos, this->fullname))
+ return true;
+
+ if (IS_LOCAL(this))
+ {
+ int MOD_RESULT = 0;
+ FOREACH_RESULT(I_OnChangeLocalUserGECOS,OnChangeLocalUserGECOS(this,gecos));
+ if (MOD_RESULT)
+ return false;
+ FOREACH_MOD(I_OnChangeName,OnChangeName(this,gecos));
+ }
+ strlcpy(this->fullname,gecos,MAXGECOS+1);
+
+ return true;
+}
+
+bool User::ChangeDisplayedHost(const char* shost)
+{
+ if (!strcmp(shost, this->dhost))
+ return true;
+
+ if (IS_LOCAL(this))
+ {
+ int MOD_RESULT = 0;
+ FOREACH_RESULT(I_OnChangeLocalUserHost,OnChangeLocalUserHost(this,shost));
+ if (MOD_RESULT)
+ return false;
+ FOREACH_MOD(I_OnChangeHost,OnChangeHost(this,shost));
+ }
+
+ if (this->ServerInstance->Config->CycleHosts)
+ this->WriteCommonExcept("QUIT :Changing hosts");
+
+ /* Fix by Om: User::dhost is 65 long, this was truncating some long hosts */
+ strlcpy(this->dhost,shost,64);
+
+ this->InvalidateCache();
+
+ if (this->ServerInstance->Config->CycleHosts)