]> git.netwichtig.de Git - user/henk/code/inspircd.git/blob - src/modules/m_chanprotect.cpp
a6d6a8a9f9553c79176e2db825c66dabc4159c45
[user/henk/code/inspircd.git] / src / modules / m_chanprotect.cpp
1 #include <stdio.h>
2
3 #include "users.h"
4 #include "channels.h"
5 #include "modules.h"
6
7 /* $ModDesc: Provides channel modes +a and +q */
8
9 char dummyvalue[] = "on";
10
11 class ModuleChanProtect : public Module
12 {
13         Server *Srv;
14         bool FirstInGetsFounder;
15         ConfigReader *Conf;
16         
17  public:
18  
19         ModuleChanProtect()
20         {
21                 Srv = new Server;
22                 Conf = new ConfigReader;
23                 // set up our modes. We're using listmodes and not normal extmodes here.
24                 // listmodes only need one parameter as everything else is assumed by the
25                 // nature of the mode thats being created.
26                 Srv->AddExtendedListMode('a');
27                 Srv->AddExtendedListMode('q');
28                 
29                 // read our config options (main config file)
30                 std::string val = Conf->ReadValue("options","noservices",0);
31                 FirstInGetsFounder = ((val == "yes") || (val == "1") || (val == "true"));
32         }
33         
34         virtual void OnRehash()
35         {
36                 delete Conf;
37                 Conf = new ConfigReader;
38                 // re-read our config options on a rehash
39                 std::string val = Conf->ReadValue("options","noservices",0);
40                 FirstInGetsFounder = ((val == "yes") || (val == "1") || (val == "true"));
41         }
42         
43         virtual void OnUserJoin(userrec* user, chanrec* channel)
44         {
45                 // if the user is the first user into the channel, mark them as the founder, but only if
46                 // the config option for it is set
47                 if (FirstInGetsFounder)
48                 {
49                         if (Srv->CountUsers(channel) == 1)
50                         {
51                                 if (user->Extend("cm_founder_"+std::string(channel->name),dummyvalue))
52                                 {
53                                         Srv->Log(DEBUG,"Marked user "+std::string(user->nick)+" as founder for "+std::string(channel->name));
54                                 }
55                         }
56                 }
57         }
58         
59         virtual int OnAccessCheck(userrec* source,userrec* dest,chanrec* channel,int access_type)
60         {
61                 // don't allow action if:
62                 // (A) Theyre founder (no matter what)
63                 // (B) Theyre protected, and you're not
64                 // always allow the action if:
65                 // (A) The source is ulined
66                 
67                 if ((Srv->IsUlined(source->nick)) || (Srv->IsUlined(source->server)))
68                 {
69                         return ACR_ALLOW;
70                 }
71
72                 switch (access_type)
73                 {
74                         case AC_DEOP:
75                                 if (dest->GetExt("cm_founder_"+std::string(channel->name)))
76                                 {
77                                         Srv->SendServ(source->fd,"482 "+std::string(source->nick)+" "+std::string(channel->name)+" :Can't deop "+std::string(dest->nick)+" as the're a channel founder");
78                                         return ACR_DENY;
79                                 }
80                                 if ((dest->GetExt("cm_protect_"+std::string(channel->name))) && (!source->GetExt("cm_protect_"+std::string(channel->name))))
81                                 {
82                                         Srv->SendServ(source->fd,"482 "+std::string(source->nick)+" "+std::string(channel->name)+" :Can't deop "+std::string(dest->nick)+" as the're protected (+a)");
83                                         return ACR_DENY;
84                                 }
85                         break;
86
87                         case AC_KICK:
88                                 if (dest->GetExt("cm_founder_"+std::string(channel->name)))
89                                 {
90                                         Srv->SendServ(source->fd,"482 "+std::string(source->nick)+" "+std::string(channel->name)+" :Can't kick "+std::string(dest->nick)+" as the're a channel founder");
91                                         return ACR_DENY;
92                                 }
93                                 if ((dest->GetExt("cm_protect_"+std::string(channel->name))) && (!source->GetExt("cm_protect_"+std::string(channel->name))))
94                                 {
95                                         Srv->SendServ(source->fd,"482 "+std::string(source->nick)+" "+std::string(channel->name)+" :Can't kick "+std::string(dest->nick)+" as the're protected (+a)");
96                                         return ACR_DENY;
97                                 }
98                         break;
99
100                         case AC_DEHALFOP:
101                                 if (dest->GetExt("cm_founder_"+std::string(channel->name)))
102                                 {
103                                         Srv->SendServ(source->fd,"482 "+std::string(source->nick)+" "+std::string(channel->name)+" :Can't de-halfop "+std::string(dest->nick)+" as the're a channel founder");
104                                         return ACR_DENY;
105                                 }
106                                 if ((dest->GetExt("cm_protect_"+std::string(channel->name))) && (!source->GetExt("cm_protect_"+std::string(channel->name))))
107                                 {
108                                         Srv->SendServ(source->fd,"482 "+std::string(source->nick)+" "+std::string(channel->name)+" :Can't de-halfop "+std::string(dest->nick)+" as the're protected (+a)");
109                                         return ACR_DENY;
110                                 }
111                         break;
112
113                         case AC_DEVOICE:
114                                 if (dest->GetExt("cm_founder_"+std::string(channel->name)))
115                                 {
116                                         Srv->SendServ(source->fd,"482 "+std::string(source->nick)+" "+std::string(channel->name)+" :Can't devoice "+std::string(dest->nick)+" as the're a channel founder");
117                                         return ACR_DENY;
118                                 }
119                                 if ((dest->GetExt("cm_protect_"+std::string(channel->name))) && (!source->GetExt("cm_protect_"+std::string(channel->name))))
120                                 {
121                                         Srv->SendServ(source->fd,"482 "+std::string(source->nick)+" "+std::string(channel->name)+" :Can't devoice "+std::string(dest->nick)+" as the're protected (+a)");
122                                         return ACR_DENY;
123                                 }
124                         break;
125                 }
126                 return ACR_DEFAULT;
127         }
128         
129         virtual int OnExtendedMode(userrec* user, void* target, char modechar, int type, bool mode_on, string_list &params)
130         {
131                 // not out mode, bail
132                 if ((modechar == 'q') && (type == MT_CHANNEL))
133                 {
134                         // set up parameters
135                         chanrec* chan = (chanrec*)target;
136                         userrec* theuser = Srv->FindNick(params[0]);
137                 
138                         // cant find the user given as the parameter, eat the mode change.
139                         if (!theuser)
140                                 return -1;
141                         
142                         // given user isnt even on the channel, eat the mode change
143                         if (!Srv->IsOnChannel(theuser,chan))
144                                 return -1;
145                         
146                         if ((Srv->IsUlined(user->nick)) || (Srv->IsUlined(user->server)) || (!strcmp(user->server,"")))
147                         {
148                                 if (mode_on)
149                                 {
150                                         if (!theuser->GetExt("cm_founder_"+std::string(chan->name)))
151                                         {
152                                                 theuser->Extend("cm_founder_"+std::string(chan->name),dummyvalue);
153                                                 return 1;
154                                         }
155                                 }
156                                 else
157                                 {
158                                         if (theuser->GetExt("cm_founder_"+std::string(chan->name)))
159                                         {
160                                                 theuser->Shrink("cm_founder_"+std::string(chan->name));
161                                                 return 1;
162                                         }
163                                 }       
164
165                                 return -1;
166                         }
167                         else
168                         {
169                                 WriteServ(user->fd,"482 %s %s :Only servers may set channel mode +q",user->nick, chan->name);
170                                 return -1;
171                         }
172                 }
173                 if ((modechar == 'a') && (type == MT_CHANNEL))
174                 {
175                         // set up parameters
176                         chanrec* chan = (chanrec*)target;
177                         userrec* theuser = Srv->FindNick(params[0]);
178                 
179                         // cant find the user given as the parameter, eat the mode change.
180                         if (!theuser)
181                                 return -1;
182                         
183                         // given user isnt even on the channel, eat the mode change
184                         if (!Srv->IsOnChannel(theuser,chan))
185                                 return -1;
186                         
187                         if ((Srv->IsUlined(user->nick)) || (Srv->IsUlined(user->server)) || (!strcmp(user->server,"")) || (user->GetExt("cm_founder_"+std::string(chan->name))))
188                         {
189                                 if (mode_on)
190                                 {
191                                         if (!theuser->GetExt("cm_founder_"+std::string(chan->name)))
192                                         {
193                                                 theuser->Extend("cm_protect_"+std::string(chan->name),dummyvalue);
194                                                 return 1;
195                                         }
196                                 }
197                                 else
198                                 {
199                                         if (theuser->GetExt("cm_founder_"+std::string(chan->name)))
200                                         {
201                                                 theuser->Shrink("cm_protect_"+std::string(chan->name));
202                                                 return 1;
203                                         }
204                                 }       
205
206                                 return -1;
207                         }
208                         else
209                         {
210                                 WriteServ(user->fd,"482 %s %s :You are not a channel founder",user->nick, chan->name);
211                                 return -1;
212                         }
213                 }
214                 return 0;
215         }
216         
217         virtual ~ModuleChanProtect()
218         {
219                 delete Conf;
220                 delete Srv;
221         }
222         
223         virtual Version GetVersion()
224         {
225                 return Version(1,0,0,0);
226         }
227         
228         virtual void OnUserConnect(userrec* user)
229         {
230         }
231
232 };
233
234
235 class ModuleChanProtectFactory : public ModuleFactory
236 {
237  public:
238         ModuleChanProtectFactory()
239         {
240         }
241         
242         ~ModuleChanProtectFactory()
243         {
244         }
245         
246         virtual Module * CreateModule()
247         {
248                 return new ModuleChanProtect;
249         }
250         
251 };
252
253
254 extern "C" void * init_module( void )
255 {
256         return new ModuleChanProtectFactory;
257 }
258