]> git.netwichtig.de Git - user/henk/code/inspircd.git/blob - src/modules/m_jumpserver.cpp
Merge pull request #96 from Justasic/insp20
[user/henk/code/inspircd.git] / src / modules / m_jumpserver.cpp
1 /*
2  * InspIRCd -- Internet Relay Chat Daemon
3  *
4  *   Copyright (C) 2007-2008 Craig Edwards <craigedwards@brainbox.cc>
5  *   Copyright (C) 2007 Dennis Friis <peavey@inspircd.org>
6  *   Copyright (C) 2007 Robin Burchell <robin+git@viroteck.net>
7  *
8  * This file is part of InspIRCd.  InspIRCd is free software: you can
9  * redistribute it and/or modify it under the terms of the GNU General Public
10  * License as published by the Free Software Foundation, version 2.
11  *
12  * This program is distributed in the hope that it will be useful, but WITHOUT
13  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
14  * FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more
15  * details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
19  */
20
21
22 #include "inspircd.h"
23
24 /* $ModDesc: Provides support for the RPL_REDIR numeric */
25
26 /** Handle /JUMPSERVER
27  */
28 class CommandJumpserver : public Command
29 {
30  public:
31         bool redirect_all_immediately;
32         bool redirect_new_users;
33         bool direction;
34         std::string redirect_to;
35         std::string reason;
36         int port;
37
38         CommandJumpserver(Module* Creator) : Command(Creator, "JUMPSERVER", 0, 4)
39         {
40                 flags_needed = 'o'; syntax = "[<server> <port> <+/-an> <reason>]";
41                 redirect_to.clear();
42                 reason.clear();
43                 port = 0;
44                 redirect_all_immediately = redirect_new_users = false;
45         }
46
47         CmdResult Handle (const std::vector<std::string> &parameters, User *user)
48         {
49                 int n_done = 0;
50                 reason = (parameters.size() < 4) ? "Please use this server/port instead" : parameters[3];
51                 redirect_all_immediately = false;
52                 redirect_new_users = true;
53                 direction = true;
54                 std::string n_done_s;
55
56                 /* No parameters: jumpserver disabled */
57                 if (!parameters.size())
58                 {
59                         if (port)
60                                 user->WriteServ("NOTICE %s :*** Disabled jumpserver (previously set to '%s:%d')", user->nick.c_str(), redirect_to.c_str(), port);
61                         else
62                                 user->WriteServ("NOTICE %s :*** jumpserver was not enabled.", user->nick.c_str());
63
64                         port = 0;
65                         redirect_to.clear();
66                         return CMD_SUCCESS;
67                 }
68
69                 port = 0;
70                 redirect_to.clear();
71
72                 if (parameters.size() >= 3)
73                 {
74                         for (const char* n = parameters[2].c_str(); *n; n++)
75                         {
76                                 switch (*n)
77                                 {
78                                         case '+':
79                                                 direction = true;
80                                         break;
81                                         case '-':
82                                                 direction = false;
83                                         break;
84                                         case 'a':
85                                                 redirect_all_immediately = direction;
86                                         break;
87                                         case 'n':
88                                                 redirect_new_users = direction;
89                                         break;
90                                         default:
91                                                 user->WriteServ("NOTICE %s :*** Invalid JUMPSERVER flag: %c", user->nick.c_str(), *n);
92                                                 return CMD_FAILURE;
93                                         break;
94                                 }
95                         }
96
97                         if (!atoi(parameters[1].c_str()))
98                         {
99                                 user->WriteServ("NOTICE %s :*** Invalid port number", user->nick.c_str());
100                                 return CMD_FAILURE;
101                         }
102
103                         if (redirect_all_immediately)
104                         {
105                                 /* Redirect everyone but the oper sending the command */
106                                 for (std::vector<LocalUser*>::const_iterator i = ServerInstance->Users->local_users.begin(); i != ServerInstance->Users->local_users.end(); i++)
107                                 {
108                                         User* t = *i;
109                                         if (!IS_OPER(t))
110                                         {
111                                                 t->WriteNumeric(10, "%s %s %s :Please use this Server/Port instead", user->nick.c_str(), parameters[0].c_str(), parameters[1].c_str());
112                                                 ServerInstance->Users->QuitUser(t, reason);
113                                                 n_done++;
114                                         }
115                                 }
116                                 if (n_done)
117                                 {
118                                         n_done_s = ConvToStr(n_done);
119                                 }
120                         }
121
122                         if (redirect_new_users)
123                         {
124                                 redirect_to = parameters[0];
125                                 port = atoi(parameters[1].c_str());
126                         }
127
128                         user->WriteServ("NOTICE %s :*** Set jumpserver to server '%s' port '%s', flags '+%s%s'%s%s%s: %s", user->nick.c_str(), parameters[0].c_str(), parameters[1].c_str(),
129                                         redirect_all_immediately ? "a" : "",
130                                         redirect_new_users ? "n" : "",
131                                         n_done ? " (" : "",
132                                         n_done ? n_done_s.c_str() : "",
133                                         n_done ? " user(s) redirected)" : "",
134                                         reason.c_str());
135                 }
136
137                 return CMD_SUCCESS;
138         }
139 };
140
141
142 class ModuleJumpServer : public Module
143 {
144         CommandJumpserver js;
145  public:
146         ModuleJumpServer() : js(this)
147         {
148                 ServerInstance->AddCommand(&js);
149                 Implementation eventlist[] = { I_OnUserRegister, I_OnRehash };
150                 ServerInstance->Modules->Attach(eventlist, this, 2);
151         }
152
153         virtual ~ModuleJumpServer()
154         {
155         }
156
157         virtual ModResult OnUserRegister(LocalUser* user)
158         {
159                 if (js.port && js.redirect_new_users)
160                 {
161                         user->WriteNumeric(10, "%s %s %d :Please use this Server/Port instead",
162                                 user->nick.c_str(), js.redirect_to.c_str(), js.port);
163                         ServerInstance->Users->QuitUser(user, js.reason);
164                         return MOD_RES_PASSTHRU;
165                 }
166                 return MOD_RES_PASSTHRU;
167         }
168
169         virtual void OnRehash(User* user)
170         {
171                 // Emergency way to unlock
172                 if (!user) js.redirect_new_users = false;
173         }
174
175         virtual Version GetVersion()
176         {
177                 return Version("Provides support for the RPL_REDIR numeric", VF_VENDOR);
178         }
179
180 };
181
182 MODULE_INIT(ModuleJumpServer)