forked from genius3000/anope-modules
-
Notifications
You must be signed in to change notification settings - Fork 0
/
m_xlinetoakill.cpp
115 lines (93 loc) · 3.42 KB
/
m_xlinetoakill.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
/*
* IRCd X-Line sync with AKILL
*
* (C) 2018 - Matt Schatz ([email protected])
* Please refer to the GPL License in use by Anope at:
* https://github.com/anope/anope/blob/master/docs/COPYING
*
* Syncs X-Lines from the uplink IRCd with the AKILL list.
*
* Configuration to put into your modules config:
module { name = "m_xlinetoakill" }
* Logging is done through the "other" type and category of "akill/sync"
*
*/
#include "module.h"
static ServiceReference<XLineManager> akills("XLineManager", "xlinemanager/sgline");
class XLineToAkill : public Module
{
BotInfo *OperServ;
public:
XLineToAkill(const Anope::string &modname, const Anope::string &creator)
: Module(modname, creator, THIRD)
, OperServ(NULL)
{
if (Anope::VersionMajor() != 2 || Anope::VersionMinor() != 0)
throw ModuleException("Requires version 2.0.x of Anope.");
if (!ModuleManager::FindModule("inspircd20"))
throw ModuleException("This module only works with the InspIRCd 2.0 protocol.");
if (!ModuleManager::FindModule("operserv") || !ModuleManager::FindModule("os_akill"))
throw ModuleException("This module requires both OperServ and OS_AKILL to function.");
this->SetAuthor("genius3000");
this->SetVersion("1.0.0");
}
void OnReload(Configuration::Conf *conf) anope_override
{
OperServ = conf->GetClient("OperServ");
}
EventReturn OnMessage(MessageSource &source, Anope::string &command, std::vector<Anope::string> ¶ms)
{
if ((command != "ADDLINE" && command != "DELLINE") || params.size() < 2 || !akills)
return EVENT_CONTINUE;
// Translate the mask from InspIRCd to Anope format
const Anope::string linetype = params[0];
Anope::string mask = params[1];
// R-Lines are sent as 'n!u@h\sreal\sname' and need to be '/n!u@h#real name/'
if (linetype == "R")
{
size_t space = mask.find("\\s");
if (space != Anope::string::npos)
{
mask = mask.replace(space, 2, "#");
mask = mask.replace_all_cs("\\s", " ");
}
mask = "/" + mask + "/";
}
// Z-Lines are sent as 'IP' and need to be '*@IP'
else if (linetype == "Z")
mask = "*@" + mask;
// G-Lines need no translating
// Ignore any other X-Line types
else if (linetype != "G")
return EVENT_CONTINUE;
// Adding
if (command == "ADDLINE" && params.size() == 6)
{
// Ignore this X-Line if it exists as an AKILL already
if (akills->HasEntry(mask))
return EVENT_CONTINUE;
const Anope::string setby = params[2];
time_t settime = convertTo<time_t>(params[3]);
time_t duration = convertTo<time_t>(params[4]);
const Anope::string reason = params[5];
time_t expires = (duration == 0) ? duration : settime + duration;
XLine *x = new XLine(mask, setby, expires, reason, XLineManager::GenerateUID());
akills->AddXLine(x);
Log(OperServ, "akill/sync") << "X-Line (" << linetype << ") sync added AKILL on " << mask << " (" << reason << "), expires in " << (expires ? Anope::Duration(expires - settime) : "never") << " [set by " << setby << "]";
}
// Removing
else if (command == "DELLINE")
{
// Ignore this X-Line if it doesn't exist as an AKILL
XLine *x = akills->HasEntry(mask);
if (!x)
return EVENT_CONTINUE;
akills->DelXLine(x);
Log(OperServ, "akill/sync") << "X-Line (" << linetype << ") sync removed AKILL on " << mask;
}
// Standard protocol modules do nothing with ADDLINE and DELLINE,
// allow other modules to act on these though.
return EVENT_CONTINUE;
}
};
MODULE_INIT(XLineToAkill)