]> git.netwichtig.de Git - user/henk/code/inspircd.git/blobdiff - src/commands.cpp
Added mode 'compression', stops abuse with modes like: +s-s+s-s+s-s
[user/henk/code/inspircd.git] / src / commands.cpp
index f7361640c5f425ef25112cf8a364bf29ffca386d..05e0a951c2feb0726e071e8b1476cbaeafa6418e 100644 (file)
@@ -1292,6 +1292,7 @@ void handle_modules(char **parameters, int pcnt, userrec *user)
                        WriteServ(user->fd,"900 %s :%s",user->nick,CleanFilename(modulename));
                }
        }
+       WriteServ(user->fd,"901 %s :End of MODULES list",user->nick);
 }
 
 void handle_stats(char **parameters, int pcnt, userrec *user)
@@ -1538,7 +1539,54 @@ void handle_squit(char **parameters, int pcnt, userrec *user)
        }
        else
        {
-               WriteServ(user->fd,"NOTICE :*** Remote SQUIT not supported yet.");
+               if (!strcasecmp("*",parameters[0]))
+               {
+                       WriteServ(user->fd,"NOTICE %s :*** You cannot issue an SQUIT this wide! If this is REALLY what you want, use a less wide mask.",user->nick);
+                       WriteOpers("*** WARNING! %s tried to SQUIT all servers at once!",user->nick);
+                       return;
+               }
+               if (!strcasecmp(ServerName,parameters[0]))
+               {
+                       WriteServ(user->fd,"NOTICE %s :*** To take the local server out of the mesh, just use /SQUIT with no parameters instead.",user->nick);
+                       return;
+               }
+               bool have_this_server = true;
+               int n_count = 0;
+               std::string server_to_squit = "";
+               while (have_this_server)
+               {
+                       have_this_server = false;
+                       for (int j = 0; j < 32; j++)
+                       {
+                               if (me[j] != NULL)
+                               {
+                                       for (int x = 0; x < me[j]->connectors.size(); x++)
+                                       {
+                                               if (match(me[j]->connectors[x].GetServerName().c_str(),parameters[0]))
+                                               {
+                                                       // found a valid ircd_connector.
+                                                       have_this_server = true;
+                                                       server_to_squit = me[j]->connectors[x].GetServerName().c_str();
+                                                       break;
+                                               }
+                                       }
+                                       }
+                               }
+                       if (have_this_server)
+                       {
+                               WriteOpers("SQUIT command issued by %s to remove %s from the mesh",user->nick,server_to_squit.c_str());
+                               WriteServ(user->fd,"NOTICE %s :*** Removing remote server %s.",user->nick,server_to_squit.c_str());
+                               char buffer[MAXBUF];
+                               snprintf(buffer,MAXBUF,"& %s",server_to_squit.c_str());
+                               NetSendToAll(buffer);
+                               DoSplit(server_to_squit.c_str());
+                               n_count++;
+                       }
+               }
+               if (!n_count)
+               {
+                       WriteServ(user->fd,"402 %s %s :Your pattern did not match any servers.",user->nick,parameters[0]);
+               }
        }
 }
 
@@ -1756,7 +1804,7 @@ void handle_nick(char **parameters, int pcnt, userrec *user)
 
                WriteCommon(user,"NICK %s",parameters[0]);
                
-               // Q token must go to ALL servers!!!
+               // N token must go to ALL servers!!!
                char buffer[MAXBUF];
                snprintf(buffer,MAXBUF,"n %s %s",user->nick,parameters[0]);
                NetSendToAll(buffer);
@@ -1797,6 +1845,25 @@ void handle_nick(char **parameters, int pcnt, userrec *user)
 }
 
 
+void handle_v(char token,char* params,serverrec* source,serverrec* reply, char* tcp_host)
+{
+       char* servername = strtok(params," ");
+       char* versionstr = strtok(NULL,"\r\n");
+
+        for (int j = 0; j < 32; j++)
+        {
+                if (me[j] != NULL)
+                {
+                        for (int x = 0; x < me[j]->connectors.size(); x++)
+                        {
+                                if (!strcasecmp(me[j]->connectors[x].GetServerName().c_str(),servername))
+                                {
+                                       me[j]->connectors[x].SetVersionString(versionstr);
+                               }
+                       }
+               }
+       }
+}
 
 void handle_V(char token,char* params,serverrec* source,serverrec* reply, char* tcp_host)
 {
@@ -1808,18 +1875,25 @@ void handle_V(char token,char* params,serverrec* source,serverrec* reply, char*
        userrec* user = Find(src);
        if (user)
        {
-               userrec* dst = Find(dest);
-               
-               if (dst)
+               // notice all - only issuable by a server
+               if (!strcmp(dest,"*"))
                {
-                       WriteTo(user, dst, "NOTICE %s :%s", dst->nick, text);
+                       NoticeAll(user,true,"%s",text);
                }
                else
                {
-                       chanrec* d = FindChan(dest);
-                       if (d)
+                       userrec* dst = Find(dest);      
+                       if (dst)
                        {
-                               ChanExceptSender(d, user, "NOTICE %s :%s", d->name, text);
+                               WriteTo(user, dst, "NOTICE %s :%s", dst->nick, text);
+                       }
+                       else
+                       {
+                               chanrec* d = FindChan(dest);
+                               if (d)
+                               {
+                                       ChanExceptSender(d, user, "NOTICE %s :%s", d->name, text);
+                               }
                        }
                }
        }
@@ -2021,7 +2095,7 @@ void handle_K(char token,char* params,serverrec* source,serverrec* reply, char*
        {
                WriteTo(user, u, "KILL %s :%s!%s!%s!%s (%s)", u->nick, source->name, ServerName, user->dhost,user->nick,reason);
                WriteOpers("*** Remote kill from %s by %s: %s!%s@%s (%s)",source->name,user->nick,u->nick,u->ident,u->host,reason);
-               snprintf(kreason,MAXBUF,"[%s] Killed (%s (%s))",source->name,user->nick,reason);
+               snprintf(kreason,MAXBUF,"[%s] Killed (From: '%s' (%s))",source->name,user->nick,reason);
                kill_link(u,kreason);
        }
 }
@@ -2066,10 +2140,9 @@ void handle_n(char token,char* params,serverrec* source,serverrec* reply, char*
        char* newnick = strtok(NULL," ");
        
        userrec* user = Find(oldnick);
-       
+
        if (user)
        {
-               WriteCommon(user,"NICK %s",newnick);
                if (is_uline(tcp_host))
                {
                        int MOD_RESULT = 0;
@@ -2088,8 +2161,9 @@ void handle_n(char token,char* params,serverrec* source,serverrec* reply, char*
                        // broadcast this because its a services thingy
                        char buffer[MAXBUF];
                        snprintf(buffer,MAXBUF,"n %s %s",user->nick,newnick);
-                       NetSendToAll(buffer);
+                       NetSendToAllExcept(tcp_host,buffer);
                }
+               WriteCommon(user,"NICK %s",newnick);
                user = ReHashNick(user->nick, newnick);
                if (!user) return;
                if (!user->nick) return;
@@ -2689,6 +2763,10 @@ void process_restricted_commands(char token,char* params,serverrec* source,serve
                case 'V':
                        handle_V(token,params,source,reply,tcp_host);
                break;
+               // v <servername> <arbitary version string>
+               case 'v':
+                       handle_v(token,params,source,reply,tcp_host);
+               break;
                // L <SOURCE> <CHANNEL> :<REASON>
                // User parting a channel
                case 'L':