diff options
Diffstat (limited to 'src')
149 files changed, 14553 insertions, 14184 deletions
diff --git a/src/actions.c b/src/actions.c index 25bea0091..6b96c66fa 100644 --- a/src/actions.c +++ b/src/actions.c @@ -180,8 +180,8 @@ void common_unban(ChannelInfo * ci, char *nick) for (ban = ci->c->bans->entries; ban; ban = next) { next = ban->next; - if (entry_match(ban, u->nick, u->username, u->host, ip) || - entry_match(ban, u->nick, u->username, u->vhost, ip)) { + if (entry_match(ban, u->nick, u->GetIdent().c_str(), u->host, ip) || + entry_match(ban, u->nick, u->GetIdent().c_str(), u->vhost, ip)) { ircdproto->SendMode(whosends(ci), ci->name, "-b %s", ban->mask); if (ircdcap->tsmode) av[3] = ban->mask; @@ -224,42 +224,3 @@ void common_svsmode(User * u, const char *modes, const char *arg) /*************************************************************************/ -/** - * Get the vhost for the user, if set else return the host, on ircds without - * vhost this returns the host - * @param u user to get the vhost for - * @return vhost - */ -char *common_get_vhost(User * u) -{ - if (!u) - return NULL; - - if (ircd->vhostmode && (u->mode & ircd->vhostmode)) - return u->vhost; - else if (ircd->vhost && u->vhost) - return u->vhost; - else - return u->host; -} - -/*************************************************************************/ - -/** - * Get the vident for the user, if set else return the ident, on ircds without - * vident this returns the ident - * @param u user to get info the vident for - * @return vident - */ -char *common_get_vident(User * u) -{ - if (!u) - return NULL; - - if (ircd->vhostmode && (u->mode & ircd->vhostmode)) - return u->vident; - else if (ircd->vident && u->vident) - return u->vident; - else - return u->username; -} diff --git a/src/botserv.c b/src/botserv.c index e671006e2..96b017bcd 100644 --- a/src/botserv.c +++ b/src/botserv.c @@ -421,14 +421,22 @@ void botchanmsgs(User * u, ChannelInfo * ci, char *buf) /* Strip off the fantasy character */ cmd++; - if (check_access(u, ci, CA_FANTASIA)) + if (check_access(u, ci, CA_FANTASIA)) + { + std::string bbuf = std::string(cmd) + " " + ci->name; + if (params) + { + bbuf += " "; + bbuf += params; + } + chanserv(u, const_cast<char *>(bbuf.c_str())); // XXX Unsafe cast, this needs reviewing -- CyberBotX event_name = EVENT_BOT_FANTASY; + } if (params) send_event(event_name, 4, cmd, u->nick, ci->name, params); else - send_event(event_name, 3, cmd, u->nick, ci->name); - } + send_event(event_name, 3, cmd, u->nick, ci->name);} } } @@ -596,8 +604,8 @@ static BanData *get_ban_data(Channel * c, User * u) if (!c || !u) return NULL; - snprintf(mask, sizeof(mask), "%s@%s", u->username, - common_get_vhost(u)); + snprintf(mask, sizeof(mask), "%s@%s", u->GetIdent().c_str(), + u->GetDisplayedHost().c_str()); for (bd = c->bd; bd; bd = next) { if (now - bd->last_use > BSKeepData) { diff --git a/src/channels.c b/src/channels.c index 4d5c08b5a..ab5e0b3a8 100644 --- a/src/channels.c +++ b/src/channels.c @@ -174,27 +174,6 @@ void chan_set_modes(const char *source, Channel * chan, int ac, const char **av, alog("debug: Changing modes for %s to %s", chan->name, merge_args(ac, av)); - u = finduser(source); - if (u && (chan_get_user_status(chan, u) & CUS_DEOPPED)) { - char *s; - - if (debug) - alog("debug: Removing instead of setting due to DEOPPED flag"); - - /* Swap adding and removing of the modes */ - for (s = const_cast<char *>(av[0]); *s; s++) { // XXX Unsafe cast, this needs reviewing -- CyberBotX - if (*s == '+') - *s = '-'; - else if (*s == '-') - *s = '+'; - } - - /* Set the resulting mode buffer */ - ircdproto->SendMode(whosends(chan->ci), chan->name, merge_args(ac, av)); - - return; - } - ac--; while ((mode = *modes++)) { @@ -256,8 +235,6 @@ void chan_set_modes(const char *source, Channel * chan, int ac, const char **av, if (add) { chan_set_user_status(chan, user, cum->status); /* If this does +o, remove any DEOPPED flag */ - if (cum->status & CUS_OP) - chan_remove_user_status(chan, user, CUS_DEOPPED); } else { chan_remove_user_status(chan, user, cum->status); } @@ -1471,7 +1448,6 @@ void chan_set_correct_modes(User * user, Channel * c, int give_modes) strcat(modebuf, "o"); strcat(userbuf, " "); strcat(userbuf, user->nick); - rem_modes |= CUS_DEOPPED; } else { add_modes &= ~CUS_OP; } @@ -1510,7 +1486,6 @@ void chan_set_correct_modes(User * user, Channel * c, int give_modes) strcat(modebuf, "o"); strcat(userbuf, " "); strcat(userbuf, user->nick); - add_modes |= CUS_DEOPPED; } if (rem_modes & CUS_HALFOP) { strcat(modebuf, "h"); @@ -2122,7 +2097,7 @@ EList *list_create() * @param ip IP to match against, set to 0 to not match this * @return 1 for a match, 0 for no match */ -int entry_match(Entry * e, char *nick, char *user, char *host, uint32 ip) +int entry_match(Entry * e, const char *nick, const char *user, const char *host, uint32 ip) { /* If we don't get an entry, or it s an invalid one, no match ~ Viper */ if (!e || e->type == ENTRYTYPE_NONE) @@ -2160,7 +2135,7 @@ int entry_match(Entry * e, char *nick, char *user, char *host, uint32 ip) * @param ip IP to match against, set to 0 to not match this * @return 1 for a match, 0 for no match */ -int entry_match_mask(Entry * e, char *mask, uint32 ip) +int entry_match_mask(Entry * e, const char *mask, uint32 ip) { char *hostmask, *nick, *user, *host; int res; @@ -2201,7 +2176,7 @@ int entry_match_mask(Entry * e, char *mask, uint32 ip) * @param ip The ip to match * @return Returns the first matching entry, if none, NULL is returned. */ -Entry *elist_match(EList * list, char *nick, char *user, char *host, +Entry *elist_match(EList * list, const char *nick, const char *user, const char *host, uint32 ip) { Entry *e; @@ -2225,7 +2200,7 @@ Entry *elist_match(EList * list, char *nick, char *user, char *host, * @param ip The ip to match * @return Returns the first matching entry, if none, NULL is returned. */ -Entry *elist_match_mask(EList * list, char *mask, uint32 ip) +Entry *elist_match_mask(EList * list, const char *mask, uint32 ip) { char *hostmask, *nick, *user, *host; Entry *res; @@ -2291,9 +2266,9 @@ Entry *elist_match_user(EList * list, User * u) ip = str_is_ip(host); /* Match what we ve got against the lists.. */ - res = elist_match(list, u->nick, u->username, u->host, ip); + res = elist_match(list, u->nick, u->GetIdent().c_str(), u->host, ip); if (!res) - elist_match(list, u->nick, u->username, u->vhost, ip); + elist_match(list, u->nick, u->GetIdent().c_str(), u->vhost, ip); if (host) delete [] host; diff --git a/src/chanserv.c b/src/chanserv.c index eff790d49..ee3b96e97 100644 --- a/src/chanserv.c +++ b/src/chanserv.c @@ -1197,7 +1197,7 @@ int check_kick(User * user, const char *chan, time_t chants) kick: if (debug) alog("debug: channel: AutoKicking %s!%s@%s from %s", user->nick, - user->username, user->host, chan); + user->GetIdent().c_str(), user->host, chan); /* Remember that the user has not been added to our channel user list * yet, so we check whether the channel does not exist OR has no user @@ -1968,22 +1968,24 @@ int get_idealban(ChannelInfo * ci, User * u, char *ret, int retlen) if (!ci || !u || !ret || retlen == 0) return 0; + std::string vident = u->GetIdent(); + switch (ci->bantype) { case 0: - snprintf(ret, retlen, "*!%s@%s", common_get_vident(u), - common_get_vhost(u)); + snprintf(ret, retlen, "*!%s@%s", vident.c_str(), + u->GetDisplayedHost().c_str()); return 1; case 1: - snprintf(ret, retlen, "*!%s%s@%s", - (strlen(common_get_vident(u)) < - (*(common_get_vident(u)) == - '~' ? USERMAX + 1 : USERMAX) ? "*" : ""), - (*(common_get_vident(u)) == - '~' ? common_get_vident(u) + 1 : common_get_vident(u)), - common_get_vhost(u)); + if (vident[0] == '~') + snprintf(ret, retlen, "*!*%s@%s", + vident.c_str(), u->GetDisplayedHost().c_str()); + else + snprintf(ret, retlen, "*!%s@%s", + vident.c_str(), u->GetDisplayedHost().c_str()); + return 1; case 2: - snprintf(ret, retlen, "*!*@%s", common_get_vhost(u)); + snprintf(ret, retlen, "*!*@%s", u->GetDisplayedHost().c_str()); return 1; case 3: mask = create_mask(u); diff --git a/src/commands.c b/src/commands.c index 52b74b488..17b6629b3 100644 --- a/src/commands.c +++ b/src/commands.c @@ -29,8 +29,8 @@ Command *lookup_cmd(Command * list, char *cmd) { Command *c; - for (c = list; c->name; c++) { - if (stricmp(c->name, cmd) == 0) { + for (c = list; ; c++) { + if (stricmp(c->name.c_str(), cmd) == 0) { return c; } } @@ -48,39 +48,66 @@ Command *lookup_cmd(Command * list, char *cmd) * @param cmd Command * @return void */ -void mod_run_cmd(char *service, User * u, CommandHash * cmdTable[], - const char *cmd) +void mod_run_cmd(char *service, User * u, CommandHash * cmdTable[], const char *cmd) { Command *c = findCommand(cmdTable, cmd); int retVal = 0; Command *current; - if (c && c->routine) { - if ((checkDefCon(DEFCON_OPER_ONLY) - || checkDefCon(DEFCON_SILENT_OPER_ONLY)) && !is_oper(u)) { - if (!checkDefCon(DEFCON_SILENT_OPER_ONLY)) { - notice_lang(service, u, OPER_DEFCON_DENIED); - } - } else { - if ((c->has_priv == NULL) || c->has_priv(u)) { - retVal = c->routine(u); - if (retVal == MOD_CONT) { - current = c->next; - while (current && retVal == MOD_CONT) { - retVal = current->routine(u); - current = current->next; - } - } - } else { - notice_lang(service, u, ACCESS_DENIED); - alog("Access denied for %s with service %s and command %s", - u->nick, service, cmd); - } - } - } else { - if ((!checkDefCon(DEFCON_SILENT_OPER_ONLY)) || is_oper(u)) { + if (!c) + { + if ((!checkDefCon(DEFCON_SILENT_OPER_ONLY)) || is_oper(u)) + { notice_lang(service, u, UNKNOWN_COMMAND_HELP, cmd, service); } + return; + } + + if ((checkDefCon(DEFCON_OPER_ONLY) || checkDefCon(DEFCON_SILENT_OPER_ONLY)) && !is_oper(u)) + { + if (!checkDefCon(DEFCON_SILENT_OPER_ONLY)) + { + notice_lang(service, u, OPER_DEFCON_DENIED); + return; + } + } + + if (c->has_priv != NULL && !c->has_priv(u)) + { + notice_lang(service, u, ACCESS_DENIED); + alog("Access denied for %s with service %s and command %s", u->nick, service, cmd); + return; + } + + std::vector<std::string> params; + std::string curparam; + char *s = NULL; + while ((s = strtok(NULL, " "))) + { + if (params.size() < c->MaxParams) + params.push_back(s); + else + curparam += s; + } + + if (!curparam.empty()) + params.push_back(curparam); + + if (params.size() < c->MinParams) + { + c->OnBadSyntax(u); + return; + } + + retVal = c->Execute(u, params); + if (retVal == MOD_CONT) + { + current = c->next; + while (current && retVal == MOD_CONT) + { + retVal = current->Execute(u, params); + current = current->next; + } } } @@ -124,7 +151,7 @@ void mod_help_cmd(char *service, User * u, CommandHash * cmdTable[], { Command *c = findCommand(cmdTable, cmd); Command *current; - int has_had_help = 0; + bool has_had_help = false; int cont = MOD_CONT; const char *p1 = NULL, *p2 = NULL, *p3 = NULL, *p4 = NULL; @@ -134,52 +161,9 @@ void mod_help_cmd(char *service, User * u, CommandHash * cmdTable[], p2 = current->help_param2; p3 = current->help_param3; p4 = current->help_param4; - if (current->helpmsg_all >= 0) { - notice_help(service, u, current->helpmsg_all, p1, p2, p3, p4); - has_had_help = 1; - } else if (current->all_help) { - cont = current->all_help(u); - has_had_help = 1; - } - if (is_services_root(u)) { - if (current->helpmsg_root >= 0) { - notice_help(service, u, current->helpmsg_root, p1, p2, p3, - p4); - has_had_help = 1; - } else if (current->root_help) { - cont = current->root_help(u); - has_had_help = 1; - } - } else if (is_services_admin(u)) { - if (current->helpmsg_admin >= 0) { - notice_help(service, u, current->helpmsg_admin, p1, p2, p3, - p4); - has_had_help = 1; - } else if (current->admin_help) { - cont = current->admin_help(u); - has_had_help = 1; - } - } else if (is_services_oper(u)) { - if (current->helpmsg_oper >= 0) { - notice_help(service, u, current->helpmsg_oper, p1, p2, p3, - p4); - has_had_help = 1; - } else if (current->oper_help) { - cont = current->oper_help(u); - has_had_help = 1; - } - } else { - if (current->helpmsg_reg >= 0) { - notice_help(service, u, current->helpmsg_reg, p1, p2, p3, - p4); - has_had_help = 1; - } else if (current->regular_help) { - cont = current->regular_help(u); - has_had_help = 1; - } - } + has_had_help = current->OnHelp(u, ""); // XXX: this needs finishing to actually pass a subcommand } - if (has_had_help == 0) { + if (has_had_help == false) { notice_lang(service, u, NO_HELP_AVAILABLE, cmd); } else { do_help_limited(service, u, c); diff --git a/src/core/bs_act.c b/src/core/bs_act.c index 0f2e34af2..f37f2d942 100644 --- a/src/core/bs_act.c +++ b/src/core/bs_act.c @@ -15,21 +15,78 @@ #include "module.h" -int do_act(User * u); void myBotServHelp(User * u); +class CommandBSAct : public Command +{ + public: + CommandBSAct() : Command("ACT", 2, 2) + { + + } + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + ChannelInfo *ci; + + if (!(ci = cs_findchan(params[0].c_str()))) + { + notice_lang(s_BotServ, u, CHAN_X_NOT_REGISTERED, params[0].c_str()); + return MOD_CONT; + } + + if (ci->flags & CI_VERBOTEN) + { + notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, ci->name); + return MOD_CONT; + } + + if (!ci->bi) + { + notice_help(s_BotServ, u, BOT_NOT_ASSIGNED); + return MOD_CONT; + } + + if (!ci->c || ci->c->usercount < BSMinUsers) + { + notice_lang(s_BotServ, u, BOT_NOT_ON_CHANNEL, ci->name); + return MOD_CONT; + } + + if (!check_access(u, ci, CA_SAY)) + { + notice_lang(s_BotServ, u, ACCESS_DENIED); + return MOD_CONT; + } + + size_t i = 0; + while ((i = params[1].find_first_of("\001"), i) && i != std::string::npos) + { + params[1].erase(i, 1); + } + + ircdproto->SendAction(ci->bi, ci->name, "%s", params[1].c_str()); + ci->bi->lastmsg = time(NULL); + if (LogBot && LogChannel && logchan && !debug && findchan(LogChannel)) + ircdproto->SendPrivmsg(ci->bi, LogChannel, "ACT %s %s %s", u->nick, ci->name, params[1].c_str()); + return MOD_CONT; + } + + void OnBadSyntax(User *u) + { + syntax_error(s_BotServ, u, "ACT", BOT_ACT_SYNTAX); + } +}; + class BSAct : public Module { public: BSAct(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("ACT", do_act, NULL, BOT_HELP_ACT, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); + this->AddCommand(BOTSERV, new CommandBSAct(), MOD_UNIQUE); this->SetBotHelp(myBotServHelp); } @@ -45,39 +102,4 @@ void myBotServHelp(User * u) notice_lang(s_BotServ, u, BOT_HELP_CMD_ACT); } -/** - * The /bs act command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_act(User * u) -{ - ChannelInfo *ci; - - char *chan = strtok(NULL, " "); - char *text = strtok(NULL, ""); - - if (!chan || !text) - syntax_error(s_BotServ, u, "ACT", BOT_ACT_SYNTAX); - else if (!(ci = cs_findchan(chan))) - notice_lang(s_BotServ, u, CHAN_X_NOT_REGISTERED, chan); - else if (ci->flags & CI_VERBOTEN) - notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, chan); - else if (!ci->bi) - notice_help(s_BotServ, u, BOT_NOT_ASSIGNED); - else if (!ci->c || ci->c->usercount < BSMinUsers) - notice_lang(s_BotServ, u, BOT_NOT_ON_CHANNEL, ci->name); - else if (!check_access(u, ci, CA_SAY)) - notice_lang(s_BotServ, u, ACCESS_DENIED); - else { - strnrepl(text, BUFSIZE, "\001", ""); - ircdproto->SendAction(ci->bi, ci->name, "%s", text); - ci->bi->lastmsg = time(NULL); - if (LogBot && LogChannel && logchan && !debug && findchan(LogChannel)) - ircdproto->SendPrivmsg(ci->bi, LogChannel, "ACT %s %s %s", - u->nick, ci->name, text); - } - return MOD_CONT; -} - MODULE_INIT("bs_act", BSAct) diff --git a/src/core/bs_assign.c b/src/core/bs_assign.c index 396031662..f9927e25d 100644 --- a/src/core/bs_assign.c +++ b/src/core/bs_assign.c @@ -15,21 +15,90 @@ #include "module.h" -int do_assign(User * u); void myBotServHelp(User * u); +class CommandBSAssign : public Command +{ + public: + CommandBSAssign() : Command("ASSIGN", 1, 1) + { + } + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + char *chan = strtok(NULL, " "); + char *nick = strtok(NULL, " "); + BotInfo *bi; + ChannelInfo *ci; + + if (readonly) + { + notice_lang(s_BotServ, u, BOT_ASSIGN_READONLY); + return MOD_CONT; + } + + if (!(bi = findbot(nick))) + { + notice_lang(s_BotServ, u, BOT_DOES_NOT_EXIST, nick); + return MOD_CONT; + } + + if (bi->flags & BI_PRIVATE && !is_oper(u)) + { + notice_lang(s_BotServ, u, PERMISSION_DENIED); + return MOD_CONT; + } + + if (!(ci = cs_findchan(chan))) + { + notice_lang(s_BotServ, u, CHAN_X_NOT_REGISTERED, chan); + return MOD_CONT; + } + + if (ci->flags & CI_VERBOTEN) + { + notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } + + if ((ci->bi) && (stricmp(ci->bi->nick, nick) == 0)) + { + notice_lang(s_BotServ, u, BOT_ASSIGN_ALREADY, ci->bi->nick, chan); + return MOD_CONT; + } + + if ((ci->botflags & BS_NOBOT) || (!check_access(u, ci, CA_ASSIGN) && !is_services_admin(u))) + { + notice_lang(s_BotServ, u, PERMISSION_DENIED); + return MOD_CONT; + } + + bi->Assign(u, ci); + notice_lang(s_BotServ, u, BOT_ASSIGN_ASSIGNED, bi->nick, ci->name); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_BotServ, u, BOT_HELP_ASSIGN); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_BotServ, u, "ASSIGN", BOT_ASSIGN_SYNTAX); + } +}; + class BSAssign : public Module { public: BSAssign(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("ASSIGN", do_assign, NULL, BOT_HELP_ASSIGN, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); + this->AddCommand(BOTSERV, new CommandBSAssign, MOD_UNIQUE); this->SetBotHelp(myBotServHelp); } @@ -44,40 +113,4 @@ void myBotServHelp(User * u) notice_lang(s_BotServ, u, BOT_HELP_CMD_ASSIGN); } -/** - * The /bs assign command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_assign(User * u) -{ - char *chan = strtok(NULL, " "); - char *nick = strtok(NULL, " "); - BotInfo *bi; - ChannelInfo *ci; - - if (readonly) - notice_lang(s_BotServ, u, BOT_ASSIGN_READONLY); - else if (!chan || !nick) - syntax_error(s_BotServ, u, "ASSIGN", BOT_ASSIGN_SYNTAX); - else if (!(bi = findbot(nick))) - notice_lang(s_BotServ, u, BOT_DOES_NOT_EXIST, nick); - else if (bi->flags & BI_PRIVATE && !is_oper(u)) - notice_lang(s_BotServ, u, PERMISSION_DENIED); - else if (!(ci = cs_findchan(chan))) - notice_lang(s_BotServ, u, CHAN_X_NOT_REGISTERED, chan); - else if (ci->flags & CI_VERBOTEN) - notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, chan); - else if ((ci->bi) && (stricmp(ci->bi->nick, nick) == 0)) - notice_lang(s_BotServ, u, BOT_ASSIGN_ALREADY, ci->bi->nick, chan); - else if ((ci->botflags & BS_NOBOT) - || (!check_access(u, ci, CA_ASSIGN) && !is_services_admin(u))) - notice_lang(s_BotServ, u, PERMISSION_DENIED); - else { - bi->Assign(u, ci); - notice_lang(s_BotServ, u, BOT_ASSIGN_ASSIGNED, bi->nick, ci->name); - } - return MOD_CONT; -} - MODULE_INIT("bs_assign", BSAssign) diff --git a/src/core/bs_badwords.c b/src/core/bs_badwords.c index 8a37e9816..41050dc93 100644 --- a/src/core/bs_badwords.c +++ b/src/core/bs_badwords.c @@ -15,80 +15,65 @@ #include "module.h" -int do_badwords(User * u); void myBotServHelp(User * u); int badwords_del_callback(User * u, int num, va_list args); int badwords_list(User * u, int index, ChannelInfo * ci, int *sent_header); int badwords_list_callback(User * u, int num, va_list args); -class BSBadwords : public Module +class CommandBSBadwords : public Command { - public: - BSBadwords(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + CommandReturn DoList(User *u, ChannelInfo *ci, const char *word) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); + int sent_header = 0; + int i = 0; - c = createCommand("BADWORDS", do_badwords, NULL, BOT_HELP_BADWORDS, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); + if (ci->bwcount == 0) + { + notice_lang(s_BotServ, u, BOT_BADWORDS_LIST_EMPTY, ci->name); + return MOD_CONT; + } + if (word && strspn(word, "1234567890,-") == strlen(word)) + { + process_numlist(word, NULL, badwords_list_callback, u, ci, &sent_header); + } + else + { + for (i = 0; i < ci->bwcount; i++) + { + if (!(ci->badwords[i].in_use)) + continue; + if (word && ci->badwords[i].word + && !match_wild_nocase(word, ci->badwords[i].word)) + continue; + badwords_list(u, i, ci, &sent_header); + } + } + if (!sent_header) + notice_lang(s_BotServ, u, BOT_BADWORDS_NO_MATCH, ci->name); - this->SetBotHelp(myBotServHelp); + return MOD_CONT; } -}; - - -/** - * Add the help response to Anopes /bs help output. - * @param u The user who is requesting help - **/ -void myBotServHelp(User * u) -{ - notice_lang(s_BotServ, u, BOT_HELP_CMD_BADWORDS); -} - -/** - * The /bs badwords command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_badwords(User * u) -{ - char *chan = strtok(NULL, " "); - char *cmd = strtok(NULL, " "); - char *word = strtok(NULL, ""); - ChannelInfo *ci; - BadWord *bw; - - unsigned i; - int need_args = (cmd - && (!stricmp(cmd, "LIST") || !stricmp(cmd, "CLEAR"))); - - if (!cmd || (need_args ? 0 : !word)) { - syntax_error(s_BotServ, u, "BADWORDS", BOT_BADWORDS_SYNTAX); - } else if (!(ci = cs_findchan(chan))) { - notice_lang(s_BotServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, chan); - } else if (!check_access(u, ci, CA_BADWORDS) - && (!need_args || !is_services_admin(u))) { - notice_lang(s_BotServ, u, ACCESS_DENIED); - } else if (stricmp(cmd, "ADD") == 0) { - + + CommandReturn DoAdd(User *u, ChannelInfo *ci, const char *word) + { char *opt, *pos; int type = BW_ANY; + unsigned i = 0; + BadWord *bw; - if (readonly) { + if (readonly) + { notice_lang(s_BotServ, u, BOT_BADWORDS_DISABLED); return MOD_CONT; } pos = strrchr(word, ' '); - if (pos) { + if (pos) + { opt = pos + 1; - if (*opt) { + if (*opt) + { if (!stricmp(opt, "SINGLE")) type = BW_SINGLE; else if (!stricmp(opt, "START")) @@ -100,26 +85,33 @@ int do_badwords(User * u) } } - for (bw = ci->badwords, i = 0; i < ci->bwcount; bw++, i++) { + for (bw = ci->badwords, i = 0; i < ci->bwcount; bw++, i++) + { if (bw->word && ((BSCaseSensitive && (!strcmp(bw->word, word))) || (!BSCaseSensitive - && (!stricmp(bw->word, word))))) { + && (!stricmp(bw->word, word))))) + { notice_lang(s_BotServ, u, BOT_BADWORDS_ALREADY_EXISTS, bw->word, ci->name); return MOD_CONT; } } - for (i = 0; i < ci->bwcount; i++) { + for (i = 0; i < ci->bwcount; i++) + { if (!ci->badwords[i].in_use) break; } - if (i == ci->bwcount) { - if (i < BSBadWordsMax) { + if (i == ci->bwcount) + { + if (i < BSBadWordsMax) + { ci->bwcount++; ci->badwords = static_cast<BadWord *>(srealloc(ci->badwords, sizeof(BadWord) * ci->bwcount)); - } else { + } + else + { notice_lang(s_BotServ, u, BOT_BADWORDS_REACHED_LIMIT, BSBadWordsMax); return MOD_CONT; @@ -131,50 +123,57 @@ int do_badwords(User * u) bw->type = type; notice_lang(s_BotServ, u, BOT_BADWORDS_ADDED, bw->word, ci->name); + return MOD_CONT; + } - } else if (stricmp(cmd, "DEL") == 0) { + CommandReturn DoDelete(User *u, ChannelInfo *ci, const char *word) + { int deleted = 0, a, b; - - if (readonly) { - notice_lang(s_BotServ, u, BOT_BADWORDS_DISABLED); - return MOD_CONT; - } + int i; + BadWord *bw; /* Special case: is it a number/list? Only do search if it isn't. */ - if (isdigit(*word) && strspn(word, "1234567890,-") == strlen(word)) { + if (isdigit(*word) && strspn(word, "1234567890,-") == strlen(word)) + { int count, last = -1; - deleted = - process_numlist(word, &count, badwords_del_callback, u, ci, - &last); - if (!deleted) { - if (count == 1) { - notice_lang(s_BotServ, u, BOT_BADWORDS_NO_SUCH_ENTRY, - last, ci->name); - } else { - notice_lang(s_BotServ, u, BOT_BADWORDS_NO_MATCH, - ci->name); + deleted = process_numlist(word, &count, badwords_del_callback, u, ci, &last); + if (!deleted) + { + if (count == 1) + { + notice_lang(s_BotServ, u, BOT_BADWORDS_NO_SUCH_ENTRY, last, ci->name); + } + else + { + notice_lang(s_BotServ, u, BOT_BADWORDS_NO_MATCH, ci->name); } - } else if (deleted == 1) { - notice_lang(s_BotServ, u, BOT_BADWORDS_DELETED_ONE, - ci->name); - } else { - notice_lang(s_BotServ, u, BOT_BADWORDS_DELETED_SEVERAL, - deleted, ci->name); } - } else { - for (i = 0; i < ci->bwcount; i++) { - if (ci->badwords[i].in_use - && !stricmp(ci->badwords[i].word, word)) + else if (deleted == 1) + { + notice_lang(s_BotServ, u, BOT_BADWORDS_DELETED_ONE, ci->name); + } + else + { + notice_lang(s_BotServ, u, BOT_BADWORDS_DELETED_SEVERAL, deleted, ci->name); + } + } + else + { + + for (i = 0; i < ci->bwcount; i++) + { + if (!ci->badwords[i].in_use) break; } - if (i == ci->bwcount) { - notice_lang(s_BotServ, u, BOT_BADWORDS_NOT_FOUND, word, - chan); + + if (i == ci->bwcount) + { + notice_lang(s_BotServ, u, BOT_BADWORDS_NOT_FOUND, word, ci->name); return MOD_CONT; } + bw = &ci->badwords[i]; - notice_lang(s_BotServ, u, BOT_BADWORDS_DELETED, bw->word, - ci->name); + notice_lang(s_BotServ, u, BOT_BADWORDS_DELETED, bw->word, ci->name); if (bw->word) delete [] bw->word; bw->word = NULL; @@ -205,8 +204,8 @@ int do_badwords(User * u) } /* After reordering only the entries at the end could still be empty. * We ll free the places no longer in use... - Viper */ - for (int j = ci->bwcount - 1; j >= 0; j--) { - if (ci->badwords[j].in_use) + for (i = ci->bwcount - 1; i >= 0; i--) { + if (ci->badwords[i].in_use) break; ci->bwcount--; } @@ -214,50 +213,124 @@ int do_badwords(User * u) static_cast<BadWord *>(srealloc(ci->badwords,sizeof(BadWord) * ci->bwcount)); } - } else if (stricmp(cmd, "LIST") == 0) { - int sent_header = 0; + return MOD_CONT; + } + + CommandReturn DoClear(User *u, ChannelInfo *ci, const char *word) + { + int i; + for (i = 0; i < ci->bwcount; i++) + if (ci->badwords[i].word) + delete [] ci->badwords[i].word; - if (ci->bwcount == 0) { - notice_lang(s_BotServ, u, BOT_BADWORDS_LIST_EMPTY, chan); + free(ci->badwords); + ci->badwords = NULL; + ci->bwcount = 0; + + notice_lang(s_BotServ, u, BOT_BADWORDS_CLEAR); + return MOD_CONT; + } + public: + CommandBSBadwords() : Command("BADWORDS", 2, 3) + { + } + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + const char *cmd = params[1].c_str(); + const char *word = params[2].c_str(); + ChannelInfo *ci; + int need_args = (cmd + && (!stricmp(cmd, "LIST") || !stricmp(cmd, "CLEAR"))); + + if (!cmd || (need_args ? 0 : !word)) + { + this->OnSyntaxError(u); return MOD_CONT; } - if (word && strspn(word, "1234567890,-") == strlen(word)) { - process_numlist(word, NULL, badwords_list_callback, u, ci, - &sent_header); - } else { - for (i = 0; i < ci->bwcount; i++) { - if (!(ci->badwords[i].in_use)) - continue; - if (word && ci->badwords[i].word - && !match_wild_nocase(word, ci->badwords[i].word)) - continue; - badwords_list(u, i, ci, &sent_header); - } + + if (!(ci = cs_findchan(chan))) + { + notice_lang(s_BotServ, u, CHAN_X_NOT_REGISTERED, chan); + return MOD_CONT; } - if (!sent_header) - notice_lang(s_BotServ, u, BOT_BADWORDS_NO_MATCH, chan); - } else if (stricmp(cmd, "CLEAR") == 0) { + if (ci->flags & CI_VERBOTEN) + { + notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } - if (readonly) { - notice_lang(s_BotServ, u, BOT_BADWORDS_DISABLED); + if (!check_access(u, ci, CA_BADWORDS) && (!need_args || !is_services_admin(u))) + { + notice_lang(s_BotServ, u, ACCESS_DENIED); return MOD_CONT; } - for (i = 0; i < ci->bwcount; i++) - if (ci->badwords[i].word) - delete [] ci->badwords[i].word; + if (readonly) + { + notice_lang(s_BotServ, u, BOT_BADWORDS_DISABLED); + return MOD_CONT; + } - free(ci->badwords); - ci->badwords = NULL; - ci->bwcount = 0; + if (stricmp(cmd, "ADD") == 0) + { + return this->DoAdd(u, ci, word); + } + else if (stricmp(cmd, "DEL") == 0) + { + return this->DoDelete(u, ci, word); + } + else if (stricmp(cmd, "LIST") == 0) + { + return this->DoList(u, ci, word); + } + else if (stricmp(cmd, "CLEAR") == 0) + { + return this->DoClear(u, ci, word); + } + else + { + this->OnSyntaxError(u); + } + return MOD_CONT; + } - notice_lang(s_BotServ, u, BOT_BADWORDS_CLEAR); + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_BotServ, u, BOT_HELP_BADWORDS); + return true; + } - } else { + void OnSyntaxError(User *u) + { syntax_error(s_BotServ, u, "BADWORDS", BOT_BADWORDS_SYNTAX); } - return MOD_CONT; +}; + +class BSBadwords : public Module +{ + public: + BSBadwords(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(BOTSERV, new CommandBSBadwords, MOD_UNIQUE); + + this->SetBotHelp(myBotServHelp); + } +}; + + +/** + * Add the help response to Anopes /bs help output. + * @param u The user who is requesting help + **/ +void myBotServHelp(User * u) +{ + notice_lang(s_BotServ, u, BOT_HELP_CMD_BADWORDS); } int badwords_del_callback(User * u, int num, va_list args) diff --git a/src/core/bs_bot.c b/src/core/bs_bot.c index 92514950a..45de014ce 100644 --- a/src/core/bs_bot.c +++ b/src/core/bs_bot.c @@ -15,72 +15,23 @@ #include "module.h" -int do_bot(User * u); void myBotServHelp(User * u); -class BSBot : public Module -{ - public: - BSBot(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("BOT", do_bot, is_services_admin, -1, -1, -1, BOT_SERVADMIN_HELP_BOT, BOT_SERVADMIN_HELP_BOT); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - - this->SetBotHelp(myBotServHelp); - } -}; - - -/** - * Add the help response to Anopes /bs help output. - * @param u The user who is requesting help - **/ -void myBotServHelp(User * u) -{ - if (is_services_admin(u)) { - notice_lang(s_BotServ, u, BOT_HELP_CMD_BOT); - } -} - -/** - * The /bs bot command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_bot(User * u) +class CommandBSBot : public Command { - BotInfo *bi; - char *cmd = strtok(NULL, " "); - char *ch = NULL; - - if (!cmd) - { - syntax_error(s_BotServ, u, "BOT", BOT_BOT_SYNTAX); - return MOD_CONT; - } - - if (readonly) - { - notice_lang(s_BotServ, u, BOT_BOT_READONLY); - return MOD_CONT; - } - - if (!stricmp(cmd, "ADD")) + private: + CommandReturn DoAdd(User *u, std::vector<std::string> ¶ms) { - char *nick = strtok(NULL, " "); - char *user = strtok(NULL, " "); - char *host = strtok(NULL, " "); - char *real = strtok(NULL, ""); + const char *nick = params[1].c_str(); + const char *user = params[2].c_str(); + const char *host = params[3].c_str(); + const char *real = params[4].c_str(); + const char *ch = NULL; + BotInfo *bi; if (!nick || !user || !host || !real) { - syntax_error(s_BotServ, u, "BOT", BOT_BOT_SYNTAX); + this->OnSyntaxError(u); return MOD_CONT; } @@ -182,18 +133,22 @@ int do_bot(User * u) bi->host, bi->real); send_event(EVENT_BOT_CREATE, 1, bi->nick); + return MOD_CONT; } - else if (!stricmp(cmd, "CHANGE")) + + CommandReturn DoChange(User *u, std::vector<std::string> ¶ms) { - char *oldnick = strtok(NULL, " "); - char *nick = strtok(NULL, " "); - char *user = strtok(NULL, " "); - char *host = strtok(NULL, " "); - char *real = strtok(NULL, ""); + const char *oldnick = params[1].c_str(); + const char *nick = params[2].c_str(); + const char *user = params[3].c_str(); + const char *host = params[4].c_str(); + const char *real = params[5].c_str(); + const char *ch = NULL; + BotInfo *bi; if (!oldnick || !nick) { - syntax_error(s_BotServ, u, "BOT", BOT_BOT_SYNTAX); + this->OnSyntaxError(u); return MOD_CONT; } @@ -351,14 +306,17 @@ int do_bot(User * u) oldnick, bi->nick, bi->user, bi->host, bi->real); send_event(EVENT_BOT_CHANGE, 1, bi->nick); + return MOD_CONT; } - else if (!stricmp(cmd, "DEL")) - { - char *nick = strtok(NULL, " "); + + CommandReturn DoDel(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[1].c_str(); + BotInfo *bi; if (!nick) { - syntax_error(s_BotServ, u, "BOT", BOT_BOT_SYNTAX); + this->OnSyntaxError(u); return MOD_CONT; } @@ -379,12 +337,88 @@ int do_bot(User * u) ircdproto->SendSQLineDel(bi->nick); delete bi; notice_lang(s_BotServ, u, BOT_BOT_DELETED, nick); + return MOD_CONT; } - else + public: + CommandBSBot() : Command("BOT", 1, 5) + { + } + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = strtok(NULL, " "); + + if (!cmd) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + if (readonly) + { + notice_lang(s_BotServ, u, BOT_BOT_READONLY); + return MOD_CONT; + } + + if (!stricmp(cmd, "ADD")) + { + return this->DoAdd(u, params); + } + else if (!stricmp(cmd, "CHANGE")) + { + return this->DoChange(u, params); + } + else if (!stricmp(cmd, "DEL")) + { + return this->DoDel(u, params); + } + else + this->OnSyntaxError(u); + + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_admin(u) && !is_services_root(u)) + return false; + + notice_lang(s_BotServ, u, BOT_SERVADMIN_HELP_BOT); + return true; + } + + void OnSyntaxError(User *u) + { syntax_error(s_BotServ, u, "BOT", BOT_BOT_SYNTAX); + } +}; - return MOD_CONT; +class BSBot : public Module +{ + public: + BSBot(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(BOTSERV, new CommandBSBot(), MOD_UNIQUE); + + this->SetBotHelp(myBotServHelp); + } +}; + + +/** + * Add the help response to Anopes /bs help output. + * @param u The user who is requesting help + **/ +void myBotServHelp(User * u) +{ + if (is_services_admin(u)) { + notice_lang(s_BotServ, u, BOT_HELP_CMD_BOT); + } } + MODULE_INIT("bs_bot", BSBot) diff --git a/src/core/bs_botlist.c b/src/core/bs_botlist.c index e1aac321b..c9f4fc350 100644 --- a/src/core/bs_botlist.c +++ b/src/core/bs_botlist.c @@ -15,21 +15,74 @@ #include "module.h" -int do_botlist(User * u); void myBotServHelp(User * u); +class CommandBSBotList : public Command +{ + public: + CommandBSBotList() : Command("BOTLIST", 0, 0) + { + } + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + int i, count = 0; + BotInfo *bi; + + if (!nbots) { + notice_lang(s_BotServ, u, BOT_BOTLIST_EMPTY); + return MOD_CONT; + } + + for (i = 0; i < 256; i++) { + for (bi = botlists[i]; bi; bi = bi->next) { + if (!(bi->flags & BI_PRIVATE)) { + if (!count) + notice_lang(s_BotServ, u, BOT_BOTLIST_HEADER); + count++; + notice_user(s_BotServ, u, " %-15s (%s@%s)", bi->nick, + bi->user, bi->host); + } + } + } + + if (is_oper(u) && count < nbots) { + notice_lang(s_BotServ, u, BOT_BOTLIST_PRIVATE_HEADER); + + for (i = 0; i < 256; i++) { + for (bi = botlists[i]; bi; bi = bi->next) { + if (bi->flags & BI_PRIVATE) { + notice_user(s_BotServ, u, " %-15s (%s@%s)", + bi->nick, bi->user, bi->host); + count++; + } + } + } + } + + if (!count) + notice_lang(s_BotServ, u, BOT_BOTLIST_EMPTY); + else + notice_lang(s_BotServ, u, BOT_BOTLIST_FOOTER, count); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_BotServ, u, BOT_HELP_BOTLIST); + return true; + } +}; + class BSBotList : public Module { public: BSBotList(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("BOTLIST", do_botlist, NULL, BOT_HELP_BOTLIST, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); + this->AddCommand(BOTSERV, new CommandBSBotList(), MOD_UNIQUE); this->SetBotHelp(myBotServHelp); } @@ -45,52 +98,5 @@ void myBotServHelp(User * u) notice_lang(s_BotServ, u, BOT_HELP_CMD_BOTLIST); } -/** - * The /bs botlist command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_botlist(User * u) -{ - int i, count = 0; - BotInfo *bi; - - if (!nbots) { - notice_lang(s_BotServ, u, BOT_BOTLIST_EMPTY); - return MOD_CONT; - } - - for (i = 0; i < 256; i++) { - for (bi = botlists[i]; bi; bi = bi->next) { - if (!(bi->flags & BI_PRIVATE)) { - if (!count) - notice_lang(s_BotServ, u, BOT_BOTLIST_HEADER); - count++; - notice_user(s_BotServ, u, " %-15s (%s@%s)", bi->nick, - bi->user, bi->host); - } - } - } - - if (is_oper(u) && count < nbots) { - notice_lang(s_BotServ, u, BOT_BOTLIST_PRIVATE_HEADER); - - for (i = 0; i < 256; i++) { - for (bi = botlists[i]; bi; bi = bi->next) { - if (bi->flags & BI_PRIVATE) { - notice_user(s_BotServ, u, " %-15s (%s@%s)", - bi->nick, bi->user, bi->host); - count++; - } - } - } - } - - if (!count) - notice_lang(s_BotServ, u, BOT_BOTLIST_EMPTY); - else - notice_lang(s_BotServ, u, BOT_BOTLIST_FOOTER, count); - return MOD_CONT; -} MODULE_INIT("bs_botlist", BSBotList) diff --git a/src/core/bs_fantasy.c b/src/core/bs_fantasy.c deleted file mode 100644 index 7c6240597..000000000 --- a/src/core/bs_fantasy.c +++ /dev/null @@ -1,79 +0,0 @@ -/* BotServ core fantasy functions - * - * (C) 2003-2009 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * - * $Id$ - * - */ -/*************************************************************************/ - -#include "module.h" - -int do_fantasy(int argc, char **argv); - -class BSFantasy : public Module -{ - public: - BSFantasy(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - EvtHook *hook; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - hook = createEventHook(EVENT_BOT_FANTASY, do_fantasy); - this->AddEventHook(hook); - } -}; - -/** - * Handle all csmodeutils fantasy commands. - * @param argc Argument count - * @param argv Argument list - * @return MOD_CONT or MOD_STOP - **/ -int do_fantasy(int argc, char **argv) -{ - User *u; - ChannelInfo *ci; - CSModeUtil *util = csmodeutils; - char *target; - - if (argc < 3) - return MOD_CONT; - - do { - if (stricmp(argv[0], util->bsname) == 0) { - /* This could have been moved to its own module - however it would require more coding to handle the pass holders - similar to how PROTECT is done - */ - if (!ircd->halfop) { - if (!stricmp(argv[0], "halfop") || !stricmp(argv[0], "dehalfop")) { - return MOD_CONT; - } - } - u = finduser(argv[1]); - ci = cs_findchan(argv[2]); - if (!u || !ci) - return MOD_CONT; - - target = ((argc == 4) ? argv[3] : NULL); - - if (!target && check_access(u, ci, util->levelself)) - bot_raw_mode(u, ci, util->mode, u->nick); - else if (target && check_access(u, ci, util->level)) - bot_raw_mode(u, ci, util->mode, target); - } - } while ((++util)->name != NULL); - - return MOD_CONT; -} - -MODULE_INIT("bs_fantasy", BSFantasy) diff --git a/src/core/bs_fantasy_kick.c b/src/core/bs_fantasy_kick.c deleted file mode 100644 index 3471ac597..000000000 --- a/src/core/bs_fantasy_kick.c +++ /dev/null @@ -1,87 +0,0 @@ -/* BotServ core fantasy functions - * - * (C) 2003-2009 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * - * $Id$ - * - */ -/*************************************************************************/ - -#include "module.h" - -int do_fantasy(int argc, char **argv); - -class BSFantasyKick : public Module -{ - public: - BSFantasyKick(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - EvtHook *hook; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - hook = createEventHook(EVENT_BOT_FANTASY, do_fantasy); - this->AddEventHook(hook); - } -}; - -/** - * Handle kick/k fantasy commands. - * @param argc Argument count - * @param argv Argument list - * @return MOD_CONT or MOD_STOP - **/ -int do_fantasy(int argc, char **argv) -{ - User *u, *u2; - ChannelInfo *ci; - char *target = NULL; - char *reason = NULL; - - if (argc < 3) - return MOD_CONT; - - if ((stricmp(argv[0], "kick") == 0) || (stricmp(argv[0], "k") == 0)) { - u = finduser(argv[1]); - ci = cs_findchan(argv[2]); - if (!u || !ci) - return MOD_CONT; - - if (argc >= 4) { - target = myStrGetToken(argv[3], ' ', 0); - reason = myStrGetTokenRemainder(argv[3], ' ', 1); - } - if (!target && check_access(u, ci, CA_KICKME)) { - bot_raw_kick(u, ci, u->nick, "Requested"); - } else if (target && check_access(u, ci, CA_KICK)) { - if (!stricmp(target, ci->bi->nick)) - bot_raw_kick(u, ci, u->nick, "Oops!"); - else { - u2 = finduser(target); - if (u2 && ci->c && is_on_chan(ci->c, u2)) { - if (!reason && !is_protected(u2)) - bot_raw_kick(u, ci, target, "Requested"); - else if (!is_protected(u2)) - bot_raw_kick(u, ci, target, reason); - } - } - } - } - - if (target) - delete [] target; - if (reason) - delete [] reason; - - return MOD_CONT; -} - -MODULE_INIT("bs_fantasy_kick", BSFantasyKick) diff --git a/src/core/bs_fantasy_kickban.c b/src/core/bs_fantasy_kickban.c deleted file mode 100644 index 3b3eb20ce..000000000 --- a/src/core/bs_fantasy_kickban.c +++ /dev/null @@ -1,89 +0,0 @@ -/* BotServ core fantasy functions - * - * (C) 2003-2009 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * - * $Id$ - * - */ -/*************************************************************************/ - -#include "module.h" - -int do_fantasy(int argc, char **argv); - -class BSFantasyKickBan : public Module -{ - public: - BSFantasyKickBan(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - EvtHook *hook; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - hook = createEventHook(EVENT_BOT_FANTASY, do_fantasy); - this->AddEventHook(hook); - } -}; - - -/** - * Handle kickban/kb fantasy commands. - * @param argc Argument count - * @param argv Argument list - * @return MOD_CONT or MOD_STOP - **/ -int do_fantasy(int argc, char **argv) -{ - User *u, *u2; - ChannelInfo *ci; - char *target = NULL; - char *reason = NULL; - - if (argc < 3) - return MOD_CONT; - - if ((stricmp(argv[0], "kickban") == 0) - || (stricmp(argv[0], "kb") == 0)) { - u = finduser(argv[1]); - ci = cs_findchan(argv[2]); - if (!u || !ci) - return MOD_CONT; - - if (argc >= 4) { - target = myStrGetToken(argv[3], ' ', 0); - reason = myStrGetTokenRemainder(argv[3], ' ', 1); - } - if (!target && check_access(u, ci, CA_BANME)) { - bot_raw_ban(u, ci, u->nick, "Requested"); - } else if (target && check_access(u, ci, CA_BAN)) { - if (stricmp(target, ci->bi->nick) == 0) { - bot_raw_ban(u, ci, u->nick, "Oops!"); - } else { - u2 = finduser(target); - if (u2 && ci->c && is_on_chan(ci->c, u2)) { - if (!reason && !is_protected(u2)) - bot_raw_ban(u, ci, target, "Requested"); - else if (!is_protected(u2)) - bot_raw_ban(u, ci, target, reason); - } - } - } - } - - if (target) - delete [] target; - if (reason) - delete [] reason; - - return MOD_CONT; -} - -MODULE_INIT("bs_fantasy_kickban", BSFantasyKickBan) diff --git a/src/core/bs_fantasy_owner.c b/src/core/bs_fantasy_owner.c deleted file mode 100644 index f0155592d..000000000 --- a/src/core/bs_fantasy_owner.c +++ /dev/null @@ -1,78 +0,0 @@ -/* BotServ core fantasy functions - * - * (C) 2003-2009 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * - * $Id$ - * - */ -/*************************************************************************/ - -#include "module.h" - -int do_fantasy(int argc, char **argv); - -class BSFantasyOwner : public Module -{ - public: - BSFantasyOwner(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - EvtHook *hook; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - /* No need to load of we don't support owner */ - if (!ircd->owner) - { - throw ModuleException("Your ircd doesn't support the owner channelmode; bs_fantasy_owner won't be loaded"); - } - - hook = createEventHook(EVENT_BOT_FANTASY, do_fantasy); - this->AddEventHook(hook); - } -}; - - -/** - * Handle owner/deowner fantasy commands. - * @param argc Argument count - * @param argv Argument list - * @return MOD_CONT or MOD_STOP - **/ -int do_fantasy(int argc, char **argv) -{ - User *u; - ChannelInfo *ci; - - if (argc < 3) - return MOD_CONT; - - if (stricmp(argv[0], "deowner") == 0) { - u = finduser(argv[1]); - ci = cs_findchan(argv[2]); - if (!u || !ci) - return MOD_CONT; - - if (is_founder(u, ci)) - bot_raw_mode(u, ci, ircd->ownerunset, u->nick); - } else if (stricmp(argv[0], "owner") == 0) { - u = finduser(argv[1]); - ci = cs_findchan(argv[2]); - if (!u || !ci) - return MOD_CONT; - - if (is_founder(u, ci)) - bot_raw_mode(u, ci, ircd->ownerset, u->nick); - } - - return MOD_CONT; -} - -MODULE_INIT("bs_fantasy_owner", BSFantasyOwner) diff --git a/src/core/bs_fantasy_seen.c b/src/core/bs_fantasy_seen.c deleted file mode 100644 index 5ef7b914e..000000000 --- a/src/core/bs_fantasy_seen.c +++ /dev/null @@ -1,128 +0,0 @@ -/* BotServ core fantasy functions - * - * (C) 2003-2009 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * - * $Id$ - * - */ -/*************************************************************************/ - -#include "module.h" - -int do_fantasy(int argc, char **argv); - -class BSFantasySeen : public Module -{ - public: - BSFantasySeen(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - EvtHook *hook; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - hook = createEventHook(EVENT_BOT_FANTASY, do_fantasy); - this->AddEventHook(hook); - } -}; - -/** - * Handle seen fantasy command. - * @param argc Argument count - * @param argv Argument list - * @return MOD_CONT or MOD_STOP - **/ -int do_fantasy(int argc, char **argv) -{ - User *u; - ChannelInfo *ci; - User *u2; - NickAlias *na; - ChanAccess *access; - char buf[BUFSIZE]; - char *target = NULL; - - if (argc < 4) - return MOD_CONT; - - if (stricmp(argv[0], "seen") == 0) { - u = finduser(argv[1]); - ci = cs_findchan(argv[2]); - if (!u || !ci) - return MOD_CONT; - - target = myStrGetToken(argv[3], ' ', 0); - - if (stricmp(ci->bi->nick, target) == 0) { - /* If we look for the bot */ - snprintf(buf, sizeof(buf), getstring(u->na, BOT_SEEN_BOT), - u->nick); - ircdproto->SendPrivmsg(ci->bi, ci->name, "%s", buf); - } else if (!(na = findnick(target)) || (na->status & NS_VERBOTEN)) { - /* If the nick is not registered or forbidden */ - snprintf(buf, sizeof(buf), getstring(u->na, BOT_SEEN_UNKNOWN), - target); - ircdproto->SendPrivmsg(ci->bi, ci->name, "%s", buf); - } else if ((u2 = nc_on_chan(ci->c, na->nc))) { - /* If the nick we're looking for is on the channel, - * there are three possibilities: it's yourself, - * it's the nick we look for, it's an alias of the - * nick we look for. - */ - if (u == u2 || (u->na && u->na->nc == na->nc)) - snprintf(buf, sizeof(buf), getstring(u->na, BOT_SEEN_YOU), - u->nick); - else if (!stricmp(u2->nick, target)) - snprintf(buf, sizeof(buf), - getstring(u->na, BOT_SEEN_ON_CHANNEL), u2->nick); - else - snprintf(buf, sizeof(buf), - getstring(u->na, BOT_SEEN_ON_CHANNEL_AS), target, - u2->nick); - - ircdproto->SendPrivmsg(ci->bi, ci->name, "%s", buf); - } else if ((access = get_access_entry(na->nc, ci))) { - /* User is on the access list but not present actually. - Special case: if access->last_seen is 0 it's that we - never seen the user. - */ - if (access->last_seen) { - char durastr[192]; - duration(u->na, durastr, sizeof(durastr), - time(NULL) - access->last_seen); - snprintf(buf, sizeof(buf), getstring(u->na, BOT_SEEN_ON), - target, durastr); - } else { - snprintf(buf, sizeof(buf), - getstring(u->na, BOT_SEEN_NEVER), target); - } - ircdproto->SendPrivmsg(ci->bi, ci->name, "%s", buf); - } else if (na->nc == ci->founder) { - /* User is the founder of the channel */ - char durastr[192]; - duration(u->na, durastr, sizeof(durastr), - time(NULL) - na->last_seen); - snprintf(buf, sizeof(buf), getstring(u->na, BOT_SEEN_ON), - target, durastr); - ircdproto->SendPrivmsg(ci->bi, ci->name, "%s", buf); - } else { - /* All other cases */ - snprintf(buf, sizeof(buf), getstring(u->na, BOT_SEEN_UNKNOWN), - target); - ircdproto->SendPrivmsg(ci->bi, ci->name, "%s", buf); - } - /* free myStrGetToken(ed) variable target (#851) */ - if (target) delete [] target; - } - - return MOD_CONT; -} - -MODULE_INIT("bs_fantasy_seen", BSFantasySeen) diff --git a/src/core/bs_help.c b/src/core/bs_help.c index cd73ee093..480dd62f7 100644 --- a/src/core/bs_help.c +++ b/src/core/bs_help.c @@ -15,41 +15,39 @@ #include "module.h" -int do_help(User * u); +class CommandBSHelp : public Command +{ + public: + CommandBSHelp() : Command("HELP", 1, 1) + { + } + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + mod_help_cmd(s_BotServ, u, BOTSERV, params[0].c_str()); + return MOD_CONT; + } + + void OnSyntaxError(User *u) + { + notice_help(s_BotServ, u, BOT_HELP); + moduleDisplayHelp(4, u); + notice_help(s_BotServ, u, BOT_HELP_FOOTER, BSMinUsers); + } +}; class BSHelp : public Module { public: BSHelp(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("HELP", do_help, NULL, -1, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); + this->AddCommand(BOTSERV, new CommandBSHelp(), MOD_UNIQUE); } }; -/** - * The /bs help command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_help(User * u) -{ - char *cmd = strtok(NULL, ""); - - if (!cmd) { - notice_help(s_BotServ, u, BOT_HELP); - moduleDisplayHelp(4, u); - notice_help(s_BotServ, u, BOT_HELP_FOOTER, BSMinUsers); - } else { - mod_help_cmd(s_BotServ, u, BOTSERV, cmd); - } - return MOD_CONT; -} MODULE_INIT("bs_help", BSHelp) diff --git a/src/core/bs_info.c b/src/core/bs_info.c index 985ff6dd3..c6acd204d 100644 --- a/src/core/bs_info.c +++ b/src/core/bs_info.c @@ -15,255 +15,262 @@ #include "module.h" -int do_info(User * u); -void send_bot_channels(User * u, BotInfo * bi); void myBotServHelp(User * u); -class BSInfo : public Module +class CommandBSInfo : public Command { - public: - BSInfo(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + void send_bot_channels(User * u, BotInfo * bi) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - c = createCommand("INFO", do_info, NULL, BOT_HELP_INFO, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - - this->SetBotHelp(myBotServHelp); - } -}; + int i; + ChannelInfo *ci; + char buf[307], *end; + *buf = 0; + end = buf; -/** - * Add the help response to Anopes /bs help output. - * @param u The user who is requesting help - **/ -void myBotServHelp(User * u) -{ - notice_lang(s_BotServ, u, BOT_HELP_CMD_INFO); -} + for (i = 0; i < 256; i++) { + for (ci = chanlists[i]; ci; ci = ci->next) { + if (ci->bi == bi) { + if (strlen(buf) + strlen(ci->name) > 300) { + notice_user(s_BotServ, u, "%s", buf); + *buf = 0; + end = buf; + } + end += + snprintf(end, sizeof(buf) - (end - buf), " %s ", + ci->name); + } + } + } -/** - * The /bs info command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_info(User * u) -{ - BotInfo *bi; - ChannelInfo *ci; - char *query = strtok(NULL, " "); + if (*buf) + notice_user(s_BotServ, u, "%s", buf); + return; + } + public: + CommandBSInfo() : Command("INFO", 1, 1) + { + } - int need_comma = 0, is_servadmin = is_services_admin(u); - char buf[BUFSIZE], *end; - const char *commastr = getstring(u->na, COMMA_SPACE); + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + BotInfo *bi; + ChannelInfo *ci; + char *query = strtok(NULL, " "); - if (!query) - syntax_error(s_BotServ, u, "INFO", BOT_INFO_SYNTAX); - else if ((bi = findbot(query))) { - struct tm *tm; + int need_comma = 0, is_servadmin = is_services_admin(u); + char buf[BUFSIZE], *end; + const char *commastr = getstring(u->na, COMMA_SPACE); - notice_lang(s_BotServ, u, BOT_INFO_BOT_HEADER, bi->nick); - notice_lang(s_BotServ, u, BOT_INFO_BOT_MASK, bi->user, bi->host); - notice_lang(s_BotServ, u, BOT_INFO_BOT_REALNAME, bi->real); - tm = localtime(&bi->created); - strftime_lang(buf, sizeof(buf), u, STRFTIME_DATE_TIME_FORMAT, tm); - notice_lang(s_BotServ, u, BOT_INFO_BOT_CREATED, buf); - notice_lang(s_BotServ, u, BOT_INFO_BOT_OPTIONS, - getstring(u->na, - (bi-> - flags & BI_PRIVATE) ? BOT_INFO_OPT_PRIVATE : - BOT_INFO_OPT_NONE)); - notice_lang(s_BotServ, u, BOT_INFO_BOT_USAGE, bi->chancount); + if ((bi = findbot(query))) { + struct tm *tm; - if (is_services_admin(u)) - send_bot_channels(u, bi); - } else if ((ci = cs_findchan(query))) { - if (!is_servadmin && !is_founder(u, ci)) { - notice_lang(s_BotServ, u, PERMISSION_DENIED); - return MOD_CONT; - } - if (ci->flags & CI_VERBOTEN) { - notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, query); - return MOD_CONT; - } + notice_lang(s_BotServ, u, BOT_INFO_BOT_HEADER, bi->nick); + notice_lang(s_BotServ, u, BOT_INFO_BOT_MASK, bi->user, bi->host); + notice_lang(s_BotServ, u, BOT_INFO_BOT_REALNAME, bi->real); + tm = localtime(&bi->created); + strftime_lang(buf, sizeof(buf), u, STRFTIME_DATE_TIME_FORMAT, tm); + notice_lang(s_BotServ, u, BOT_INFO_BOT_CREATED, buf); + notice_lang(s_BotServ, u, BOT_INFO_BOT_OPTIONS, + getstring(u->na, + (bi-> + flags & BI_PRIVATE) ? BOT_INFO_OPT_PRIVATE : + BOT_INFO_OPT_NONE)); + notice_lang(s_BotServ, u, BOT_INFO_BOT_USAGE, bi->chancount); - notice_lang(s_BotServ, u, BOT_INFO_CHAN_HEADER, ci->name); - if (ci->bi) - notice_lang(s_BotServ, u, BOT_INFO_CHAN_BOT, ci->bi->nick); - else - notice_lang(s_BotServ, u, BOT_INFO_CHAN_BOT_NONE); + if (is_services_admin(u)) + this->send_bot_channels(u, bi); + } else if ((ci = cs_findchan(query))) { + if (!is_servadmin && !is_founder(u, ci)) { + notice_lang(s_BotServ, u, PERMISSION_DENIED); + return MOD_CONT; + } + if (ci->flags & CI_VERBOTEN) { + notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, query); + return MOD_CONT; + } - if (ci->botflags & BS_KICK_BADWORDS) { - if (ci->ttb[TTB_BADWORDS]) - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_BADWORDS_BAN, - getstring(u->na, BOT_INFO_ACTIVE), - ci->ttb[TTB_BADWORDS]); + notice_lang(s_BotServ, u, BOT_INFO_CHAN_HEADER, ci->name); + if (ci->bi) + notice_lang(s_BotServ, u, BOT_INFO_CHAN_BOT, ci->bi->nick); else + notice_lang(s_BotServ, u, BOT_INFO_CHAN_BOT_NONE); + + if (ci->botflags & BS_KICK_BADWORDS) { + if (ci->ttb[TTB_BADWORDS]) + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_BADWORDS_BAN, + getstring(u->na, BOT_INFO_ACTIVE), + ci->ttb[TTB_BADWORDS]); + else + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_BADWORDS, + getstring(u->na, BOT_INFO_ACTIVE)); + } else notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_BADWORDS, - getstring(u->na, BOT_INFO_ACTIVE)); - } else - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_BADWORDS, - getstring(u->na, BOT_INFO_INACTIVE)); - if (ci->botflags & BS_KICK_BOLDS) { - if (ci->ttb[TTB_BOLDS]) - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_BOLDS_BAN, - getstring(u->na, BOT_INFO_ACTIVE), - ci->ttb[TTB_BOLDS]); - else + getstring(u->na, BOT_INFO_INACTIVE)); + if (ci->botflags & BS_KICK_BOLDS) { + if (ci->ttb[TTB_BOLDS]) + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_BOLDS_BAN, + getstring(u->na, BOT_INFO_ACTIVE), + ci->ttb[TTB_BOLDS]); + else + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_BOLDS, + getstring(u->na, BOT_INFO_ACTIVE)); + } else notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_BOLDS, - getstring(u->na, BOT_INFO_ACTIVE)); - } else - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_BOLDS, - getstring(u->na, BOT_INFO_INACTIVE)); - if (ci->botflags & BS_KICK_CAPS) { - if (ci->ttb[TTB_CAPS]) - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_CAPS_BAN, - getstring(u->na, BOT_INFO_ACTIVE), - ci->ttb[TTB_CAPS], ci->capsmin, - ci->capspercent); - else - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_CAPS_ON, - getstring(u->na, BOT_INFO_ACTIVE), ci->capsmin, - ci->capspercent); - } else - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_CAPS_OFF, - getstring(u->na, BOT_INFO_INACTIVE)); - if (ci->botflags & BS_KICK_COLORS) { - if (ci->ttb[TTB_COLORS]) - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_COLORS_BAN, - getstring(u->na, BOT_INFO_ACTIVE), - ci->ttb[TTB_COLORS]); - else + getstring(u->na, BOT_INFO_INACTIVE)); + if (ci->botflags & BS_KICK_CAPS) { + if (ci->ttb[TTB_CAPS]) + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_CAPS_BAN, + getstring(u->na, BOT_INFO_ACTIVE), + ci->ttb[TTB_CAPS], ci->capsmin, + ci->capspercent); + else + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_CAPS_ON, + getstring(u->na, BOT_INFO_ACTIVE), ci->capsmin, + ci->capspercent); + } else + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_CAPS_OFF, + getstring(u->na, BOT_INFO_INACTIVE)); + if (ci->botflags & BS_KICK_COLORS) { + if (ci->ttb[TTB_COLORS]) + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_COLORS_BAN, + getstring(u->na, BOT_INFO_ACTIVE), + ci->ttb[TTB_COLORS]); + else + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_COLORS, + getstring(u->na, BOT_INFO_ACTIVE)); + } else notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_COLORS, - getstring(u->na, BOT_INFO_ACTIVE)); - } else - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_COLORS, - getstring(u->na, BOT_INFO_INACTIVE)); - if (ci->botflags & BS_KICK_FLOOD) { - if (ci->ttb[TTB_FLOOD]) - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_FLOOD_BAN, - getstring(u->na, BOT_INFO_ACTIVE), - ci->ttb[TTB_FLOOD], ci->floodlines, - ci->floodsecs); - else - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_FLOOD_ON, - getstring(u->na, BOT_INFO_ACTIVE), - ci->floodlines, ci->floodsecs); - } else - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_FLOOD_OFF, - getstring(u->na, BOT_INFO_INACTIVE)); - if (ci->botflags & BS_KICK_REPEAT) { - if (ci->ttb[TTB_REPEAT]) - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_REPEAT_BAN, - getstring(u->na, BOT_INFO_ACTIVE), - ci->ttb[TTB_REPEAT], ci->repeattimes); - else - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_REPEAT_ON, - getstring(u->na, BOT_INFO_ACTIVE), - ci->repeattimes); - } else - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_REPEAT_OFF, - getstring(u->na, BOT_INFO_INACTIVE)); - if (ci->botflags & BS_KICK_REVERSES) { - if (ci->ttb[TTB_REVERSES]) - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_REVERSES_BAN, - getstring(u->na, BOT_INFO_ACTIVE), - ci->ttb[TTB_REVERSES]); - else + getstring(u->na, BOT_INFO_INACTIVE)); + if (ci->botflags & BS_KICK_FLOOD) { + if (ci->ttb[TTB_FLOOD]) + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_FLOOD_BAN, + getstring(u->na, BOT_INFO_ACTIVE), + ci->ttb[TTB_FLOOD], ci->floodlines, + ci->floodsecs); + else + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_FLOOD_ON, + getstring(u->na, BOT_INFO_ACTIVE), + ci->floodlines, ci->floodsecs); + } else + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_FLOOD_OFF, + getstring(u->na, BOT_INFO_INACTIVE)); + if (ci->botflags & BS_KICK_REPEAT) { + if (ci->ttb[TTB_REPEAT]) + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_REPEAT_BAN, + getstring(u->na, BOT_INFO_ACTIVE), + ci->ttb[TTB_REPEAT], ci->repeattimes); + else + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_REPEAT_ON, + getstring(u->na, BOT_INFO_ACTIVE), + ci->repeattimes); + } else + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_REPEAT_OFF, + getstring(u->na, BOT_INFO_INACTIVE)); + if (ci->botflags & BS_KICK_REVERSES) { + if (ci->ttb[TTB_REVERSES]) + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_REVERSES_BAN, + getstring(u->na, BOT_INFO_ACTIVE), + ci->ttb[TTB_REVERSES]); + else + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_REVERSES, + getstring(u->na, BOT_INFO_ACTIVE)); + } else notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_REVERSES, - getstring(u->na, BOT_INFO_ACTIVE)); - } else - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_REVERSES, - getstring(u->na, BOT_INFO_INACTIVE)); - if (ci->botflags & BS_KICK_UNDERLINES) { - if (ci->ttb[TTB_UNDERLINES]) - notice_lang(s_BotServ, u, - BOT_INFO_CHAN_KICK_UNDERLINES_BAN, - getstring(u->na, BOT_INFO_ACTIVE), - ci->ttb[TTB_UNDERLINES]); - else + getstring(u->na, BOT_INFO_INACTIVE)); + if (ci->botflags & BS_KICK_UNDERLINES) { + if (ci->ttb[TTB_UNDERLINES]) + notice_lang(s_BotServ, u, + BOT_INFO_CHAN_KICK_UNDERLINES_BAN, + getstring(u->na, BOT_INFO_ACTIVE), + ci->ttb[TTB_UNDERLINES]); + else + notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_UNDERLINES, + getstring(u->na, BOT_INFO_ACTIVE)); + } else notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_UNDERLINES, - getstring(u->na, BOT_INFO_ACTIVE)); + getstring(u->na, BOT_INFO_INACTIVE)); + + end = buf; + *end = 0; + if (ci->botflags & BS_DONTKICKOPS) { + end += snprintf(end, sizeof(buf) - (end - buf), "%s", + getstring(u->na, BOT_INFO_OPT_DONTKICKOPS)); + need_comma = 1; + } + if (ci->botflags & BS_DONTKICKVOICES) { + end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", + need_comma ? commastr : "", + getstring(u->na, BOT_INFO_OPT_DONTKICKVOICES)); + need_comma = 1; + } + if (ci->botflags & BS_FANTASY) { + end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", + need_comma ? commastr : "", + getstring(u->na, BOT_INFO_OPT_FANTASY)); + need_comma = 1; + } + if (ci->botflags & BS_GREET) { + end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", + need_comma ? commastr : "", + getstring(u->na, BOT_INFO_OPT_GREET)); + need_comma = 1; + } + if (ci->botflags & BS_NOBOT) { + end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", + need_comma ? commastr : "", + getstring(u->na, BOT_INFO_OPT_NOBOT)); + need_comma = 1; + } + if (ci->botflags & BS_SYMBIOSIS) { + end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", + need_comma ? commastr : "", + getstring(u->na, BOT_INFO_OPT_SYMBIOSIS)); + need_comma = 1; + } + notice_lang(s_BotServ, u, BOT_INFO_CHAN_OPTIONS, + *buf ? buf : getstring(u->na, BOT_INFO_OPT_NONE)); + } else - notice_lang(s_BotServ, u, BOT_INFO_CHAN_KICK_UNDERLINES, - getstring(u->na, BOT_INFO_INACTIVE)); + notice_lang(s_BotServ, u, BOT_INFO_NOT_FOUND, query); + return MOD_CONT; + } - end = buf; - *end = 0; - if (ci->botflags & BS_DONTKICKOPS) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s", - getstring(u->na, BOT_INFO_OPT_DONTKICKOPS)); - need_comma = 1; - } - if (ci->botflags & BS_DONTKICKVOICES) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, BOT_INFO_OPT_DONTKICKVOICES)); - need_comma = 1; - } - if (ci->botflags & BS_FANTASY) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, BOT_INFO_OPT_FANTASY)); - need_comma = 1; - } - if (ci->botflags & BS_GREET) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, BOT_INFO_OPT_GREET)); - need_comma = 1; - } - if (ci->botflags & BS_NOBOT) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, BOT_INFO_OPT_NOBOT)); - need_comma = 1; - } - if (ci->botflags & BS_SYMBIOSIS) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, BOT_INFO_OPT_SYMBIOSIS)); - need_comma = 1; - } - notice_lang(s_BotServ, u, BOT_INFO_CHAN_OPTIONS, - *buf ? buf : getstring(u->na, BOT_INFO_OPT_NONE)); + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_BotServ, u, BOT_HELP_INFO); + return true; + } - } else - notice_lang(s_BotServ, u, BOT_INFO_NOT_FOUND, query); - return MOD_CONT; -} + void OnSyntaxError(User *u) + { + syntax_error(s_BotServ, u, "INFO", BOT_INFO_SYNTAX); + } +}; -void send_bot_channels(User * u, BotInfo * bi) +class BSInfo : public Module { - int i; - ChannelInfo *ci; - char buf[307], *end; - - *buf = 0; - end = buf; + public: + BSInfo(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(BOTSERV, new CommandBSInfo(), MOD_UNIQUE); - for (i = 0; i < 256; i++) { - for (ci = chanlists[i]; ci; ci = ci->next) { - if (ci->bi == bi) { - if (strlen(buf) + strlen(ci->name) > 300) { - notice_user(s_BotServ, u, "%s", buf); - *buf = 0; - end = buf; - } - end += - snprintf(end, sizeof(buf) - (end - buf), " %s ", - ci->name); - } - } + this->SetBotHelp(myBotServHelp); } +}; - if (*buf) - notice_user(s_BotServ, u, "%s", buf); - return; + +/** + * Add the help response to Anopes /bs help output. + * @param u The user who is requesting help + **/ +void myBotServHelp(User * u) +{ + notice_lang(s_BotServ, u, BOT_HELP_CMD_INFO); } MODULE_INIT("bs_info", BSInfo) diff --git a/src/core/bs_kick.c b/src/core/bs_kick.c index 1df4ab44f..8d5688375 100644 --- a/src/core/bs_kick.c +++ b/src/core/bs_kick.c @@ -18,341 +18,345 @@ int do_kickcmd(User * u); void myBotServHelp(User * u); - -class BSKick : public Module +class CommandBSKick : public Command { public: - BSKick(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandBSKick() : Command("KICK", 3, 4) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - c = createCommand("KICK", do_kickcmd, NULL, BOT_HELP_KICK, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("KICK BADWORDS", NULL, NULL, BOT_HELP_KICK_BADWORDS, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("KICK BOLDS", NULL, NULL, BOT_HELP_KICK_BOLDS, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("KICK CAPS", NULL, NULL, BOT_HELP_KICK_CAPS, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("KICK COLORS", NULL, NULL, BOT_HELP_KICK_COLORS, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("KICK FLOOD", NULL, NULL, BOT_HELP_KICK_FLOOD, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("KICK REPEAT", NULL, NULL, BOT_HELP_KICK_REPEAT, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("KICK REVERSES", NULL, NULL, BOT_HELP_KICK_REVERSES, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("KICK UNDERLINES", NULL, NULL, BOT_HELP_KICK_UNDERLINES, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - - this->SetBotHelp(myBotServHelp); } -}; - - -/** - * Add the help response to Anopes /bs help output. - * @param u The user who is requesting help - **/ -void myBotServHelp(User * u) -{ - notice_lang(s_BotServ, u, BOT_HELP_CMD_KICK); -} -/** - * The /bs kick command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_kickcmd(User * u) -{ - char *chan = strtok(NULL, " "); - char *option = strtok(NULL, " "); - char *value = strtok(NULL, " "); - char *ttb = strtok(NULL, " "); + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + const char *option = params[1].c_str(); + const char *value = params[2].c_str(); + const char *ttb = params[3].c_str(); - ChannelInfo *ci; + ChannelInfo *ci; - if (readonly) - notice_lang(s_BotServ, u, BOT_KICK_DISABLED); - else if (!chan || !option || !value) - syntax_error(s_BotServ, u, "KICK", BOT_KICK_SYNTAX); - else if (stricmp(value, "ON") && stricmp(value, "OFF")) - syntax_error(s_BotServ, u, "KICK", BOT_KICK_SYNTAX); - else if (!(ci = cs_findchan(chan))) - notice_lang(s_BotServ, u, CHAN_X_NOT_REGISTERED, chan); - else if (ci->flags & CI_VERBOTEN) - notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, chan); - else if (!is_services_admin(u) && !check_access(u, ci, CA_SET)) - notice_lang(s_BotServ, u, ACCESS_DENIED); - else if (!ci->bi) - notice_help(s_BotServ, u, BOT_NOT_ASSIGNED); - else { - if (!stricmp(option, "BADWORDS")) { - if (!stricmp(value, "ON")) { - if (ttb) { - ci->ttb[TTB_BADWORDS] = - strtol(ttb, NULL, 10); - /* Only error if errno returns ERANGE or EINVAL or we are less then 0 - TSL */ - if (errno == ERANGE || errno == EINVAL - || ci->ttb[TTB_BADWORDS] < 0) { - /* leaving the debug behind since we might want to know what these are */ - if (debug) { - alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_BADWORDS]); + if (readonly) + notice_lang(s_BotServ, u, BOT_KICK_DISABLED); + else if (!chan || !option || !value) + syntax_error(s_BotServ, u, "KICK", BOT_KICK_SYNTAX); + else if (stricmp(value, "ON") && stricmp(value, "OFF")) + syntax_error(s_BotServ, u, "KICK", BOT_KICK_SYNTAX); + else if (!(ci = cs_findchan(chan))) + notice_lang(s_BotServ, u, CHAN_X_NOT_REGISTERED, chan); + else if (ci->flags & CI_VERBOTEN) + notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, chan); + else if (!is_services_admin(u) && !check_access(u, ci, CA_SET)) + notice_lang(s_BotServ, u, ACCESS_DENIED); + else if (!ci->bi) + notice_help(s_BotServ, u, BOT_NOT_ASSIGNED); + else { + if (!stricmp(option, "BADWORDS")) { + if (!stricmp(value, "ON")) { + if (ttb) { + ci->ttb[TTB_BADWORDS] = + strtol(ttb, NULL, 10); + /* Only error if errno returns ERANGE or EINVAL or we are less then 0 - TSL */ + if (errno == ERANGE || errno == EINVAL + || ci->ttb[TTB_BADWORDS] < 0) { + /* leaving the debug behind since we might want to know what these are */ + if (debug) { + alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_BADWORDS]); + } + /* reset the value back to 0 - TSL */ + ci->ttb[TTB_BADWORDS] = 0; + notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); + return MOD_CONT; } - /* reset the value back to 0 - TSL */ + } else { ci->ttb[TTB_BADWORDS] = 0; - notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); - return MOD_CONT; } + ci->botflags |= BS_KICK_BADWORDS; + if (ci->ttb[TTB_BADWORDS]) + notice_lang(s_BotServ, u, BOT_KICK_BADWORDS_ON_BAN, + ci->ttb[TTB_BADWORDS]); + else + notice_lang(s_BotServ, u, BOT_KICK_BADWORDS_ON); } else { - ci->ttb[TTB_BADWORDS] = 0; + ci->botflags &= ~BS_KICK_BADWORDS; + notice_lang(s_BotServ, u, BOT_KICK_BADWORDS_OFF); } - ci->botflags |= BS_KICK_BADWORDS; - if (ci->ttb[TTB_BADWORDS]) - notice_lang(s_BotServ, u, BOT_KICK_BADWORDS_ON_BAN, - ci->ttb[TTB_BADWORDS]); - else - notice_lang(s_BotServ, u, BOT_KICK_BADWORDS_ON); - } else { - ci->botflags &= ~BS_KICK_BADWORDS; - notice_lang(s_BotServ, u, BOT_KICK_BADWORDS_OFF); - } - } else if (!stricmp(option, "BOLDS")) { - if (!stricmp(value, "ON")) { - if (ttb) { - ci->ttb[TTB_BOLDS] = strtol(ttb, NULL, 10); - if (errno == ERANGE || errno == EINVAL - || ci->ttb[TTB_BOLDS] < 0) { - if (debug) { - alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_BOLDS]); + } else if (!stricmp(option, "BOLDS")) { + if (!stricmp(value, "ON")) { + if (ttb) { + ci->ttb[TTB_BOLDS] = strtol(ttb, NULL, 10); + if (errno == ERANGE || errno == EINVAL + || ci->ttb[TTB_BOLDS] < 0) { + if (debug) { + alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_BOLDS]); + } + ci->ttb[TTB_BOLDS] = 0; + notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); + return MOD_CONT; } + } else ci->ttb[TTB_BOLDS] = 0; - notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); - return MOD_CONT; - } - } else - ci->ttb[TTB_BOLDS] = 0; - ci->botflags |= BS_KICK_BOLDS; - if (ci->ttb[TTB_BOLDS]) - notice_lang(s_BotServ, u, BOT_KICK_BOLDS_ON_BAN, - ci->ttb[TTB_BOLDS]); - else - notice_lang(s_BotServ, u, BOT_KICK_BOLDS_ON); - } else { - ci->botflags &= ~BS_KICK_BOLDS; - notice_lang(s_BotServ, u, BOT_KICK_BOLDS_OFF); - } - } else if (!stricmp(option, "CAPS")) { - if (!stricmp(value, "ON")) { - char *min = strtok(NULL, " "); - char *percent = strtok(NULL, " "); + ci->botflags |= BS_KICK_BOLDS; + if (ci->ttb[TTB_BOLDS]) + notice_lang(s_BotServ, u, BOT_KICK_BOLDS_ON_BAN, + ci->ttb[TTB_BOLDS]); + else + notice_lang(s_BotServ, u, BOT_KICK_BOLDS_ON); + } else { + ci->botflags &= ~BS_KICK_BOLDS; + notice_lang(s_BotServ, u, BOT_KICK_BOLDS_OFF); + } + } else if (!stricmp(option, "CAPS")) { + if (!stricmp(value, "ON")) { + char *min = strtok(NULL, " "); + char *percent = strtok(NULL, " "); - if (ttb) { - ci->ttb[TTB_CAPS] = strtol(ttb, NULL, 10); - if (errno == ERANGE || errno == EINVAL - || ci->ttb[TTB_CAPS] < 0) { - if (debug) { - alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_CAPS]); + if (ttb) { + ci->ttb[TTB_CAPS] = strtol(ttb, NULL, 10); + if (errno == ERANGE || errno == EINVAL + || ci->ttb[TTB_CAPS] < 0) { + if (debug) { + alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_CAPS]); + } + ci->ttb[TTB_CAPS] = 0; + notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); + return MOD_CONT; } + } else ci->ttb[TTB_CAPS] = 0; - notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); - return MOD_CONT; - } - } else - ci->ttb[TTB_CAPS] = 0; - if (!min) - ci->capsmin = 10; - else - ci->capsmin = atol(min); - if (ci->capsmin < 1) - ci->capsmin = 10; + if (!min) + ci->capsmin = 10; + else + ci->capsmin = atol(min); + if (ci->capsmin < 1) + ci->capsmin = 10; - if (!percent) - ci->capspercent = 25; - else - ci->capspercent = atol(percent); - if (ci->capspercent < 1 || ci->capspercent > 100) - ci->capspercent = 25; + if (!percent) + ci->capspercent = 25; + else + ci->capspercent = atol(percent); + if (ci->capspercent < 1 || ci->capspercent > 100) + ci->capspercent = 25; - ci->botflags |= BS_KICK_CAPS; - if (ci->ttb[TTB_CAPS]) - notice_lang(s_BotServ, u, BOT_KICK_CAPS_ON_BAN, - ci->capsmin, ci->capspercent, - ci->ttb[TTB_CAPS]); - else - notice_lang(s_BotServ, u, BOT_KICK_CAPS_ON, - ci->capsmin, ci->capspercent); - } else { - ci->botflags &= ~BS_KICK_CAPS; - notice_lang(s_BotServ, u, BOT_KICK_CAPS_OFF); - } - } else if (!stricmp(option, "COLORS")) { - if (!stricmp(value, "ON")) { - if (ttb) { - ci->ttb[TTB_COLORS] = strtol(ttb, NULL, 10); - if (errno == ERANGE || errno == EINVAL - || ci->ttb[TTB_COLORS] < 0) { - if (debug) { - alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_COLORS]); + ci->botflags |= BS_KICK_CAPS; + if (ci->ttb[TTB_CAPS]) + notice_lang(s_BotServ, u, BOT_KICK_CAPS_ON_BAN, + ci->capsmin, ci->capspercent, + ci->ttb[TTB_CAPS]); + else + notice_lang(s_BotServ, u, BOT_KICK_CAPS_ON, + ci->capsmin, ci->capspercent); + } else { + ci->botflags &= ~BS_KICK_CAPS; + notice_lang(s_BotServ, u, BOT_KICK_CAPS_OFF); + } + } else if (!stricmp(option, "COLORS")) { + if (!stricmp(value, "ON")) { + if (ttb) { + ci->ttb[TTB_COLORS] = strtol(ttb, NULL, 10); + if (errno == ERANGE || errno == EINVAL + || ci->ttb[TTB_COLORS] < 0) { + if (debug) { + alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_COLORS]); + } + ci->ttb[TTB_COLORS] = 0; + notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); + return MOD_CONT; } + } else ci->ttb[TTB_COLORS] = 0; - notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); - return MOD_CONT; - } - } else - ci->ttb[TTB_COLORS] = 0; - ci->botflags |= BS_KICK_COLORS; - if (ci->ttb[TTB_COLORS]) - notice_lang(s_BotServ, u, BOT_KICK_COLORS_ON_BAN, - ci->ttb[TTB_COLORS]); - else - notice_lang(s_BotServ, u, BOT_KICK_COLORS_ON); - } else { - ci->botflags &= ~BS_KICK_COLORS; - notice_lang(s_BotServ, u, BOT_KICK_COLORS_OFF); - } - } else if (!stricmp(option, "FLOOD")) { - if (!stricmp(value, "ON")) { - char *lines = strtok(NULL, " "); - char *secs = strtok(NULL, " "); + ci->botflags |= BS_KICK_COLORS; + if (ci->ttb[TTB_COLORS]) + notice_lang(s_BotServ, u, BOT_KICK_COLORS_ON_BAN, + ci->ttb[TTB_COLORS]); + else + notice_lang(s_BotServ, u, BOT_KICK_COLORS_ON); + } else { + ci->botflags &= ~BS_KICK_COLORS; + notice_lang(s_BotServ, u, BOT_KICK_COLORS_OFF); + } + } else if (!stricmp(option, "FLOOD")) { + if (!stricmp(value, "ON")) { + char *lines = strtok(NULL, " "); + char *secs = strtok(NULL, " "); - if (ttb) { - ci->ttb[TTB_FLOOD] = strtol(ttb, NULL, 10); - if (errno == ERANGE || errno == EINVAL - || ci->ttb[TTB_FLOOD] < 0) { - if (debug) { - alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_FLOOD]); + if (ttb) { + ci->ttb[TTB_FLOOD] = strtol(ttb, NULL, 10); + if (errno == ERANGE || errno == EINVAL + || ci->ttb[TTB_FLOOD] < 0) { + if (debug) { + alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_FLOOD]); + } + ci->ttb[TTB_FLOOD] = 0; + notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); + return MOD_CONT; } + } else ci->ttb[TTB_FLOOD] = 0; - notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); - return MOD_CONT; - } - } else - ci->ttb[TTB_FLOOD] = 0; - if (!lines) - ci->floodlines = 6; - else - ci->floodlines = atol(lines); - if (ci->floodlines < 2) - ci->floodlines = 6; + if (!lines) + ci->floodlines = 6; + else + ci->floodlines = atol(lines); + if (ci->floodlines < 2) + ci->floodlines = 6; - if (!secs) - ci->floodsecs = 10; - else - ci->floodsecs = atol(secs); - if (ci->floodsecs < 1 || ci->floodsecs > BSKeepData) - ci->floodsecs = 10; + if (!secs) + ci->floodsecs = 10; + else + ci->floodsecs = atol(secs); + if (ci->floodsecs < 1 || ci->floodsecs > BSKeepData) + ci->floodsecs = 10; - ci->botflags |= BS_KICK_FLOOD; - if (ci->ttb[TTB_FLOOD]) - notice_lang(s_BotServ, u, BOT_KICK_FLOOD_ON_BAN, - ci->floodlines, ci->floodsecs, - ci->ttb[TTB_FLOOD]); - else - notice_lang(s_BotServ, u, BOT_KICK_FLOOD_ON, - ci->floodlines, ci->floodsecs); - } else { - ci->botflags &= ~BS_KICK_FLOOD; - notice_lang(s_BotServ, u, BOT_KICK_FLOOD_OFF); - } - } else if (!stricmp(option, "REPEAT")) { - if (!stricmp(value, "ON")) { - char *times = strtok(NULL, " "); + ci->botflags |= BS_KICK_FLOOD; + if (ci->ttb[TTB_FLOOD]) + notice_lang(s_BotServ, u, BOT_KICK_FLOOD_ON_BAN, + ci->floodlines, ci->floodsecs, + ci->ttb[TTB_FLOOD]); + else + notice_lang(s_BotServ, u, BOT_KICK_FLOOD_ON, + ci->floodlines, ci->floodsecs); + } else { + ci->botflags &= ~BS_KICK_FLOOD; + notice_lang(s_BotServ, u, BOT_KICK_FLOOD_OFF); + } + } else if (!stricmp(option, "REPEAT")) { + if (!stricmp(value, "ON")) { + char *times = strtok(NULL, " "); - if (ttb) { - ci->ttb[TTB_REPEAT] = strtol(ttb, NULL, 10); - if (errno == ERANGE || errno == EINVAL - || ci->ttb[TTB_REPEAT] < 0) { - if (debug) { - alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_REPEAT]); + if (ttb) { + ci->ttb[TTB_REPEAT] = strtol(ttb, NULL, 10); + if (errno == ERANGE || errno == EINVAL + || ci->ttb[TTB_REPEAT] < 0) { + if (debug) { + alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_REPEAT]); + } + ci->ttb[TTB_REPEAT] = 0; + notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); + return MOD_CONT; } + } else ci->ttb[TTB_REPEAT] = 0; - notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); - return MOD_CONT; - } - } else - ci->ttb[TTB_REPEAT] = 0; - if (!times) - ci->repeattimes = 3; - else - ci->repeattimes = atol(times); - if (ci->repeattimes < 2) - ci->repeattimes = 3; + if (!times) + ci->repeattimes = 3; + else + ci->repeattimes = atol(times); + if (ci->repeattimes < 2) + ci->repeattimes = 3; - ci->botflags |= BS_KICK_REPEAT; - if (ci->ttb[TTB_REPEAT]) - notice_lang(s_BotServ, u, BOT_KICK_REPEAT_ON_BAN, - ci->repeattimes, ci->ttb[TTB_REPEAT]); - else - notice_lang(s_BotServ, u, BOT_KICK_REPEAT_ON, - ci->repeattimes); - } else { - ci->botflags &= ~BS_KICK_REPEAT; - notice_lang(s_BotServ, u, BOT_KICK_REPEAT_OFF); - } - } else if (!stricmp(option, "REVERSES")) { - if (!stricmp(value, "ON")) { - if (ttb) { - ci->ttb[TTB_REVERSES] = - strtol(ttb, NULL, 10); - if (errno == ERANGE || errno == EINVAL - || ci->ttb[TTB_REVERSES] < 0) { - if (debug) { - alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_REVERSES]); + ci->botflags |= BS_KICK_REPEAT; + if (ci->ttb[TTB_REPEAT]) + notice_lang(s_BotServ, u, BOT_KICK_REPEAT_ON_BAN, + ci->repeattimes, ci->ttb[TTB_REPEAT]); + else + notice_lang(s_BotServ, u, BOT_KICK_REPEAT_ON, + ci->repeattimes); + } else { + ci->botflags &= ~BS_KICK_REPEAT; + notice_lang(s_BotServ, u, BOT_KICK_REPEAT_OFF); + } + } else if (!stricmp(option, "REVERSES")) { + if (!stricmp(value, "ON")) { + if (ttb) { + ci->ttb[TTB_REVERSES] = + strtol(ttb, NULL, 10); + if (errno == ERANGE || errno == EINVAL + || ci->ttb[TTB_REVERSES] < 0) { + if (debug) { + alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_REVERSES]); + } + ci->ttb[TTB_REVERSES] = 0; + notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); + return MOD_CONT; } + } else ci->ttb[TTB_REVERSES] = 0; - notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); - return MOD_CONT; - } - } else - ci->ttb[TTB_REVERSES] = 0; - ci->botflags |= BS_KICK_REVERSES; - if (ci->ttb[TTB_REVERSES]) - notice_lang(s_BotServ, u, BOT_KICK_REVERSES_ON_BAN, - ci->ttb[TTB_REVERSES]); - else - notice_lang(s_BotServ, u, BOT_KICK_REVERSES_ON); - } else { - ci->botflags &= ~BS_KICK_REVERSES; - notice_lang(s_BotServ, u, BOT_KICK_REVERSES_OFF); - } - } else if (!stricmp(option, "UNDERLINES")) { - if (!stricmp(value, "ON")) { - if (ttb) { - ci->ttb[TTB_UNDERLINES] = - strtol(ttb, NULL, 10); - if (errno == ERANGE || errno == EINVAL - || ci->ttb[TTB_UNDERLINES] < 0) { - if (debug) { - alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_UNDERLINES]); + ci->botflags |= BS_KICK_REVERSES; + if (ci->ttb[TTB_REVERSES]) + notice_lang(s_BotServ, u, BOT_KICK_REVERSES_ON_BAN, + ci->ttb[TTB_REVERSES]); + else + notice_lang(s_BotServ, u, BOT_KICK_REVERSES_ON); + } else { + ci->botflags &= ~BS_KICK_REVERSES; + notice_lang(s_BotServ, u, BOT_KICK_REVERSES_OFF); + } + } else if (!stricmp(option, "UNDERLINES")) { + if (!stricmp(value, "ON")) { + if (ttb) { + ci->ttb[TTB_UNDERLINES] = + strtol(ttb, NULL, 10); + if (errno == ERANGE || errno == EINVAL + || ci->ttb[TTB_UNDERLINES] < 0) { + if (debug) { + alog("debug: errno is %d ERANGE %d EINVAL %d ttb %d", errno, ERANGE, EINVAL, ci->ttb[TTB_UNDERLINES]); + } + ci->ttb[TTB_UNDERLINES] = 0; + notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); + return MOD_CONT; } + } else ci->ttb[TTB_UNDERLINES] = 0; - notice_lang(s_BotServ, u, BOT_KICK_BAD_TTB, ttb); - return MOD_CONT; - } - } else - ci->ttb[TTB_UNDERLINES] = 0; - ci->botflags |= BS_KICK_UNDERLINES; - if (ci->ttb[TTB_UNDERLINES]) - notice_lang(s_BotServ, u, BOT_KICK_UNDERLINES_ON_BAN, - ci->ttb[TTB_UNDERLINES]); - else - notice_lang(s_BotServ, u, BOT_KICK_UNDERLINES_ON); - } else { - ci->botflags &= ~BS_KICK_UNDERLINES; - notice_lang(s_BotServ, u, BOT_KICK_UNDERLINES_OFF); - } - } else - notice_help(s_BotServ, u, BOT_KICK_UNKNOWN, option); + ci->botflags |= BS_KICK_UNDERLINES; + if (ci->ttb[TTB_UNDERLINES]) + notice_lang(s_BotServ, u, BOT_KICK_UNDERLINES_ON_BAN, + ci->ttb[TTB_UNDERLINES]); + else + notice_lang(s_BotServ, u, BOT_KICK_UNDERLINES_ON); + } else { + ci->botflags &= ~BS_KICK_UNDERLINES; + notice_lang(s_BotServ, u, BOT_KICK_UNDERLINES_OFF); + } + } else + notice_help(s_BotServ, u, BOT_KICK_UNKNOWN, option); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + // XXX: This is not a good way to handle it, we need to accept params for HELP. + notice_help(s_BotServ, u, BOT_HELP_KICK); + notice_help(s_BotServ, u, BOT_HELP_KICK_BADWORDS); + notice_help(s_BotServ, u, BOT_HELP_KICK_BOLDS); + notice_help(s_BotServ, u, BOT_HELP_KICK_CAPS); + notice_help(s_BotServ, u, BOT_HELP_KICK_COLORS); + notice_help(s_BotServ, u, BOT_HELP_KICK_FLOOD); + notice_help(s_BotServ, u, BOT_HELP_KICK_REPEAT); + notice_help(s_BotServ, u, BOT_HELP_KICK_REVERSES); + notice_help(s_BotServ, u, BOT_HELP_KICK_UNDERLINES); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_BotServ, u, "KICK", BOT_KICK_SYNTAX); } - return MOD_CONT; +}; + +class BSKick : public Module +{ + public: + BSKick(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(BOTSERV, new CommandBSKick(), MOD_UNIQUE); + + this->SetBotHelp(myBotServHelp); + } +}; + + +/** + * Add the help response to Anopes /bs help output. + * @param u The user who is requesting help + **/ +void myBotServHelp(User * u) +{ + notice_lang(s_BotServ, u, BOT_HELP_CMD_KICK); } + MODULE_INIT("bs_kick", BSKick) diff --git a/src/core/bs_say.c b/src/core/bs_say.c index 023ef6b77..dd995bcc1 100644 --- a/src/core/bs_say.c +++ b/src/core/bs_say.c @@ -15,21 +15,86 @@ #include "module.h" -int do_say(User * u); void myBotServHelp(User * u); +class CommandBSSay : public Command +{ + public: + CommandBSSay() : Command("SAY", 2, 2) + { + } + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + ChannelInfo *ci; + + const char *chan = params[0].c_str(); + const char *text = params[1].c_str(); + + if (!(ci = cs_findchan(chan))) + { + notice_lang(s_BotServ, u, CHAN_X_NOT_REGISTERED, chan); + return MOD_CONT; + } + + if (ci->flags & CI_VERBOTEN) + { + notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } + + if (!ci->bi) + { + notice_help(s_BotServ, u, BOT_NOT_ASSIGNED); + return MOD_CONT; + } + + if (!ci->c || ci->c->usercount < BSMinUsers) + { + notice_lang(s_BotServ, u, BOT_NOT_ON_CHANNEL, ci->name); + return MOD_CONT; + } + + if (!check_access(u, ci, CA_SAY)) + { + notice_lang(s_BotServ, u, ACCESS_DENIED); + return MOD_CONT; + } + + if (text[0] == '\001') + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + ircdproto->SendPrivmsg(ci->bi, ci->name, "%s", text); + ci->bi->lastmsg = time(NULL); + if (LogBot && LogChannel && logchan && !debug && findchan(LogChannel)) + ircdproto->SendPrivmsg(ci->bi, LogChannel, "SAY %s %s %s", u->nick, ci->name, text); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_BotServ, u, BOT_HELP_SAY); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_BotServ, u, "SAY", BOT_SAY_SYNTAX); + } +}; + class BSSay : public Module { public: BSSay(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("SAY", do_say, NULL, BOT_HELP_SAY, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); + this->AddCommand(BOTSERV, new CommandBSSay(), MOD_UNIQUE); this->SetBotHelp(myBotServHelp); } @@ -45,42 +110,5 @@ void myBotServHelp(User * u) notice_lang(s_BotServ, u, BOT_HELP_CMD_SAY); } -/** - * The /bs say command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_say(User * u) -{ - ChannelInfo *ci; - - char *chan = strtok(NULL, " "); - char *text = strtok(NULL, ""); - - if (!chan || !text) - syntax_error(s_BotServ, u, "SAY", BOT_SAY_SYNTAX); - else if (!(ci = cs_findchan(chan))) - notice_lang(s_BotServ, u, CHAN_X_NOT_REGISTERED, chan); - else if (ci->flags & CI_VERBOTEN) - notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, chan); - else if (!ci->bi) - notice_help(s_BotServ, u, BOT_NOT_ASSIGNED); - else if (!ci->c || ci->c->usercount < BSMinUsers) - notice_lang(s_BotServ, u, BOT_NOT_ON_CHANNEL, ci->name); - else if (!check_access(u, ci, CA_SAY)) - notice_lang(s_BotServ, u, ACCESS_DENIED); - else { - if (text[0] != '\001') { - ircdproto->SendPrivmsg(ci->bi, ci->name, "%s", text); - ci->bi->lastmsg = time(NULL); - if (LogBot && LogChannel && logchan && !debug && findchan(LogChannel)) - ircdproto->SendPrivmsg(ci->bi, LogChannel, - "SAY %s %s %s", u->nick, ci->name, text); - } else { - syntax_error(s_BotServ, u, "SAY", BOT_SAY_SYNTAX); - } - } - return MOD_CONT; -} MODULE_INIT("bs_say", BSSay) diff --git a/src/core/bs_set.c b/src/core/bs_set.c index 52dc7e51c..9132ed300 100644 --- a/src/core/bs_set.c +++ b/src/core/bs_set.c @@ -15,9 +15,165 @@ #include "module.h" -int do_set(User * u); void myBotServHelp(User * u); +class CommandBSSet : public Command +{ + public: + CommandBSSet() : Command("SET", 3, 3) + { + } + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + const char *option = params[1].c_str(); + const char *value = params[2].c_str(); + int is_servadmin = is_services_admin(u); + ChannelInfo *ci; + + if (readonly) + { + notice_lang(s_BotServ, u, BOT_SET_DISABLED); + return MOD_CONT; + } + + if (is_servadmin && !stricmp(option, "PRIVATE")) + { + BotInfo *bi; + + if (!(bi = findbot(chan))) + { + notice_lang(s_BotServ, u, BOT_DOES_NOT_EXIST, chan); + return MOD_CONT; + } + + if (!stricmp(value, "ON")) + { + bi->flags |= BI_PRIVATE; + notice_lang(s_BotServ, u, BOT_SET_PRIVATE_ON, bi->nick); + } + else if (!stricmp(value, "OFF")) + { + bi->flags &= ~BI_PRIVATE; + notice_lang(s_BotServ, u, BOT_SET_PRIVATE_OFF, bi->nick); + } + else + { + syntax_error(s_BotServ, u, "SET PRIVATE", BOT_SET_PRIVATE_SYNTAX); + } + return MOD_CONT; + } else if (!(ci = cs_findchan(chan))) + notice_lang(s_BotServ, u, CHAN_X_NOT_REGISTERED, chan); + else if (ci->flags & CI_VERBOTEN) + notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, chan); + else if (!is_servadmin && !check_access(u, ci, CA_SET)) + notice_lang(s_BotServ, u, ACCESS_DENIED); + else { + if (!stricmp(option, "DONTKICKOPS")) { + if (!stricmp(value, "ON")) { + ci->botflags |= BS_DONTKICKOPS; + notice_lang(s_BotServ, u, BOT_SET_DONTKICKOPS_ON, + ci->name); + } else if (!stricmp(value, "OFF")) { + ci->botflags &= ~BS_DONTKICKOPS; + notice_lang(s_BotServ, u, BOT_SET_DONTKICKOPS_OFF, + ci->name); + } else { + syntax_error(s_BotServ, u, "SET DONTKICKOPS", + BOT_SET_DONTKICKOPS_SYNTAX); + } + } else if (!stricmp(option, "DONTKICKVOICES")) { + if (!stricmp(value, "ON")) { + ci->botflags |= BS_DONTKICKVOICES; + notice_lang(s_BotServ, u, BOT_SET_DONTKICKVOICES_ON, + ci->name); + } else if (!stricmp(value, "OFF")) { + ci->botflags &= ~BS_DONTKICKVOICES; + notice_lang(s_BotServ, u, BOT_SET_DONTKICKVOICES_OFF, + ci->name); + } else { + syntax_error(s_BotServ, u, "SET DONTKICKVOICES", + BOT_SET_DONTKICKVOICES_SYNTAX); + } + } else if (!stricmp(option, "FANTASY")) { + if (!stricmp(value, "ON")) { + ci->botflags |= BS_FANTASY; + notice_lang(s_BotServ, u, BOT_SET_FANTASY_ON, ci->name); + } else if (!stricmp(value, "OFF")) { + ci->botflags &= ~BS_FANTASY; + notice_lang(s_BotServ, u, BOT_SET_FANTASY_OFF, ci->name); + } else { + syntax_error(s_BotServ, u, "SET FANTASY", + BOT_SET_FANTASY_SYNTAX); + } + } else if (!stricmp(option, "GREET")) { + if (!stricmp(value, "ON")) { + ci->botflags |= BS_GREET; + notice_lang(s_BotServ, u, BOT_SET_GREET_ON, ci->name); + } else if (!stricmp(value, "OFF")) { + ci->botflags &= ~BS_GREET; + notice_lang(s_BotServ, u, BOT_SET_GREET_OFF, ci->name); + } else { + syntax_error(s_BotServ, u, "SET GREET", + BOT_SET_GREET_SYNTAX); + } + } else if (is_servadmin && !stricmp(option, "NOBOT")) { + if (!stricmp(value, "ON")) { + ci->botflags |= BS_NOBOT; + if (ci->bi) + ci->bi->UnAssign(u, ci); + notice_lang(s_BotServ, u, BOT_SET_NOBOT_ON, ci->name); + } else if (!stricmp(value, "OFF")) { + ci->botflags &= ~BS_NOBOT; + notice_lang(s_BotServ, u, BOT_SET_NOBOT_OFF, ci->name); + } else { + syntax_error(s_BotServ, u, "SET NOBOT", + BOT_SET_NOBOT_SYNTAX); + } + } else if (!stricmp(option, "SYMBIOSIS")) { + if (!stricmp(value, "ON")) { + ci->botflags |= BS_SYMBIOSIS; + notice_lang(s_BotServ, u, BOT_SET_SYMBIOSIS_ON, ci->name); + } else if (!stricmp(value, "OFF")) { + ci->botflags &= ~BS_SYMBIOSIS; + notice_lang(s_BotServ, u, BOT_SET_SYMBIOSIS_OFF, ci->name); + } else { + syntax_error(s_BotServ, u, "SET SYMBIOSIS", + BOT_SET_SYMBIOSIS_SYNTAX); + } + } else { + notice_help(s_BotServ, u, BOT_SET_UNKNOWN, option); + } + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + // This needs to change XXX + notice_lang(s_BotServ, u, BOT_HELP_SET); + notice_lang(s_BotServ, u, BOT_HELP_SET_DONTKICKOPS); + notice_lang(s_BotServ, u, BOT_HELP_SET_DONTKICKVOICES); + notice_lang(s_BotServ, u, BOT_HELP_SET_FANTASY); + notice_lang(s_BotServ, u, BOT_HELP_SET_GREET); + notice_lang(s_BotServ, u, BOT_HELP_SET_SYMBIOSIS); + + if (is_services_admin(u) || is_services_root(u)) + { + notice_lang(s_BotServ, u, BOT_SERVADMIN_HELP_SET); + notice_lang(s_BotServ, u, BOT_SERVADMIN_HELP_SET_NOBOT); + notice_lang(s_BotServ, u, BOT_SERVADMIN_HELP_SET_PRIVATE); + } + + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_BotServ, u, "SET", BOT_SET_SYNTAX); + } +}; class BSSet : public Module { public: @@ -28,26 +184,8 @@ class BSSet : public Module this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - - c = createCommand("SET", do_set, NULL, BOT_HELP_SET, -1, -1, BOT_SERVADMIN_HELP_SET, BOT_SERVADMIN_HELP_SET); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("SET DONTKICKOPS", NULL, NULL, BOT_HELP_SET_DONTKICKOPS, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("SET DONTKICKVOICES", NULL, NULL, BOT_HELP_SET_DONTKICKVOICES, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("SET FANTASY", NULL, NULL, BOT_HELP_SET_FANTASY, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("SET GREET", NULL, NULL, BOT_HELP_SET_GREET, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("SET SYMBIOSIS", NULL, NULL, BOT_HELP_SET_SYMBIOSIS, -1, -1, -1, -1); + this->AddCommand(BOTSERV, new CommandBSSet(), MOD_UNIQUE); c->help_param1 = s_ChanServ; - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("SET NOBOT", NULL, NULL, -1, -1, -1, BOT_SERVADMIN_HELP_SET_NOBOT, BOT_SERVADMIN_HELP_SET_NOBOT); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); - c = createCommand("SET PRIVATE", NULL, NULL, -1, -1, -1, - BOT_SERVADMIN_HELP_SET_PRIVATE, - BOT_SERVADMIN_HELP_SET_PRIVATE); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); this->SetBotHelp(myBotServHelp); } @@ -63,126 +201,4 @@ void myBotServHelp(User * u) notice_lang(s_BotServ, u, BOT_HELP_CMD_SET); } -/** - * The /bs set command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_set(User * u) -{ - char *chan = strtok(NULL, " "); - char *option = strtok(NULL, " "); - char *value = strtok(NULL, " "); - int is_servadmin = is_services_admin(u); - - ChannelInfo *ci; - - if (readonly) - notice_lang(s_BotServ, u, BOT_SET_DISABLED); - else if (!chan || !option || !value) - syntax_error(s_BotServ, u, "SET", BOT_SET_SYNTAX); - else if (is_servadmin && !stricmp(option, "PRIVATE")) { - BotInfo *bi; - - if ((bi = findbot(chan))) { - if (!stricmp(value, "ON")) { - bi->flags |= BI_PRIVATE; - notice_lang(s_BotServ, u, BOT_SET_PRIVATE_ON, bi->nick); - } else if (!stricmp(value, "OFF")) { - bi->flags &= ~BI_PRIVATE; - notice_lang(s_BotServ, u, BOT_SET_PRIVATE_OFF, bi->nick); - } else { - syntax_error(s_BotServ, u, "SET PRIVATE", - BOT_SET_PRIVATE_SYNTAX); - } - } else { - notice_lang(s_BotServ, u, BOT_DOES_NOT_EXIST, chan); - } - return MOD_CONT; - } else if (!(ci = cs_findchan(chan))) - notice_lang(s_BotServ, u, CHAN_X_NOT_REGISTERED, chan); - else if (ci->flags & CI_VERBOTEN) - notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, chan); - else if (!is_servadmin && !check_access(u, ci, CA_SET)) - notice_lang(s_BotServ, u, ACCESS_DENIED); - else { - if (!stricmp(option, "DONTKICKOPS")) { - if (!stricmp(value, "ON")) { - ci->botflags |= BS_DONTKICKOPS; - notice_lang(s_BotServ, u, BOT_SET_DONTKICKOPS_ON, - ci->name); - } else if (!stricmp(value, "OFF")) { - ci->botflags &= ~BS_DONTKICKOPS; - notice_lang(s_BotServ, u, BOT_SET_DONTKICKOPS_OFF, - ci->name); - } else { - syntax_error(s_BotServ, u, "SET DONTKICKOPS", - BOT_SET_DONTKICKOPS_SYNTAX); - } - } else if (!stricmp(option, "DONTKICKVOICES")) { - if (!stricmp(value, "ON")) { - ci->botflags |= BS_DONTKICKVOICES; - notice_lang(s_BotServ, u, BOT_SET_DONTKICKVOICES_ON, - ci->name); - } else if (!stricmp(value, "OFF")) { - ci->botflags &= ~BS_DONTKICKVOICES; - notice_lang(s_BotServ, u, BOT_SET_DONTKICKVOICES_OFF, - ci->name); - } else { - syntax_error(s_BotServ, u, "SET DONTKICKVOICES", - BOT_SET_DONTKICKVOICES_SYNTAX); - } - } else if (!stricmp(option, "FANTASY")) { - if (!stricmp(value, "ON")) { - ci->botflags |= BS_FANTASY; - notice_lang(s_BotServ, u, BOT_SET_FANTASY_ON, ci->name); - } else if (!stricmp(value, "OFF")) { - ci->botflags &= ~BS_FANTASY; - notice_lang(s_BotServ, u, BOT_SET_FANTASY_OFF, ci->name); - } else { - syntax_error(s_BotServ, u, "SET FANTASY", - BOT_SET_FANTASY_SYNTAX); - } - } else if (!stricmp(option, "GREET")) { - if (!stricmp(value, "ON")) { - ci->botflags |= BS_GREET; - notice_lang(s_BotServ, u, BOT_SET_GREET_ON, ci->name); - } else if (!stricmp(value, "OFF")) { - ci->botflags &= ~BS_GREET; - notice_lang(s_BotServ, u, BOT_SET_GREET_OFF, ci->name); - } else { - syntax_error(s_BotServ, u, "SET GREET", - BOT_SET_GREET_SYNTAX); - } - } else if (is_servadmin && !stricmp(option, "NOBOT")) { - if (!stricmp(value, "ON")) { - ci->botflags |= BS_NOBOT; - if (ci->bi) - ci->bi->UnAssign(u, ci); - notice_lang(s_BotServ, u, BOT_SET_NOBOT_ON, ci->name); - } else if (!stricmp(value, "OFF")) { - ci->botflags &= ~BS_NOBOT; - notice_lang(s_BotServ, u, BOT_SET_NOBOT_OFF, ci->name); - } else { - syntax_error(s_BotServ, u, "SET NOBOT", - BOT_SET_NOBOT_SYNTAX); - } - } else if (!stricmp(option, "SYMBIOSIS")) { - if (!stricmp(value, "ON")) { - ci->botflags |= BS_SYMBIOSIS; - notice_lang(s_BotServ, u, BOT_SET_SYMBIOSIS_ON, ci->name); - } else if (!stricmp(value, "OFF")) { - ci->botflags &= ~BS_SYMBIOSIS; - notice_lang(s_BotServ, u, BOT_SET_SYMBIOSIS_OFF, ci->name); - } else { - syntax_error(s_BotServ, u, "SET SYMBIOSIS", - BOT_SET_SYMBIOSIS_SYNTAX); - } - } else { - notice_help(s_BotServ, u, BOT_SET_UNKNOWN, option); - } - } - return MOD_CONT; -} - MODULE_INIT("bs_set", BSSet) diff --git a/src/core/bs_unassign.c b/src/core/bs_unassign.c index 9066be2dd..fd8f487a6 100644 --- a/src/core/bs_unassign.c +++ b/src/core/bs_unassign.c @@ -18,18 +18,56 @@ int do_unassign(User * u); void myBotServHelp(User * u); +class CommandBSUnassign : public Command +{ + public: + CommandBSUnassign() : Command("UNASSIGN", 1, 1) + { + } + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + ChannelInfo *ci; + + if (readonly) + notice_lang(s_BotServ, u, BOT_ASSIGN_READONLY); + else if (!(ci = cs_findchan(chan))) + notice_lang(s_BotServ, u, CHAN_X_NOT_REGISTERED, chan); + else if (ci->flags & CI_VERBOTEN) + notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, chan); + else if (!is_services_admin(u) && !check_access(u, ci, CA_ASSIGN)) + notice_lang(s_BotServ, u, ACCESS_DENIED); + else if (!ci->bi) + notice_help(s_BotServ, u, BOT_NOT_ASSIGNED); + else { + ci->bi->UnAssign(u, ci); + notice_lang(s_BotServ, u, BOT_UNASSIGN_UNASSIGNED, ci->name); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_BotServ, u, BOT_HELP_UNASSIGN); + return true; + } + + void OnBadSyntax(User *u) + { + syntax_error(s_BotServ, u, "UNASSIGN", BOT_UNASSIGN_SYNTAX); + } +}; + class BSUnassign : public Module { public: BSUnassign(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("UNASSIGN", do_unassign, NULL, BOT_HELP_UNASSIGN, -1, -1, -1, -1); - this->AddCommand(BOTSERV, c, MOD_UNIQUE); + this->AddCommand(BOTSERV, new CommandBSUnassign, MOD_UNIQUE); this->SetBotHelp(myBotServHelp); } @@ -46,33 +84,4 @@ void myBotServHelp(User * u) notice_lang(s_BotServ, u, BOT_HELP_CMD_UNASSIGN); } -/** - * The /bs unassign command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_unassign(User * u) -{ - char *chan = strtok(NULL, " "); - ChannelInfo *ci; - - if (readonly) - notice_lang(s_BotServ, u, BOT_ASSIGN_READONLY); - else if (!chan) - syntax_error(s_BotServ, u, "UNASSIGN", BOT_UNASSIGN_SYNTAX); - else if (!(ci = cs_findchan(chan))) - notice_lang(s_BotServ, u, CHAN_X_NOT_REGISTERED, chan); - else if (ci->flags & CI_VERBOTEN) - notice_lang(s_BotServ, u, CHAN_X_FORBIDDEN, chan); - else if (!is_services_admin(u) && !check_access(u, ci, CA_ASSIGN)) - notice_lang(s_BotServ, u, ACCESS_DENIED); - else if (!ci->bi) - notice_help(s_BotServ, u, BOT_NOT_ASSIGNED); - else { - ci->bi->UnAssign(u, ci); - notice_lang(s_BotServ, u, BOT_UNASSIGN_UNASSIGNED, ci->name); - } - return MOD_CONT; -} - MODULE_INIT("bs_unassign", BSUnassign) diff --git a/src/core/cs_access.c b/src/core/cs_access.c index 34f110225..c55bebd84 100644 --- a/src/core/cs_access.c +++ b/src/core/cs_access.c @@ -16,35 +16,8 @@ #include "module.h" -int do_access(User * u); -int do_levels(User * u); - void myChanServHelp(User * u); -class CSAccess : public Module -{ - public: - CSAccess(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion - ("$Id$"); - this->SetType(CORE); - - c = createCommand("ACCESS", do_access, NULL, CHAN_HELP_ACCESS, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - c = createCommand("ACCESS LEVELS", NULL, NULL, CHAN_HELP_ACCESS_LEVELS, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - c = createCommand("LEVELS", do_levels, NULL, CHAN_HELP_LEVELS, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - this->SetChanHelp(myChanServHelp); - } -}; - - - /** * Add the help response to anopes /cs help output. * @param u The user who is requesting help @@ -120,409 +93,442 @@ static int access_list_callback(User * u, int num, va_list args) } -/** - * The /cs access command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_access(User * u) +class CommandCSAccess : public Command { - char *chan = strtok(NULL, " "); - char *cmd = strtok(NULL, " "); - char *nick = strtok(NULL, " "); - char *s = strtok(NULL, " "); - char event_access[BUFSIZE]; - - ChannelInfo *ci; - NickAlias *na = NULL; - NickCore *nc; - ChanAccess *access; - - unsigned i; - int level = 0, ulev; - int is_list = (cmd && stricmp(cmd, "LIST") == 0); - int is_servadmin = is_services_admin(u); - - /* If LIST, we don't *require* any parameters, but we can take any. - * If DEL, we require a nick and no level. - * Else (ADD), we require a level (which implies a nick). */ - if (!cmd || ((is_list || !stricmp(cmd, "CLEAR")) ? 0 : - (stricmp(cmd, "DEL") == 0) ? (!nick || s) : !s)) { - syntax_error(s_ChanServ, u, "ACCESS", CHAN_ACCESS_SYNTAX); - } else if (!(ci = cs_findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - /* We still allow LIST in xOP mode, but not others */ - } else if ((ci->flags & CI_XOP) && !is_list) { - if (ircd->halfop) - notice_lang(s_ChanServ, u, CHAN_ACCESS_XOP_HOP, s_ChanServ); - else - notice_lang(s_ChanServ, u, CHAN_ACCESS_XOP, s_ChanServ); - } else if (((is_list && !check_access(u, ci, CA_ACCESS_LIST)) - || (!is_list && !check_access(u, ci, CA_ACCESS_CHANGE))) - && !is_servadmin) { - notice_lang(s_ChanServ, u, ACCESS_DENIED); - } else if (stricmp(cmd, "ADD") == 0) { - if (readonly) { - notice_lang(s_ChanServ, u, CHAN_ACCESS_DISABLED); - return MOD_CONT; - } - - level = atoi(s); - ulev = get_access(u, ci); - - if (!is_servadmin && level >= ulev) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - return MOD_CONT; - } - - if (level == 0) { - notice_lang(s_ChanServ, u, CHAN_ACCESS_LEVEL_NONZERO); - return MOD_CONT; - } else if (level <= ACCESS_INVALID || level >= ACCESS_FOUNDER) { - notice_lang(s_ChanServ, u, CHAN_ACCESS_LEVEL_RANGE, - ACCESS_INVALID + 1, ACCESS_FOUNDER - 1); - return MOD_CONT; - } - - na = findnick(nick); - if (!na) { - notice_lang(s_ChanServ, u, CHAN_ACCESS_NICKS_ONLY); - return MOD_CONT; - } - if (na->status & NS_VERBOTEN) { - notice_lang(s_ChanServ, u, NICK_X_FORBIDDEN, nick); - return MOD_CONT; - } + public: + CommandCSAccess() : Command("ACCESS", 0, 4) + { + } - nc = na->nc; - for (access = ci->access, i = 0; i < ci->accesscount; - access++, i++) { - if (access->nc == nc) { - /* Don't allow lowering from a level >= ulev */ - if (!is_servadmin && access->level >= ulev) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - return MOD_CONT; - } - if (access->level == level) { - notice_lang(s_ChanServ, u, CHAN_ACCESS_LEVEL_UNCHANGED, - access->nc->display, chan, level); - return MOD_CONT; - } - access->level = level; - snprintf(event_access, BUFSIZE, "%d", access->level); - send_event(EVENT_ACCESS_CHANGE, 4, ci->name, u->nick, - na->nick, event_access); - alog("%s: %s!%s@%s (level %d) set access level %d to %s (group %s) on channel %s", s_ChanServ, u->nick, u->username, u->host, ulev, access->level, na->nick, nc->display, ci->name); - notice_lang(s_ChanServ, u, CHAN_ACCESS_LEVEL_CHANGED, - access->nc->display, chan, level); + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + const char *cmd = params[1].c_str(); + const char *nick = params[2].c_str(); + const char *s = params[3].c_str(); + char event_access[BUFSIZE]; + + ChannelInfo *ci; + NickAlias *na = NULL; + NickCore *nc; + ChanAccess *access; + + unsigned i; + int level = 0, ulev; + int is_list = (cmd && stricmp(cmd, "LIST") == 0); + int is_servadmin = is_services_admin(u); + + /* If LIST, we don't *require* any parameters, but we can take any. + * If DEL, we require a nick and no level. + * Else (ADD), we require a level (which implies a nick). */ + if (!cmd || ((is_list || !stricmp(cmd, "CLEAR")) ? 0 : + (stricmp(cmd, "DEL") == 0) ? (!nick || s) : !s)) { + syntax_error(s_ChanServ, u, "ACCESS", CHAN_ACCESS_SYNTAX); + } else if (!(ci = cs_findchan(chan))) { + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + } else if (ci->flags & CI_VERBOTEN) { + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + /* We still allow LIST in xOP mode, but not others */ + } else if ((ci->flags & CI_XOP) && !is_list) { + if (ircd->halfop) + notice_lang(s_ChanServ, u, CHAN_ACCESS_XOP_HOP, s_ChanServ); + else + notice_lang(s_ChanServ, u, CHAN_ACCESS_XOP, s_ChanServ); + } else if (((is_list && !check_access(u, ci, CA_ACCESS_LIST)) + || (!is_list && !check_access(u, ci, CA_ACCESS_CHANGE))) + && !is_servadmin) { + notice_lang(s_ChanServ, u, ACCESS_DENIED); + } else if (stricmp(cmd, "ADD") == 0) { + if (readonly) { + notice_lang(s_ChanServ, u, CHAN_ACCESS_DISABLED); return MOD_CONT; } - } - /* All entries should be in use so we no longer need - * to go over the entire list.. - for (i = 0; i < ci->accesscount; i++) { - if (!ci->access[i].in_use) - break; - } - */ + level = atoi(s); + ulev = get_access(u, ci); - if (i < CSAccessMax) { - ci->accesscount++; - ci->access = - static_cast<ChanAccess *>(srealloc(ci->access, - sizeof(ChanAccess) * ci->accesscount)); - } else { - notice_lang(s_ChanServ, u, CHAN_ACCESS_REACHED_LIMIT, - CSAccessMax); - return MOD_CONT; - } - - access = &ci->access[i]; - access->nc = nc; - access->in_use = 1; - access->level = level; - access->last_seen = 0; - - snprintf(event_access, BUFSIZE, "%d", access->level); - send_event(EVENT_ACCESS_ADD, 4, ci->name, u->nick, na->nick, - event_access); - alog("%s: %s!%s@%s (level %d) set access level %d to %s (group %s) on channel %s", s_ChanServ, u->nick, u->username, u->host, ulev, access->level, na->nick, nc->display, ci->name); - notice_lang(s_ChanServ, u, CHAN_ACCESS_ADDED, nc->display, - ci->name, access->level); - } else if (stricmp(cmd, "DEL") == 0) { - int deleted, a, b; - if (readonly) { - notice_lang(s_ChanServ, u, CHAN_ACCESS_DISABLED); - return MOD_CONT; - } - - if (ci->accesscount == 0) { - notice_lang(s_ChanServ, u, CHAN_ACCESS_LIST_EMPTY, chan); - return MOD_CONT; - } + if (!is_servadmin && level >= ulev) { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + return MOD_CONT; + } - /* Special case: is it a number/list? Only do search if it isn't. */ - if (isdigit(*nick) && strspn(nick, "1234567890,-") == strlen(nick)) { - int count, last = -1, perm = 0; - deleted = process_numlist(nick, &count, access_del_callback, u, - ci, &last, &perm, get_access(u, ci)); - if (!deleted) { - if (perm) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - } else if (count == 1) { - notice_lang(s_ChanServ, u, CHAN_ACCESS_NO_SUCH_ENTRY, - last, ci->name); - } else { - notice_lang(s_ChanServ, u, CHAN_ACCESS_NO_MATCH, - ci->name); - } - } else if (deleted == 1) { - notice_lang(s_ChanServ, u, CHAN_ACCESS_DELETED_ONE, - ci->name); - } else { - notice_lang(s_ChanServ, u, CHAN_ACCESS_DELETED_SEVERAL, - deleted, ci->name); + if (level == 0) { + notice_lang(s_ChanServ, u, CHAN_ACCESS_LEVEL_NONZERO); + return MOD_CONT; + } else if (level <= ACCESS_INVALID || level >= ACCESS_FOUNDER) { + notice_lang(s_ChanServ, u, CHAN_ACCESS_LEVEL_RANGE, + ACCESS_INVALID + 1, ACCESS_FOUNDER - 1); + return MOD_CONT; } - } else { + na = findnick(nick); if (!na) { - notice_lang(s_ChanServ, u, NICK_X_NOT_REGISTERED, nick); + notice_lang(s_ChanServ, u, CHAN_ACCESS_NICKS_ONLY); return MOD_CONT; } + if (na->status & NS_VERBOTEN) { + notice_lang(s_ChanServ, u, NICK_X_FORBIDDEN, nick); + return MOD_CONT; + } + nc = na->nc; - for (i = 0; i < ci->accesscount; i++) { - if (ci->access[i].nc == nc) - break; + for (access = ci->access, i = 0; i < ci->accesscount; + access++, i++) { + if (access->nc == nc) { + /* Don't allow lowering from a level >= ulev */ + if (!is_servadmin && access->level >= ulev) { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + return MOD_CONT; + } + if (access->level == level) { + notice_lang(s_ChanServ, u, CHAN_ACCESS_LEVEL_UNCHANGED, + access->nc->display, chan, level); + return MOD_CONT; + } + access->level = level; + snprintf(event_access, BUFSIZE, "%d", access->level); + send_event(EVENT_ACCESS_CHANGE, 4, ci->name, u->nick, + na->nick, event_access); + alog("%s: %s!%s@%s (level %d) set access level %d to %s (group %s) on channel %s", s_ChanServ, u->nick, u->GetIdent().c_str(), u->host, ulev, access->level, na->nick, nc->display, ci->name); + notice_lang(s_ChanServ, u, CHAN_ACCESS_LEVEL_CHANGED, + access->nc->display, chan, level); + return MOD_CONT; + } } - if (i == ci->accesscount) { - notice_lang(s_ChanServ, u, CHAN_ACCESS_NOT_FOUND, nick, - chan); + + if (i < CSAccessMax) { + ci->accesscount++; + ci->access = + static_cast<ChanAccess *>(srealloc(ci->access, + sizeof(ChanAccess) * ci->accesscount)); + } else { + notice_lang(s_ChanServ, u, CHAN_ACCESS_REACHED_LIMIT, + CSAccessMax); return MOD_CONT; } + access = &ci->access[i]; - if (!is_servadmin && get_access(u, ci) <= access->level) { - deleted = 0; - notice_lang(s_ChanServ, u, PERMISSION_DENIED); + access->nc = nc; + access->in_use = 1; + access->level = level; + access->last_seen = 0; + + snprintf(event_access, BUFSIZE, "%d", access->level); + send_event(EVENT_ACCESS_ADD, 4, ci->name, u->nick, na->nick, + event_access); + alog("%s: %s!%s@%s (level %d) set access level %d to %s (group %s) on channel %s", s_ChanServ, u->nick, u->GetIdent().c_str(), u->host, ulev, access->level, na->nick, nc->display, ci->name); + notice_lang(s_ChanServ, u, CHAN_ACCESS_ADDED, nc->display, + ci->name, access->level); + } else if (stricmp(cmd, "DEL") == 0) { + int deleted, a, b; + if (readonly) { + notice_lang(s_ChanServ, u, CHAN_ACCESS_DISABLED); + return MOD_CONT; + } + + if (ci->accesscount == 0) { + notice_lang(s_ChanServ, u, CHAN_ACCESS_LIST_EMPTY, chan); + return MOD_CONT; + } + + /* Special case: is it a number/list? Only do search if it isn't. */ + if (isdigit(*nick) && strspn(nick, "1234567890,-") == strlen(nick)) { + int count, last = -1, perm = 0; + deleted = process_numlist(nick, &count, access_del_callback, u, + ci, &last, &perm, get_access(u, ci)); + if (!deleted) { + if (perm) { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + } else if (count == 1) { + notice_lang(s_ChanServ, u, CHAN_ACCESS_NO_SUCH_ENTRY, + last, ci->name); + } else { + notice_lang(s_ChanServ, u, CHAN_ACCESS_NO_MATCH, + ci->name); + } + } else if (deleted == 1) { + notice_lang(s_ChanServ, u, CHAN_ACCESS_DELETED_ONE, + ci->name); + } else { + notice_lang(s_ChanServ, u, CHAN_ACCESS_DELETED_SEVERAL, + deleted, ci->name); + } } else { - notice_lang(s_ChanServ, u, CHAN_ACCESS_DELETED, - access->nc->display, ci->name); - alog("%s: %s!%s@%s (level %d) deleted access of %s (group %s) on %s", s_ChanServ, u->nick, u->username, u->host, get_access(u, ci), na->nick, access->nc->display, chan); - access->nc = NULL; - access->in_use = 0; - deleted = 1; + na = findnick(nick); + if (!na) { + notice_lang(s_ChanServ, u, NICK_X_NOT_REGISTERED, nick); + return MOD_CONT; + } + nc = na->nc; + for (i = 0; i < ci->accesscount; i++) { + if (ci->access[i].nc == nc) + break; + } + if (i == ci->accesscount) { + notice_lang(s_ChanServ, u, CHAN_ACCESS_NOT_FOUND, nick, + chan); + return MOD_CONT; + } + access = &ci->access[i]; + if (!is_servadmin && get_access(u, ci) <= access->level) { + deleted = 0; + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + } else { + notice_lang(s_ChanServ, u, CHAN_ACCESS_DELETED, + access->nc->display, ci->name); + alog("%s: %s!%s@%s (level %d) deleted access of %s (group %s) on %s", s_ChanServ, u->nick, u->GetIdent().c_str(), u->host, get_access(u, ci), na->nick, access->nc->display, chan); + access->nc = NULL; + access->in_use = 0; + deleted = 1; + } } - } - if (deleted) { - /* Reordering - DrStein */ - for (b = 0; b < ci->accesscount; b++) { - if (ci->access[b].in_use) { - for (a = 0; a < ci->accesscount; a++) { - if (a > b) - break; - if (!ci->access[a].in_use) { - ci->access[a].in_use = 1; - ci->access[a].level = ci->access[b].level; - ci->access[a].nc = ci->access[b].nc; - ci->access[a].last_seen = - ci->access[b].last_seen; - ci->access[b].nc = NULL; - ci->access[b].in_use = 0; - break; + if (deleted) { + /* Reordering - DrStein */ + for (b = 0; b < ci->accesscount; b++) { + if (ci->access[b].in_use) { + for (a = 0; a < ci->accesscount; a++) { + if (a > b) + break; + if (!ci->access[a].in_use) { + ci->access[a].in_use = 1; + ci->access[a].level = ci->access[b].level; + ci->access[a].nc = ci->access[b].nc; + ci->access[a].last_seen = + ci->access[b].last_seen; + ci->access[b].nc = NULL; + ci->access[b].in_use = 0; + break; + } } } } - } - /* After reordering only the entries at the end could still be empty. - * We ll free the places no longer in use... */ - for (i = ci->accesscount - 1; i >= 0; i--) { - if (ci->access[i].in_use == 1) - break; + /* After reordering only the entries at the end could still be empty. + * We ll free the places no longer in use... */ + for (i = ci->accesscount - 1; i >= 0; i--) { + if (ci->access[i].in_use == 1) + break; - ci->accesscount--; + ci->accesscount--; + } + ci->access = + static_cast<ChanAccess *>(srealloc(ci->access,sizeof(ChanAccess) * ci->accesscount)); + + /* We don't know the nick if someone used numbers, so we trigger the event without + * nick param. We just do this once, even if someone enters a range. -Certus */ + if (na) + send_event(EVENT_ACCESS_DEL, 3, ci->name, u->nick, na->nick); + else + send_event(EVENT_ACCESS_DEL, 2, ci->name, u->nick); } - ci->access = - static_cast<ChanAccess *>(srealloc(ci->access,sizeof(ChanAccess) * ci->accesscount)); + } else if (stricmp(cmd, "LIST") == 0) { + int sent_header = 0; - /* We don't know the nick if someone used numbers, so we trigger the event without - * nick param. We just do this once, even if someone enters a range. -Certus */ - if (na) - send_event(EVENT_ACCESS_DEL, 3, ci->name, u->nick, na->nick); - else - send_event(EVENT_ACCESS_DEL, 2, ci->name, u->nick); - } - } else if (stricmp(cmd, "LIST") == 0) { - int sent_header = 0; + if (ci->accesscount == 0) { + notice_lang(s_ChanServ, u, CHAN_ACCESS_LIST_EMPTY, chan); + return MOD_CONT; + } + if (nick && strspn(nick, "1234567890,-") == strlen(nick)) { + process_numlist(nick, NULL, access_list_callback, u, ci, + &sent_header); + } else { + for (i = 0; i < ci->accesscount; i++) { + if (nick && ci->access[i].nc + && !match_wild_nocase(nick, ci->access[i].nc->display)) + continue; + access_list(u, i, ci, &sent_header); + } + } + if (!sent_header) { + notice_lang(s_ChanServ, u, CHAN_ACCESS_NO_MATCH, chan); + } else { + notice_lang(s_ChanServ, u, CHAN_ACCESS_LIST_FOOTER, ci->name); + } + } else if (stricmp(cmd, "CLEAR") == 0) { - if (ci->accesscount == 0) { - notice_lang(s_ChanServ, u, CHAN_ACCESS_LIST_EMPTY, chan); - return MOD_CONT; - } - if (nick && strspn(nick, "1234567890,-") == strlen(nick)) { - process_numlist(nick, NULL, access_list_callback, u, ci, - &sent_header); - } else { - for (i = 0; i < ci->accesscount; i++) { - if (nick && ci->access[i].nc - && !match_wild_nocase(nick, ci->access[i].nc->display)) - continue; - access_list(u, i, ci, &sent_header); + if (readonly) { + notice_lang(s_ChanServ, u, CHAN_ACCESS_DISABLED); + return MOD_CONT; } - } - if (!sent_header) { - notice_lang(s_ChanServ, u, CHAN_ACCESS_NO_MATCH, chan); - } else { - notice_lang(s_ChanServ, u, CHAN_ACCESS_LIST_FOOTER, ci->name); - } - } else if (stricmp(cmd, "CLEAR") == 0) { - if (readonly) { - notice_lang(s_ChanServ, u, CHAN_ACCESS_DISABLED); - return MOD_CONT; - } + if (!is_servadmin && !is_founder(u, ci)) { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + return MOD_CONT; + } - if (!is_servadmin && !is_founder(u, ci)) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - return MOD_CONT; - } + free(ci->access); + ci->access = NULL; + ci->accesscount = 0; - free(ci->access); - ci->access = NULL; - ci->accesscount = 0; + send_event(EVENT_ACCESS_CLEAR, 2, ci->name, u->nick); - send_event(EVENT_ACCESS_CLEAR, 2, ci->name, u->nick); + notice_lang(s_ChanServ, u, CHAN_ACCESS_CLEAR, ci->name); + alog("%s: %s!%s@%s (level %d) cleared access list on %s", + s_ChanServ, u->nick, u->GetIdent().c_str(), u->host, + get_access(u, ci), chan); - notice_lang(s_ChanServ, u, CHAN_ACCESS_CLEAR, ci->name); - alog("%s: %s!%s@%s (level %d) cleared access list on %s", - s_ChanServ, u->nick, u->username, u->host, - get_access(u, ci), chan); + } else { + syntax_error(s_ChanServ, u, "ACCESS", CHAN_ACCESS_SYNTAX); + } + return MOD_CONT; + } - } else { - syntax_error(s_ChanServ, u, "ACCESS", CHAN_ACCESS_SYNTAX); + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_ChanServ, u, CHAN_HELP_ACCESS); + notice_lang(s_ChanServ, u, CHAN_HELP_ACCESS_LEVELS); + return true; } - return MOD_CONT; -} +}; -int do_levels(User * u) +class CommandCSLevels : public Command { - char *chan = strtok(NULL, " "); - char *cmd = strtok(NULL, " "); - char *what = strtok(NULL, " "); - char *s = strtok(NULL, " "); - char *error; - - ChannelInfo *ci; - int level; - int i; - - /* If SET, we want two extra parameters; if DIS[ABLE] or FOUNDER, we want only - * one; else, we want none. - */ - if (!cmd - || ((stricmp(cmd, "SET") == 0) ? !s - : ((strnicmp(cmd, "DIS", 3) == 0)) ? (!what || s) : !!what)) { - syntax_error(s_ChanServ, u, "LEVELS", CHAN_LEVELS_SYNTAX); - } else if (!(ci = cs_findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - } else if (ci->flags & CI_XOP) { - notice_lang(s_ChanServ, u, CHAN_LEVELS_XOP); - } else if (!is_founder(u, ci) && !is_services_admin(u)) { - notice_lang(s_ChanServ, u, ACCESS_DENIED); - } else if (stricmp(cmd, "SET") == 0) { - level = strtol(s, &error, 10); - - if (*error != '\0') { - syntax_error(s_ChanServ, u, "LEVELS", CHAN_LEVELS_SYNTAX); - return MOD_CONT; - } - - if (level <= ACCESS_INVALID || level >= ACCESS_FOUNDER) { - notice_lang(s_ChanServ, u, CHAN_LEVELS_RANGE, - ACCESS_INVALID + 1, ACCESS_FOUNDER - 1); - return MOD_CONT; - } - - for (i = 0; levelinfo[i].what >= 0; i++) { - if (stricmp(levelinfo[i].name, what) == 0) { - ci->levels[levelinfo[i].what] = level; + public: + CommandCSLevels() : Command("LEVELS", 2, 4) + { + } - alog("%s: %s!%s@%s set level %s on channel %s to %d", - s_ChanServ, u->nick, u->username, u->host, - levelinfo[i].name, ci->name, level); - notice_lang(s_ChanServ, u, CHAN_LEVELS_CHANGED, - levelinfo[i].name, chan, level); + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + const char *cmd = params[1].c_str(); + const char *what = params[2].c_str(); + const char *s = params[3].c_str(); + char *error; + + ChannelInfo *ci; + int level; + int i; + + /* If SET, we want two extra parameters; if DIS[ABLE] or FOUNDER, we want only + * one; else, we want none. + */ + if (!cmd + || ((stricmp(cmd, "SET") == 0) ? !s + : ((strnicmp(cmd, "DIS", 3) == 0)) ? (!what || s) : !!what)) { + syntax_error(s_ChanServ, u, "LEVELS", CHAN_LEVELS_SYNTAX); + } else if (!(ci = cs_findchan(chan))) { + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + } else if (ci->flags & CI_VERBOTEN) { + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + } else if (ci->flags & CI_XOP) { + notice_lang(s_ChanServ, u, CHAN_LEVELS_XOP); + } else if (!is_founder(u, ci) && !is_services_admin(u)) { + notice_lang(s_ChanServ, u, ACCESS_DENIED); + } else if (stricmp(cmd, "SET") == 0) { + level = strtol(s, &error, 10); + + if (*error != '\0') { + syntax_error(s_ChanServ, u, "LEVELS", CHAN_LEVELS_SYNTAX); return MOD_CONT; } - } - notice_lang(s_ChanServ, u, CHAN_LEVELS_UNKNOWN, what, s_ChanServ); - - } else if (stricmp(cmd, "DIS") == 0 || stricmp(cmd, "DISABLE") == 0) { - for (i = 0; levelinfo[i].what >= 0; i++) { - if (stricmp(levelinfo[i].name, what) == 0) { - ci->levels[levelinfo[i].what] = ACCESS_INVALID; - - alog("%s: %s!%s@%s disabled level %s on channel %s", - s_ChanServ, u->nick, u->username, u->host, - levelinfo[i].name, ci->name); - notice_lang(s_ChanServ, u, CHAN_LEVELS_DISABLED, - levelinfo[i].name, chan); + if (level <= ACCESS_INVALID || level >= ACCESS_FOUNDER) { + notice_lang(s_ChanServ, u, CHAN_LEVELS_RANGE, + ACCESS_INVALID + 1, ACCESS_FOUNDER - 1); return MOD_CONT; } - } - notice_lang(s_ChanServ, u, CHAN_LEVELS_UNKNOWN, what, s_ChanServ); - } else if (stricmp(cmd, "LIST") == 0) { - notice_lang(s_ChanServ, u, CHAN_LEVELS_LIST_HEADER, chan); + for (i = 0; levelinfo[i].what >= 0; i++) { + if (stricmp(levelinfo[i].name, what) == 0) { + ci->levels[levelinfo[i].what] = level; + + alog("%s: %s!%s@%s set level %s on channel %s to %d", + s_ChanServ, u->nick, u->GetIdent().c_str(), u->host, + levelinfo[i].name, ci->name, level); + notice_lang(s_ChanServ, u, CHAN_LEVELS_CHANGED, + levelinfo[i].name, chan, level); + return MOD_CONT; + } + } + + notice_lang(s_ChanServ, u, CHAN_LEVELS_UNKNOWN, what, s_ChanServ); - if (!levelinfo_maxwidth) { + } else if (stricmp(cmd, "DIS") == 0 || stricmp(cmd, "DISABLE") == 0) { for (i = 0; levelinfo[i].what >= 0; i++) { - int len = strlen(levelinfo[i].name); - if (len > levelinfo_maxwidth) - levelinfo_maxwidth = len; + if (stricmp(levelinfo[i].name, what) == 0) { + ci->levels[levelinfo[i].what] = ACCESS_INVALID; + + alog("%s: %s!%s@%s disabled level %s on channel %s", + s_ChanServ, u->nick, u->GetIdent().c_str(), u->host, + levelinfo[i].name, ci->name); + notice_lang(s_ChanServ, u, CHAN_LEVELS_DISABLED, + levelinfo[i].name, chan); + return MOD_CONT; + } } - } - for (i = 0; levelinfo[i].what >= 0; i++) { - int j = ci->levels[levelinfo[i].what]; + notice_lang(s_ChanServ, u, CHAN_LEVELS_UNKNOWN, what, s_ChanServ); + } else if (stricmp(cmd, "LIST") == 0) { + notice_lang(s_ChanServ, u, CHAN_LEVELS_LIST_HEADER, chan); - if (j == ACCESS_INVALID) { - j = levelinfo[i].what; + if (!levelinfo_maxwidth) { + for (i = 0; levelinfo[i].what >= 0; i++) { + int len = strlen(levelinfo[i].name); + if (len > levelinfo_maxwidth) + levelinfo_maxwidth = len; + } + } - if (j == CA_AUTOOP || j == CA_AUTODEOP || j == CA_AUTOVOICE - || j == CA_NOJOIN) { - notice_lang(s_ChanServ, u, CHAN_LEVELS_LIST_DISABLED, + for (i = 0; levelinfo[i].what >= 0; i++) { + int j = ci->levels[levelinfo[i].what]; + + if (j == ACCESS_INVALID) { + j = levelinfo[i].what; + + if (j == CA_AUTOOP || j == CA_AUTODEOP || j == CA_AUTOVOICE + || j == CA_NOJOIN) { + notice_lang(s_ChanServ, u, CHAN_LEVELS_LIST_DISABLED, + levelinfo_maxwidth, levelinfo[i].name); + } else { + notice_lang(s_ChanServ, u, CHAN_LEVELS_LIST_DISABLED, + levelinfo_maxwidth, levelinfo[i].name); + } + } else if (j == ACCESS_FOUNDER) { + notice_lang(s_ChanServ, u, CHAN_LEVELS_LIST_FOUNDER, levelinfo_maxwidth, levelinfo[i].name); } else { - notice_lang(s_ChanServ, u, CHAN_LEVELS_LIST_DISABLED, - levelinfo_maxwidth, levelinfo[i].name); + notice_lang(s_ChanServ, u, CHAN_LEVELS_LIST_NORMAL, + levelinfo_maxwidth, levelinfo[i].name, j); } - } else if (j == ACCESS_FOUNDER) { - notice_lang(s_ChanServ, u, CHAN_LEVELS_LIST_FOUNDER, - levelinfo_maxwidth, levelinfo[i].name); - } else { - notice_lang(s_ChanServ, u, CHAN_LEVELS_LIST_NORMAL, - levelinfo_maxwidth, levelinfo[i].name, j); } + + } else if (stricmp(cmd, "RESET") == 0) { + reset_levels(ci); + + alog("%s: %s!%s@%s reset levels definitions on channel %s", + s_ChanServ, u->nick, u->GetIdent().c_str(), u->host, ci->name); + notice_lang(s_ChanServ, u, CHAN_LEVELS_RESET, chan); + } else { + syntax_error(s_ChanServ, u, "LEVELS", CHAN_LEVELS_SYNTAX); } + return MOD_CONT; + } - } else if (stricmp(cmd, "RESET") == 0) { - reset_levels(ci); + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_ChanServ, u, CHAN_HELP_LEVELS); + return true; + } +}; - alog("%s: %s!%s@%s reset levels definitions on channel %s", - s_ChanServ, u->nick, u->username, u->host, ci->name); - notice_lang(s_ChanServ, u, CHAN_LEVELS_RESET, chan); - } else { - syntax_error(s_ChanServ, u, "LEVELS", CHAN_LEVELS_SYNTAX); + +class CSAccess : public Module +{ + public: + CSAccess(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + + this->AddCommand(CHANSERV, new CommandCSAccess(), MOD_UNIQUE); + this->AddCommand(CHANSERV, new CommandCSLevels(), MOD_UNIQUE); + this->SetChanHelp(myChanServHelp); } - return MOD_CONT; -} +}; + MODULE_INIT("cs_access", CSAccess) diff --git a/src/core/cs_akick.c b/src/core/cs_akick.c index 54fa125a9..3b43f4692 100644 --- a/src/core/cs_akick.c +++ b/src/core/cs_akick.c @@ -16,27 +16,8 @@ #include "module.h" -int do_akick(User * u); void myChanServHelp(User * u); -int get_access_nc(NickCore *nc, ChannelInfo *ci); -class CSAKick : public Module -{ - public: - CSAKick(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("AKICK", do_akick, NULL, CHAN_HELP_AKICK, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - - this->SetChanHelp(myChanServHelp); - } -}; @@ -49,12 +30,6 @@ void myChanServHelp(User * u) notice_lang(s_ChanServ, u, CHAN_HELP_CMD_AKICK); } -/** - * The /cs akick command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ - /* `last' is set to the last index this routine was called with */ int akick_del(User * u, AutoKick * akick) { if (!(akick->flags & AK_USED)) @@ -164,490 +139,523 @@ int akick_view_callback(User * u, int num, va_list args) return akick_view(u, num - 1, ci, sent_header); } +int get_access_nc(NickCore *nc, ChannelInfo *ci) +{ + ChanAccess *access; + if (!ci || !nc) + return 0; + if ((access = get_access_entry(nc, ci))) + return access->level; + return 0; +} -int do_akick(User * u) +class CommandCSAKick : public Command { - char *chan = strtok(NULL, " "); - char *cmd = strtok(NULL, " "); - char *mask = strtok(NULL, " "); - char *reason = strtok(NULL, ""); - ChannelInfo *ci; - AutoKick *akick; - int i; - Channel *c; - struct c_userlist *cu = NULL; - struct c_userlist *next; - User *u2; - const char *argv[3]; - int count = 0; - - if (!cmd || (!mask && (!stricmp(cmd, "ADD") || !stricmp(cmd, "STICK") - || !stricmp(cmd, "UNSTICK") - || !stricmp(cmd, "DEL")))) { - - syntax_error(s_ChanServ, u, "AKICK", CHAN_AKICK_SYNTAX); - } else if (!(ci = cs_findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - } else if (!check_access(u, ci, CA_AKICK) && !is_services_admin(u)) { - notice_lang(s_ChanServ, u, ACCESS_DENIED); - } else if (stricmp(cmd, "ADD") == 0) { - NickAlias *na = findnick(mask), *na2; - NickCore *nc = NULL; - char *nick, *user, *host; - int freemask = 0; - - if (readonly) { - notice_lang(s_ChanServ, u, CHAN_AKICK_DISABLED); - return MOD_CONT; - } + public: + CommandCSAKick() : Command("AKICK", 2, 4) + { + } - if (!na) { - split_usermask(mask, &nick, &user, &host); - mask = new char[strlen(nick) + strlen(user) + strlen(host) + 3]; - freemask = 1; - sprintf(mask, "%s!%s@%s", nick, user, host); - delete [] nick; - delete [] user; - delete [] host; - } else { - if (na->status & NS_VERBOTEN) { - notice_lang(s_ChanServ, u, NICK_X_FORBIDDEN, mask); + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + const char *cmd = params[1].c_str(); + const char *mask = params[2].c_str(); + if (params[5].length() > 200) + params[5].resize(200); // XXX: is this right? + const char *reason = params[5].c_str(); + ChannelInfo *ci; + AutoKick *akick; + int i; + Channel *c; + struct c_userlist *cu = NULL; + struct c_userlist *unext; + User *u2; + const char *argv[3]; + int count = 0; + + if (!cmd || (!mask && (!stricmp(cmd, "ADD") || !stricmp(cmd, "STICK") + || !stricmp(cmd, "UNSTICK") + || !stricmp(cmd, "DEL")))) { + + syntax_error(s_ChanServ, u, "AKICK", CHAN_AKICK_SYNTAX); + } else if (!(ci = cs_findchan(chan))) { + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + } else if (ci-> flags & CI_VERBOTEN) { + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + } else if (!check_access(u, ci, CA_AKICK) && !is_services_admin(u)) { + notice_lang(s_ChanServ, u, ACCESS_DENIED); + } else if (stricmp(cmd, "ADD") == 0) { + NickAlias *na = findnick(mask), *na2; + NickCore *nc = NULL; + char *nick, *user, *host; + int freemask = 0; + + if (readonly) { + notice_lang(s_ChanServ, u, CHAN_AKICK_DISABLED); return MOD_CONT; } - nc = na->nc; - } - /* Check excepts BEFORE we get this far */ - if (ircd->except) { - if (is_excepted_mask(ci, mask) == 1) { - notice_lang(s_ChanServ, u, CHAN_EXCEPTED, mask, chan); - if (freemask) - delete [] mask; - return MOD_CONT; + if (!na) { + split_usermask(mask, &nick, &user, &host); + char *smask = new char[strlen(nick) + strlen(user) + strlen(host) + 3]; + freemask = 1; + sprintf(smask, "%s!%s@%s", nick, user, host); + mask = smask; + delete [] nick; + delete [] user; + delete [] host; + } else { + if (na->status & NS_VERBOTEN) { + notice_lang(s_ChanServ, u, NICK_X_FORBIDDEN, mask); + return MOD_CONT; + } + nc = na->nc; } - } - /* Check whether target nick has equal/higher access - * or whether the mask matches a user with higher/equal access - Viper */ - if ((ci->flags & CI_PEACE) && nc) { - if ((nc == ci->founder) || (get_access_nc(nc, ci) >= get_access(u, ci))) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - if (freemask) - delete [] mask; - return MOD_CONT; + /* Check excepts BEFORE we get this far */ + if (ircd->except) { + if (is_excepted_mask(ci, mask) == 1) { + notice_lang(s_ChanServ, u, CHAN_EXCEPTED, mask, chan); + if (freemask) + delete [] mask; + return MOD_CONT; + } } - } else if ((ci->flags & CI_PEACE)) { - char buf[BUFSIZE]; - /* Match against all currently online users with equal or - * higher access. - Viper */ - for (i = 0; i < 1024; i++) { - for (u2 = userlist[i]; u2; u2 = u2->next) { - if (is_founder(u2, ci) || (get_access(u2, ci) >= get_access(u, ci))) { - if (match_usermask(mask, u2)) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - delete [] mask; - return MOD_CONT; + + /* Check whether target nick has equal/higher access + * or whether the mask matches a user with higher/equal access - Viper */ + if ((ci->flags & CI_PEACE) && nc) { + if ((nc == ci->founder) || (get_access_nc(nc, ci) >= get_access(u, ci))) { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + if (freemask) + delete [] mask; + return MOD_CONT; + } + } else if ((ci->flags & CI_PEACE)) { + char buf[BUFSIZE]; + /* Match against all currently online users with equal or + * higher access. - Viper */ + for (i = 0; i < 1024; i++) { + for (u2 = userlist[i]; u2; u2 = u2->next) { + if (is_founder(u2, ci) || (get_access(u2, ci) >= get_access(u, ci))) { + if (match_usermask(mask, u2)) { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + delete [] mask; + return MOD_CONT; + } } } } - } - - /* Match against the lastusermask of all nickalias's with equal - * or higher access. - Viper */ - for (i = 0; i < 1024; i++) { - for (na2 = nalists[i]; na2; na2 = na2->next) { - if (na2->status & NS_VERBOTEN) - continue; - if (na2->nc && ((na2->nc == ci->founder) || (get_access_nc(na2->nc, ci) - >= get_access(u, ci)))) { - snprintf(buf, BUFSIZE, "%s!%s", na2->nick, na2->last_usermask); - if (match_wild_nocase(mask, buf)) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - delete [] mask; - return MOD_CONT; + /* Match against the lastusermask of all nickalias's with equal + * or higher access. - Viper */ + for (i = 0; i < 1024; i++) { + for (na2 = nalists[i]; na2; na2 = na2->next) { + if (na2->status & NS_VERBOTEN) + continue; + + if (na2->nc && ((na2->nc == ci->founder) || (get_access_nc(na2->nc, ci) + >= get_access(u, ci)))) { + snprintf(buf, BUFSIZE, "%s!%s", na2->nick, na2->last_usermask); + if (match_wild_nocase(mask, buf)) { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + delete [] mask; + return MOD_CONT; + } } } } } - } - for (akick = ci->akick, i = 0; i < ci->akickcount; akick++, i++) { - if (!(akick->flags & AK_USED)) - continue; - if ((akick->flags & AK_ISNICK) ? akick->u.nc == nc - : stricmp(akick->u.mask, mask) == 0) { - notice_lang(s_ChanServ, u, CHAN_AKICK_ALREADY_EXISTS, - (akick->flags & AK_ISNICK) ? akick->u.nc-> - display : akick->u.mask, chan); + for (akick = ci->akick, i = 0; i < ci->akickcount; akick++, i++) { + if (!(akick->flags & AK_USED)) + continue; + if ((akick->flags & AK_ISNICK) ? akick->u.nc == nc + : stricmp(akick->u.mask, mask) == 0) { + notice_lang(s_ChanServ, u, CHAN_AKICK_ALREADY_EXISTS, + (akick->flags & AK_ISNICK) ? akick->u.nc-> + display : akick->u.mask, chan); + if (freemask) + delete [] mask; + return MOD_CONT; + } + } + + + /* All entries should be in use so we don't have to go over + * the entire list. We simply add new entries at the end. */ + if (ci->akickcount >= CSAutokickMax) { + notice_lang(s_ChanServ, u, CHAN_AKICK_REACHED_LIMIT, CSAutokickMax); if (freemask) delete [] mask; return MOD_CONT; } - } - - /* All entries should be in use so we don't have to go over - * the entire list. We simply add new entries at the end. */ - if (ci->akickcount >= CSAutokickMax) { - notice_lang(s_ChanServ, u, CHAN_AKICK_REACHED_LIMIT, CSAutokickMax); - if (freemask) - delete [] mask; - return MOD_CONT; - } - ci->akickcount++; - ci->akick = - static_cast<AutoKick *>(srealloc(ci->akick, sizeof(AutoKick) * ci->akickcount)); - akick = &ci->akick[i]; - akick->flags = AK_USED; - if (nc) { - akick->flags |= AK_ISNICK; - akick->u.nc = nc; - } else { - akick->u.mask = sstrdup(mask); - } - akick->creator = sstrdup(u->nick); - akick->addtime = time(NULL); - if (reason) { - if (strlen(reason) > 200) - reason[200] = '\0'; - akick->reason = sstrdup(reason); - } else { - akick->reason = NULL; - } - - /* Auto ENFORCE #63 */ - c = findchan(ci->name); - if (c) { - cu = c->users; - while (cu) { - next = cu->next; - if (check_kick(cu->user, c->name, c->creation_time)) { - argv[0] = sstrdup(c->name); - argv[1] = sstrdup(cu->user->nick); - if (akick->reason) - argv[2] = sstrdup(akick->reason); - else - argv[2] = sstrdup("none"); - - do_kick(s_ChanServ, 3, argv); + ci->akickcount++; + ci->akick = + static_cast<AutoKick *>(srealloc(ci->akick, sizeof(AutoKick) * ci->akickcount)); + akick = &ci->akick[i]; + akick->flags = AK_USED; + if (nc) { + akick->flags |= AK_ISNICK; + akick->u.nc = nc; + } else { + akick->u.mask = sstrdup(mask); + } + akick->creator = sstrdup(u->nick); + akick->addtime = time(NULL); + if (reason) { + akick->reason = sstrdup(reason); + } else { + akick->reason = NULL; + } - delete [] argv[2]; - delete [] argv[1]; - delete [] argv[0]; - count++; + /* Auto ENFORCE #63 */ + c = findchan(ci->name); + if (c) { + cu = c->users; + while (cu) { + unext = cu->next; + if (check_kick(cu->user, c->name, c->creation_time)) { + argv[0] = sstrdup(c->name); + argv[1] = sstrdup(cu->user->nick); + if (akick->reason) + argv[2] = sstrdup(akick->reason); + else + argv[2] = sstrdup("none"); + + do_kick(s_ChanServ, 3, argv); + + delete [] argv[2]; + delete [] argv[1]; + delete [] argv[0]; + count++; + } + cu = unext; } - cu = next; } - } - notice_lang(s_ChanServ, u, CHAN_AKICK_ADDED, mask, chan); + notice_lang(s_ChanServ, u, CHAN_AKICK_ADDED, mask, chan); - if (count) - notice_lang(s_ChanServ, u, CHAN_AKICK_ENFORCE_DONE, chan, - count); + if (count) + notice_lang(s_ChanServ, u, CHAN_AKICK_ENFORCE_DONE, chan, + count); - if (freemask) - delete [] mask; + if (freemask) + delete [] mask; - } else if (stricmp(cmd, "STICK") == 0) { - NickAlias *na; - NickCore *nc; + } else if (stricmp(cmd, "STICK") == 0) { + NickAlias *na; + NickCore *nc; - if (readonly) { - notice_lang(s_ChanServ, u, CHAN_AKICK_DISABLED); - return MOD_CONT; - } + if (readonly) { + notice_lang(s_ChanServ, u, CHAN_AKICK_DISABLED); + return MOD_CONT; + } - if (ci->akickcount == 0) { - notice_lang(s_ChanServ, u, CHAN_AKICK_LIST_EMPTY, ci->name); - return MOD_CONT; - } + if (ci->akickcount == 0) { + notice_lang(s_ChanServ, u, CHAN_AKICK_LIST_EMPTY, ci->name); + return MOD_CONT; + } - na = findnick(mask); - nc = (na ? na->nc : NULL); + na = findnick(mask); + nc = (na ? na->nc : NULL); - for (akick = ci->akick, i = 0; i < ci->akickcount; akick++, i++) { - if (!(akick->flags & AK_USED) || (akick->flags & AK_ISNICK)) - continue; - if (!stricmp(akick->u.mask, mask)) - break; - } + for (akick = ci->akick, i = 0; i < ci->akickcount; akick++, i++) { + if (!(akick->flags & AK_USED) || (akick->flags & AK_ISNICK)) + continue; + if (!stricmp(akick->u.mask, mask)) + break; + } + + if (i == ci->akickcount) { + notice_lang(s_ChanServ, u, CHAN_AKICK_NOT_FOUND, mask, + ci->name); + return MOD_CONT; + } - if (i == ci->akickcount) { - notice_lang(s_ChanServ, u, CHAN_AKICK_NOT_FOUND, mask, + akick->flags |= AK_STUCK; + notice_lang(s_ChanServ, u, CHAN_AKICK_STUCK, akick->u.mask, ci->name); - return MOD_CONT; - } - akick->flags |= AK_STUCK; - notice_lang(s_ChanServ, u, CHAN_AKICK_STUCK, akick->u.mask, - ci->name); + if (ci->c) + stick_mask(ci, akick); + } else if (stricmp(cmd, "UNSTICK") == 0) { + NickAlias *na; + NickCore *nc; - if (ci->c) - stick_mask(ci, akick); - } else if (stricmp(cmd, "UNSTICK") == 0) { - NickAlias *na; - NickCore *nc; + if (readonly) { + notice_lang(s_ChanServ, u, CHAN_AKICK_DISABLED); + return MOD_CONT; + } - if (readonly) { - notice_lang(s_ChanServ, u, CHAN_AKICK_DISABLED); - return MOD_CONT; - } + if (ci->akickcount == 0) { + notice_lang(s_ChanServ, u, CHAN_AKICK_LIST_EMPTY, ci->name); + return MOD_CONT; + } - if (ci->akickcount == 0) { - notice_lang(s_ChanServ, u, CHAN_AKICK_LIST_EMPTY, ci->name); - return MOD_CONT; - } + na = findnick(mask); + nc = (na ? na->nc : NULL); - na = findnick(mask); - nc = (na ? na->nc : NULL); + for (akick = ci->akick, i = 0; i < ci->akickcount; akick++, i++) { + if (!(akick->flags & AK_USED) || (akick->flags & AK_ISNICK)) + continue; + if (!stricmp(akick->u.mask, mask)) + break; + } - for (akick = ci->akick, i = 0; i < ci->akickcount; akick++, i++) { - if (!(akick->flags & AK_USED) || (akick->flags & AK_ISNICK)) - continue; - if (!stricmp(akick->u.mask, mask)) - break; - } + if (i == ci->akickcount) { + notice_lang(s_ChanServ, u, CHAN_AKICK_NOT_FOUND, mask, + ci->name); + return MOD_CONT; + } - if (i == ci->akickcount) { - notice_lang(s_ChanServ, u, CHAN_AKICK_NOT_FOUND, mask, + akick->flags &= ~AK_STUCK; + notice_lang(s_ChanServ, u, CHAN_AKICK_UNSTUCK, akick->u.mask, ci->name); - return MOD_CONT; - } - - akick->flags &= ~AK_STUCK; - notice_lang(s_ChanServ, u, CHAN_AKICK_UNSTUCK, akick->u.mask, - ci->name); - } else if (stricmp(cmd, "DEL") == 0) { - int deleted, a, b; + } else if (stricmp(cmd, "DEL") == 0) { + int deleted, a, b; - if (readonly) { - notice_lang(s_ChanServ, u, CHAN_AKICK_DISABLED); - return MOD_CONT; - } + if (readonly) { + notice_lang(s_ChanServ, u, CHAN_AKICK_DISABLED); + return MOD_CONT; + } - if (ci->akickcount == 0) { - notice_lang(s_ChanServ, u, CHAN_AKICK_LIST_EMPTY, chan); - return MOD_CONT; - } + if (ci->akickcount == 0) { + notice_lang(s_ChanServ, u, CHAN_AKICK_LIST_EMPTY, chan); + return MOD_CONT; + } - /* Special case: is it a number/list? Only do search if it isn't. */ - if (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask)) { - int last = -1; - deleted = process_numlist(mask, &count, akick_del_callback, u, - ci, &last); - if (!deleted) { - if (count == 1) { - notice_lang(s_ChanServ, u, CHAN_AKICK_NO_SUCH_ENTRY, - last, ci->name); - } else { - notice_lang(s_ChanServ, u, CHAN_AKICK_NO_MATCH, + /* Special case: is it a number/list? Only do search if it isn't. */ + if (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask)) { + int last = -1; + deleted = process_numlist(mask, &count, akick_del_callback, u, + ci, &last); + if (!deleted) { + if (count == 1) { + notice_lang(s_ChanServ, u, CHAN_AKICK_NO_SUCH_ENTRY, + last, ci->name); + } else { + notice_lang(s_ChanServ, u, CHAN_AKICK_NO_MATCH, + ci->name); + } + } else if (deleted == 1) { + notice_lang(s_ChanServ, u, CHAN_AKICK_DELETED_ONE, ci->name); + } else { + notice_lang(s_ChanServ, u, CHAN_AKICK_DELETED_SEVERAL, + deleted, ci->name); } - } else if (deleted == 1) { - notice_lang(s_ChanServ, u, CHAN_AKICK_DELETED_ONE, - ci->name); } else { - notice_lang(s_ChanServ, u, CHAN_AKICK_DELETED_SEVERAL, - deleted, ci->name); - } - } else { - NickAlias *na = findnick(mask); - NickCore *nc = (na ? na->nc : NULL); + NickAlias *na = findnick(mask); + NickCore *nc = (na ? na->nc : NULL); - for (akick = ci->akick, i = 0; i < ci->akickcount; - akick++, i++) { - if (!(akick->flags & AK_USED)) - continue; - if (((akick->flags & AK_ISNICK) && akick->u.nc == nc) - || (!(akick->flags & AK_ISNICK) - && stricmp(akick->u.mask, mask) == 0)) - break; - } - if (i == ci->akickcount) { - notice_lang(s_ChanServ, u, CHAN_AKICK_NOT_FOUND, mask, - chan); - return MOD_CONT; + for (akick = ci->akick, i = 0; i < ci->akickcount; + akick++, i++) { + if (!(akick->flags & AK_USED)) + continue; + if (((akick->flags & AK_ISNICK) && akick->u.nc == nc) + || (!(akick->flags & AK_ISNICK) + && stricmp(akick->u.mask, mask) == 0)) + break; + } + if (i == ci->akickcount) { + notice_lang(s_ChanServ, u, CHAN_AKICK_NOT_FOUND, mask, + chan); + return MOD_CONT; + } + notice_lang(s_ChanServ, u, CHAN_AKICK_DELETED, mask, chan); + akick_del(u, akick); + deleted = 1; } - notice_lang(s_ChanServ, u, CHAN_AKICK_DELETED, mask, chan); - akick_del(u, akick); - deleted = 1; - } - if (deleted) { - /* Reordering - DrStein */ - for (b = 0; b < ci->akickcount; b++) { - if (ci->akick[b].flags & AK_USED) { - for (a = 0; a < ci->akickcount; a++) { - if (a > b) - break; - if (!(ci->akick[a].flags & AK_USED)) { - ci->akick[a].flags = ci->akick[b].flags; - if (ci->akick[b].flags & AK_ISNICK) { - ci->akick[a].u.nc = ci->akick[b].u.nc; - } else { - ci->akick[a].u.mask = - sstrdup(ci->akick[b].u.mask); + if (deleted) { + /* Reordering - DrStein */ + for (b = 0; b < ci->akickcount; b++) { + if (ci->akick[b].flags & AK_USED) { + for (a = 0; a < ci->akickcount; a++) { + if (a > b) + break; + if (!(ci->akick[a].flags & AK_USED)) { + ci->akick[a].flags = ci->akick[b].flags; + if (ci->akick[b].flags & AK_ISNICK) { + ci->akick[a].u.nc = ci->akick[b].u.nc; + } else { + ci->akick[a].u.mask = + sstrdup(ci->akick[b].u.mask); + } + /* maybe we should first check whether there + is a reason before we sstdrup it -Certus */ + if (ci->akick[b].reason) + ci->akick[a].reason = + sstrdup(ci->akick[b].reason); + else + ci->akick[a].reason = NULL; + ci->akick[a].creator = + sstrdup(ci->akick[b].creator); + ci->akick[a].addtime = ci->akick[b].addtime; + + akick_del(u, &ci->akick[b]); + break; } - /* maybe we should first check whether there - is a reason before we sstdrup it -Certus */ - if (ci->akick[b].reason) - ci->akick[a].reason = - sstrdup(ci->akick[b].reason); - else - ci->akick[a].reason = NULL; - ci->akick[a].creator = - sstrdup(ci->akick[b].creator); - ci->akick[a].addtime = ci->akick[b].addtime; - - akick_del(u, &ci->akick[b]); - break; } } } - } - /* After reordering only the entries at the end could still be empty. - * We ll free the places no longer in use... - Viper */ - for (i = ci->akickcount - 1; i >= 0; i--) { - if (ci->akick[i].flags & AK_USED) - break; + /* After reordering only the entries at the end could still be empty. + * We ll free the places no longer in use... - Viper */ + for (i = ci->akickcount - 1; i >= 0; i--) { + if (ci->akick[i].flags & AK_USED) + break; - ci->akickcount--; + ci->akickcount--; + } + ci->akick = + static_cast<AutoKick *>(srealloc(ci->akick,sizeof(AutoKick) * ci->akickcount)); } - ci->akick = - static_cast<AutoKick *>(srealloc(ci->akick,sizeof(AutoKick) * ci->akickcount)); - } - } else if (stricmp(cmd, "LIST") == 0) { - int sent_header = 0; + } else if (stricmp(cmd, "LIST") == 0) { + int sent_header = 0; - if (ci->akickcount == 0) { - notice_lang(s_ChanServ, u, CHAN_AKICK_LIST_EMPTY, chan); - return MOD_CONT; - } - if (mask && isdigit(*mask) && - strspn(mask, "1234567890,-") == strlen(mask)) { - process_numlist(mask, NULL, akick_list_callback, u, ci, - &sent_header); - } else { - for (akick = ci->akick, i = 0; i < ci->akickcount; - akick++, i++) { - if (!(akick->flags & AK_USED)) - continue; - if (mask) { - if (!(akick->flags & AK_ISNICK) - && !match_wild_nocase(mask, akick->u.mask)) - continue; - if ((akick->flags & AK_ISNICK) - && !match_wild_nocase(mask, akick->u.nc->display)) + if (ci->akickcount == 0) { + notice_lang(s_ChanServ, u, CHAN_AKICK_LIST_EMPTY, chan); + return MOD_CONT; + } + if (mask && isdigit(*mask) && + strspn(mask, "1234567890,-") == strlen(mask)) { + process_numlist(mask, NULL, akick_list_callback, u, ci, + &sent_header); + } else { + for (akick = ci->akick, i = 0; i < ci->akickcount; + akick++, i++) { + if (!(akick->flags & AK_USED)) continue; + if (mask) { + if (!(akick->flags & AK_ISNICK) + && !match_wild_nocase(mask, akick->u.mask)) + continue; + if ((akick->flags & AK_ISNICK) + && !match_wild_nocase(mask, akick->u.nc->display)) + continue; + } + akick_list(u, i, ci, &sent_header); } - akick_list(u, i, ci, &sent_header); } - } - if (!sent_header) - notice_lang(s_ChanServ, u, CHAN_AKICK_NO_MATCH, chan); - - } else if (stricmp(cmd, "VIEW") == 0) { - int sent_header = 0; + if (!sent_header) + notice_lang(s_ChanServ, u, CHAN_AKICK_NO_MATCH, chan); - if (ci->akickcount == 0) { - notice_lang(s_ChanServ, u, CHAN_AKICK_LIST_EMPTY, chan); - return MOD_CONT; - } - if (mask && isdigit(*mask) && - strspn(mask, "1234567890,-") == strlen(mask)) { - process_numlist(mask, NULL, akick_view_callback, u, ci, - &sent_header); - } else { - for (akick = ci->akick, i = 0; i < ci->akickcount; - akick++, i++) { - if (!(akick->flags & AK_USED)) - continue; - if (mask) { - if (!(akick->flags & AK_ISNICK) - && !match_wild_nocase(mask, akick->u.mask)) - continue; - if ((akick->flags & AK_ISNICK) - && !match_wild_nocase(mask, akick->u.nc->display)) + } else if (stricmp(cmd, "VIEW") == 0) { + int sent_header = 0; + if (ci->akickcount == 0) { + notice_lang(s_ChanServ, u, CHAN_AKICK_LIST_EMPTY, chan); + return MOD_CONT; + } + if (mask && isdigit(*mask) && + strspn(mask, "1234567890,-") == strlen(mask)) { + process_numlist(mask, NULL, akick_view_callback, u, ci, + &sent_header); + } else { + for (akick = ci->akick, i = 0; i < ci->akickcount; + akick++, i++) { + if (!(akick->flags & AK_USED)) continue; + if (mask) { + if (!(akick->flags & AK_ISNICK) + && !match_wild_nocase(mask, akick->u.mask)) + continue; + if ((akick->flags & AK_ISNICK) + && !match_wild_nocase(mask, akick->u.nc->display)) + continue; + } + akick_view(u, i, ci, &sent_header); } - akick_view(u, i, ci, &sent_header); } - } - if (!sent_header) - notice_lang(s_ChanServ, u, CHAN_AKICK_NO_MATCH, chan); + if (!sent_header) + notice_lang(s_ChanServ, u, CHAN_AKICK_NO_MATCH, chan); - } else if (stricmp(cmd, "ENFORCE") == 0) { - c = findchan(ci->name); - cu = NULL; - count = 0; + } else if (stricmp(cmd, "ENFORCE") == 0) { + c = findchan(ci->name); + cu = NULL; + count = 0; - if (!c) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, ci->name); - return MOD_CONT; - } + if (!c) { + notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, ci->name); + return MOD_CONT; + } - cu = c->users; + cu = c->users; - while (cu) { - next = cu->next; - if (check_kick(cu->user, c->name, c->creation_time)) { - argv[0] = sstrdup(c->name); - argv[1] = sstrdup(cu->user->nick); - argv[2] = sstrdup(CSAutokickReason); + while (cu) { + unext = cu->next; + if (check_kick(cu->user, c->name, c->creation_time)) { + argv[0] = sstrdup(c->name); + argv[1] = sstrdup(cu->user->nick); + argv[2] = sstrdup(CSAutokickReason); - do_kick(s_ChanServ, 3, argv); + do_kick(s_ChanServ, 3, argv); - delete [] argv[2]; - delete [] argv[1]; - delete [] argv[0]; + delete [] argv[2]; + delete [] argv[1]; + delete [] argv[0]; - count++; + count++; + } + cu = unext; } - cu = next; - } - notice_lang(s_ChanServ, u, CHAN_AKICK_ENFORCE_DONE, chan, count); + notice_lang(s_ChanServ, u, CHAN_AKICK_ENFORCE_DONE, chan, count); - } else if (stricmp(cmd, "CLEAR") == 0) { + } else if (stricmp(cmd, "CLEAR") == 0) { - if (readonly) { - notice_lang(s_ChanServ, u, CHAN_AKICK_DISABLED); - return MOD_CONT; - } + if (readonly) { + notice_lang(s_ChanServ, u, CHAN_AKICK_DISABLED); + return MOD_CONT; + } - for (akick = ci->akick, i = 0; i < ci->akickcount; akick++, i++) { - if (!(akick->flags & AK_USED)) - continue; - akick_del(u, akick); - } + for (akick = ci->akick, i = 0; i < ci->akickcount; akick++, i++) { + if (!(akick->flags & AK_USED)) + continue; + akick_del(u, akick); + } - free(ci->akick); - ci->akick = NULL; - ci->akickcount = 0; + free(ci->akick); + ci->akick = NULL; + ci->akickcount = 0; - notice_lang(s_ChanServ, u, CHAN_AKICK_CLEAR, ci->name); + notice_lang(s_ChanServ, u, CHAN_AKICK_CLEAR, ci->name); - } else { + } else { + syntax_error(s_ChanServ, u, "AKICK", CHAN_AKICK_SYNTAX); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_ChanServ, u, CHAN_HELP_AKICK); + return true; + } + + void OnSyntaxError(User *u) + { syntax_error(s_ChanServ, u, "AKICK", CHAN_AKICK_SYNTAX); } - return MOD_CONT; -} +}; -int get_access_nc(NickCore *nc, ChannelInfo *ci) -{ - ChanAccess *access; - if (!ci || !nc) - return 0; - if ((access = get_access_entry(nc, ci))) - return access->level; - return 0; -} +class CSAKick : public Module +{ + public: + CSAKick(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(CHANSERV, new CommandCSAKick(), MOD_UNIQUE); + + this->SetChanHelp(myChanServHelp); + } +}; MODULE_INIT("cs_akick", CSAKick) diff --git a/src/core/cs_ban.c b/src/core/cs_ban.c index f1da5f2a6..9f4ddd023 100644 --- a/src/core/cs_ban.c +++ b/src/core/cs_ban.c @@ -15,30 +15,8 @@ #include "module.h" -int do_unban(User * u); -int do_ban(User * u); void myChanServHelp(User * u); -class CSBan : public Module -{ - public: - CSBan(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("BAN", do_ban, NULL, CHAN_HELP_BAN, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - c = createCommand("UNBAN", do_unban, NULL, CHAN_HELP_UNBAN, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - - this->SetChanHelp(myChanServHelp); - } -}; - /** * Add the help response to anopes /cs help output. @@ -50,167 +28,172 @@ void myChanServHelp(User * u) notice_lang(s_ChanServ, u, CHAN_HELP_CMD_UNBAN); } -/** - * The /cs ban command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_ban(User * u) +class CommandCSBan : public Command { - char *chan = strtok(NULL, " "); - char *params = strtok(NULL, " "); - char *reason = strtok(NULL, ""); + public: + CommandCSBan() : Command("BAN", 1, 3) + { - Channel *c; - ChannelInfo *ci; - User *u2; + } - int is_same; + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + const char *target = params[1].c_str(); + params[2].resize(200); + const char *reason = params[2].c_str(); - if (!reason) { - reason = const_cast<char *>("Requested"); // XXX unsafe cast -- w00t - } else { - if (strlen(reason) > 200) - reason[200] = '\0'; - } + Channel *c; + ChannelInfo *ci; + User *u2; - if (!chan) { - struct u_chanlist *uc, *next; - - /* Bans the user on every channels he is on. */ - - for (uc = u->chans; uc; uc = next) { - next = uc->next; - if ((ci = uc->chan->ci) && !(ci->flags & CI_VERBOTEN) - && check_access(u, ci, CA_BANME)) { - const char *av[3]; - char mask[BUFSIZE]; - - /* - * Dont ban/kick the user on channels where he is excepted - * to prevent services <-> server wars. - */ - if (ircd->except) { - if (is_excepted(ci, u)) - notice_lang(s_ChanServ, u, CHAN_EXCEPTED, - u->nick, ci->name); - continue; - } - if (is_protected(u)) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - continue; - } - - av[0] = "+b"; - get_idealban(ci, u, mask, sizeof(mask)); - av[1] = mask; - ircdproto->SendMode(whosends(ci), uc->chan->name, "+b %s", - av[1]); - chan_set_modes(s_ChanServ, uc->chan, 2, av, 1); - - if ((ci->flags & CI_SIGNKICK) - || ((ci->flags & CI_SIGNKICK_LEVEL) - && !check_access(u, ci, CA_SIGNKICK))) - ircdproto->SendKick(whosends(ci), ci->name, u->nick, - "%s (%s)", reason, u->nick); - else - ircdproto->SendKick(whosends(ci), ci->name, u->nick, "%s", - reason); - - const char *kav[4]; - kav[0] = ci->name; - kav[1] = u->nick; - kav[2] = reason; - do_kick(s_ChanServ, 3, kav); - } + if (!chan) + return MOD_CONT; + + int is_same; + + if (!reason) + reason = "Requested"; + + if (!target) + target = u->nick; + + is_same = (stricmp(target, u->nick) == 0); + + if (!(c = findchan(chan))) { + notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); + } else if (!(ci = c->ci)) { + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + } else if (ci->flags & CI_VERBOTEN) { + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + } else if (is_same ? !(u2 = u) : !(u2 = finduser(target))) { + notice_lang(s_ChanServ, u, NICK_X_NOT_IN_USE, target); + } else if (!is_same ? !check_access(u, ci, CA_BAN) : + !check_access(u, ci, CA_BANME)) { + notice_lang(s_ChanServ, u, ACCESS_DENIED); + } else if (!is_same && (ci->flags & CI_PEACE) + && (get_access(u2, ci) >= get_access(u, ci))) { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + /* + * Dont ban/kick the user on channels where he is excepted + * to prevent services <-> server wars. + */ + } else if (ircd->except && is_excepted(ci, u2)) { + notice_lang(s_ChanServ, u, CHAN_EXCEPTED, u2->nick, ci->name); + } else if (ircd->protectedumode && is_protected(u2)) { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + } else { + const char *av[3]; + char mask[BUFSIZE]; + + av[0] = "+b"; + get_idealban(ci, u2, mask, sizeof(mask)); + av[1] = mask; + ircdproto->SendMode(whosends(ci), c->name, "+b %s", av[1]); + chan_set_modes(s_ChanServ, c, 2, av, 1); + + /* We still allow host banning while not allowing to kick */ + if (!is_on_chan(c, u2)) + return MOD_CONT; + + if ((ci->flags & CI_SIGNKICK) + || ((ci->flags & CI_SIGNKICK_LEVEL) + && !check_access(u, ci, CA_SIGNKICK))) + ircdproto->SendKick(whosends(ci), ci->name, target, "%s (%s)", + reason, u->nick); + else + ircdproto->SendKick(whosends(ci), ci->name, target, "%s", reason); + + const char *kav[4]; + kav[0] = ci->name; + kav[1] = target; + kav[2] = reason; + do_kick(s_ChanServ, 3, kav); } return MOD_CONT; - } else if (!params) { - params = u->nick; } - is_same = (params == u->nick) ? 1 : (stricmp(params, u->nick) == 0); - - if (!(c = findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); - } else if (!(ci = c->ci)) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - } else if (is_same ? !(u2 = u) : !(u2 = finduser(params))) { - notice_lang(s_ChanServ, u, NICK_X_NOT_IN_USE, params); - } else if (!is_same ? !check_access(u, ci, CA_BAN) : - !check_access(u, ci, CA_BANME)) { - notice_lang(s_ChanServ, u, ACCESS_DENIED); - } else if (!is_same && (ci->flags & CI_PEACE) - && (get_access(u2, ci) >= get_access(u, ci))) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - /* - * Dont ban/kick the user on channels where he is excepted - * to prevent services <-> server wars. - */ - } else if (ircd->except && is_excepted(ci, u2)) { - notice_lang(s_ChanServ, u, CHAN_EXCEPTED, u2->nick, ci->name); - } else if (ircd->protectedumode && is_protected(u2)) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - } else { - const char *av[3]; - char mask[BUFSIZE]; - - av[0] = "+b"; - get_idealban(ci, u2, mask, sizeof(mask)); - av[1] = mask; - ircdproto->SendMode(whosends(ci), c->name, "+b %s", av[1]); - chan_set_modes(s_ChanServ, c, 2, av, 1); - - /* We still allow host banning while not allowing to kick */ - if (!is_on_chan(c, u2)) - return MOD_CONT; - - if ((ci->flags & CI_SIGNKICK) - || ((ci->flags & CI_SIGNKICK_LEVEL) - && !check_access(u, ci, CA_SIGNKICK))) - ircdproto->SendKick(whosends(ci), ci->name, params, "%s (%s)", - reason, u->nick); - else - ircdproto->SendKick(whosends(ci), ci->name, params, "%s", reason); - - const char *kav[4]; - kav[0] = ci->name; - kav[1] = params; - kav[2] = reason; - do_kick(s_ChanServ, 3, kav); + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_ChanServ, u, CHAN_HELP_BAN); + return true; } - return MOD_CONT; -} +}; -/** - * The /cs unban command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_unban(User * u) + + +class CommandCSUnban : public Command { - char *chan = strtok(NULL, " "); - Channel *c; - ChannelInfo *ci; + public: + CommandCSUnban() : Command("UNBAN", 1, 1) + { + + } + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + char *chan = strtok(NULL, " "); + Channel *c; + ChannelInfo *ci; + + if (!(c = findchan(chan))) + { + notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); + return MOD_CONT; + } + + if (!(ci = c->ci)) + { + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + return MOD_CONT; + } + + if (ci->flags & CI_VERBOTEN) + { + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } + + if (!check_access(u, ci, CA_UNBAN)) + { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + return MOD_CONT; + } - if (!chan) { - syntax_error(s_ChanServ, u, "UNBAN", CHAN_UNBAN_SYNTAX); - } else if (!(c = findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); - } else if (!(ci = c->ci)) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - } else if (!check_access(u, ci, CA_UNBAN)) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - } else { common_unban(ci, u->nick); notice_lang(s_ChanServ, u, CHAN_UNBANNED, chan); + return MOD_CONT; } - return MOD_CONT; -} + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_ChanServ, u, CHAN_HELP_UNBAN); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_ChanServ, u, "UNBAN", CHAN_UNBAN_SYNTAX); + } +}; + + + +class CSBan : public Module +{ + public: + CSBan(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(CHANSERV, new CommandCSBan(), MOD_UNIQUE); + this->AddCommand(CHANSERV, new CommandCSUnban(), MOD_UNIQUE); + + this->SetChanHelp(myChanServHelp); + } +}; + MODULE_INIT("cs_ban", CSBan) diff --git a/src/core/cs_clear.c b/src/core/cs_clear.c index b67af5817..db90da572 100644 --- a/src/core/cs_clear.c +++ b/src/core/cs_clear.c @@ -15,29 +15,8 @@ #include "module.h" -int do_clear(User * u); void myChanServHelp(User * u); -class CSClear : public Module -{ - public: - CSClear(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("CLEAR", do_clear, NULL, CHAN_HELP_CLEAR, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - - this->SetChanHelp(myChanServHelp); - } -}; - - - /** * Add the help response to anopes /cs help output. * @param u The user who is requesting help @@ -47,315 +26,344 @@ void myChanServHelp(User * u) notice_lang(s_ChanServ, u, CHAN_HELP_CMD_CLEAR); } -/** - * The /cs clear command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_clear(User * u) +class CommandCSClear : public Command { - char *chan = strtok(NULL, " "); - char *what = strtok(NULL, " "); - Channel *c; - ChannelInfo *ci; + public: + CommandCSClear() : Command("CLEAR", 2, 2) + { - if (!what) { - syntax_error(s_ChanServ, u, "CLEAR", CHAN_CLEAR_SYNTAX); - } else if (!(c = findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); - } else if (!(ci = c->ci)) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - } else if (!u || !check_access(u, ci, CA_CLEAR)) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - } else if (stricmp(what, "bans") == 0) { - const char *av[2]; - Entry *ban, *next; - - if (c->bans && c->bans->count) { - for (ban = c->bans->entries; ban; ban = next) { - next = ban->next; - av[0] = "-b"; - av[1] = ban->mask; - ircdproto->SendMode(whosends(ci), chan, "-b %s", ban->mask); - chan_set_modes(whosends(ci)->nick, c, 2, av, 0); - } - } + } - notice_lang(s_ChanServ, u, CHAN_CLEARED_BANS, chan); - } else if (ircd->except && stricmp(what, "excepts") == 0) { - const char *av[2]; - Entry *except, *next; - - if (c->excepts && c->excepts->count) { - for (except = c->excepts->entries; except; except = next) { - next = except->next; - av[0] = "-e"; - av[1] = except->mask; - ircdproto->SendMode(whosends(ci), chan, "-e %s", except->mask); - chan_set_modes(whosends(ci)->nick, c, 2, av, 0); - } - } - notice_lang(s_ChanServ, u, CHAN_CLEARED_EXCEPTS, chan); - - } else if (ircd->invitemode && stricmp(what, "invites") == 0) { - const char *av[2]; - Entry *invite, *next; - - if (c->invites && c->invites->count) { - for (invite = c->invites->entries; invite; invite = next) { - next = invite->next; - av[0] = "-I"; - av[1] = invite->mask; - ircdproto->SendMode(whosends(ci), chan, "-I %s", invite->mask); - chan_set_modes(whosends(ci)->nick, c, 2, av, 0); + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + const char *what = params[1].c_str(); + Channel *c; + ChannelInfo *ci; + + if (!what) { + syntax_error(s_ChanServ, u, "CLEAR", CHAN_CLEAR_SYNTAX); + } else if (!(c = findchan(chan))) { + notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); + } else if (!(ci = c->ci)) { + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + } else if (ci->flags & CI_VERBOTEN) { + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + } else if (!u || !check_access(u, ci, CA_CLEAR)) { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + } else if (stricmp(what, "bans") == 0) { + const char *av[2]; + Entry *ban, *bnext; + + if (c->bans && c->bans->count) { + for (ban = c->bans->entries; ban; ban = bnext) { + bnext = ban->next; + av[0] = "-b"; + av[1] = ban->mask; + ircdproto->SendMode(whosends(ci), chan, "-b %s", ban->mask); + chan_set_modes(whosends(ci)->nick, c, 2, av, 0); + } } - } - notice_lang(s_ChanServ, u, CHAN_CLEARED_INVITES, chan); - - } else if (stricmp(what, "modes") == 0) { - const char *argv[2]; - - if (c->mode) { - /* Clear modes the bulk of the modes */ - ircdproto->SendMode(whosends(ci), c->name, "%s", - ircd->modestoremove); - argv[0] = ircd->modestoremove; - chan_set_modes(whosends(ci)->nick, c, 1, argv, 0); - - /* to prevent the internals from complaining send -k, -L, -f by themselves if we need - to send them - TSL */ - if (c->key) { - ircdproto->SendMode(whosends(ci), c->name, "-k %s", c->key); - argv[0] = "-k"; - argv[1] = c->key; - chan_set_modes(whosends(ci)->nick, c, 2, argv, 0); + + notice_lang(s_ChanServ, u, CHAN_CLEARED_BANS, chan); + } else if (ircd->except && stricmp(what, "excepts") == 0) { + const char *av[2]; + Entry *except, *bnext; + + if (c->excepts && c->excepts->count) { + for (except = c->excepts->entries; except; except = bnext) { + bnext = except->next; + av[0] = "-e"; + av[1] = except->mask; + ircdproto->SendMode(whosends(ci), chan, "-e %s", except->mask); + chan_set_modes(whosends(ci)->nick, c, 2, av, 0); + } } - if (ircd->Lmode && c->redirect) { - ircdproto->SendMode(whosends(ci), c->name, "-L %s", - c->redirect); - argv[0] = "-L"; - argv[1] = c->redirect; - chan_set_modes(whosends(ci)->nick, c, 2, argv, 0); + notice_lang(s_ChanServ, u, CHAN_CLEARED_EXCEPTS, chan); + + } else if (ircd->invitemode && stricmp(what, "invites") == 0) { + const char *av[2]; + Entry *invite, *bnext; + + if (c->invites && c->invites->count) { + for (invite = c->invites->entries; invite; invite = bnext) { + bnext = invite->next; + av[0] = "-I"; + av[1] = invite->mask; + ircdproto->SendMode(whosends(ci), chan, "-I %s", invite->mask); + chan_set_modes(whosends(ci)->nick, c, 2, av, 0); + } } - if (ircd->fmode && c->flood) { - if (flood_mode_char_remove) { - ircdproto->SendMode(whosends(ci), c->name, "%s %s", - flood_mode_char_remove, c->flood); - argv[0] = flood_mode_char_remove; - argv[1] = c->flood; + notice_lang(s_ChanServ, u, CHAN_CLEARED_INVITES, chan); + + } else if (stricmp(what, "modes") == 0) { + const char *argv[2]; + + if (c->mode) { + /* Clear modes the bulk of the modes */ + ircdproto->SendMode(whosends(ci), c->name, "%s", + ircd->modestoremove); + argv[0] = ircd->modestoremove; + chan_set_modes(whosends(ci)->nick, c, 1, argv, 0); + + /* to prevent the internals from complaining send -k, -L, -f by themselves if we need + to send them - TSL */ + if (c->key) { + ircdproto->SendMode(whosends(ci), c->name, "-k %s", c->key); + argv[0] = "-k"; + argv[1] = c->key; chan_set_modes(whosends(ci)->nick, c, 2, argv, 0); - } else { - if (debug) { - alog("debug: flood_mode_char_remove was not set unable to remove flood/throttle modes"); + } + if (ircd->Lmode && c->redirect) { + ircdproto->SendMode(whosends(ci), c->name, "-L %s", + c->redirect); + argv[0] = "-L"; + argv[1] = c->redirect; + chan_set_modes(whosends(ci)->nick, c, 2, argv, 0); + } + if (ircd->fmode && c->flood) { + if (flood_mode_char_remove) { + ircdproto->SendMode(whosends(ci), c->name, "%s %s", + flood_mode_char_remove, c->flood); + argv[0] = flood_mode_char_remove; + argv[1] = c->flood; + chan_set_modes(whosends(ci)->nick, c, 2, argv, 0); + } else { + if (debug) { + alog("debug: flood_mode_char_remove was not set unable to remove flood/throttle modes"); + } } } + check_modes(c); } - check_modes(c); - } - notice_lang(s_ChanServ, u, CHAN_CLEARED_MODES, chan); - } else if (stricmp(what, "ops") == 0) { - const char *av[6]; /* The max we have to hold: chan, ts, modes(max3), nick, nick, nick */ - int ac, isop, isadmin, isown, count, i; - char buf[BUFSIZE], tmp[BUFSIZE], tmp2[BUFSIZE]; - struct c_userlist *cu, *next; - - if (ircd->svsmode_ucmode) { - av[0] = chan; - ircdproto->SendSVSModeChan(av[0], "-o", NULL); - if (ircd->owner) { - ircdproto->SendSVSModeChan(av[0], ircd->ownerunset, NULL); - } - if (ircd->protect || ircd->admin) { - ircdproto->SendSVSModeChan(av[0], ircd->adminunset, NULL); + notice_lang(s_ChanServ, u, CHAN_CLEARED_MODES, chan); + } else if (stricmp(what, "ops") == 0) { + const char *av[6]; /* The max we have to hold: chan, ts, modes(max3), nick, nick, nick */ + int ac, isop, isadmin, isown, count, i; + char buf[BUFSIZE], tmp[BUFSIZE], tmp2[BUFSIZE]; + struct c_userlist *cu, *bnext; + + if (ircd->svsmode_ucmode) { + av[0] = chan; + ircdproto->SendSVSModeChan(av[0], "-o", NULL); + if (ircd->owner) { + ircdproto->SendSVSModeChan(av[0], ircd->ownerunset, NULL); + } + if (ircd->protect || ircd->admin) { + ircdproto->SendSVSModeChan(av[0], ircd->adminunset, NULL); + } + for (cu = c->users; cu; cu = bnext) { + bnext = cu->next; + isop = chan_has_user_status(c, cu->user, CUS_OP); + isadmin = chan_has_user_status(c, cu->user, CUS_PROTECT); + isown = chan_has_user_status(c, cu->user, CUS_OWNER); + count = (isop ? 1 : 0) + (isadmin ? 1 : 0) + (isown ? 1 : 0); + + if (!isop && !isadmin && !isown) + continue; + + snprintf(tmp, BUFSIZE, "-%s%s%s", (isop ? "o" : ""), (isadmin ? + ircd->adminunset+1 : ""), (isown ? ircd->ownerunset+1 : "")); + + if (ircdcap->tsmode) { + snprintf(buf, BUFSIZE - 1, "%ld", static_cast<long>(time(NULL))); + av[1] = buf; + av[2] = tmp; + /* We have to give as much nicks as modes.. - Viper */ + for (i = 0; i < count; i++) + av[i+3] = cu->user->nick; + ac = 3 + i; + } else { + av[1] = tmp; + /* We have to give as much nicks as modes.. - Viper */ + for (i = 0; i < count; i++) + av[i+2] = cu->user->nick; + ac = 2 + i; + } + + do_cmode(s_ChanServ, ac, av); + } + } else { + av[0] = chan; + for (cu = c->users; cu; cu = bnext) { + bnext = cu->next; + isop = chan_has_user_status(c, cu->user, CUS_OP); + isadmin = chan_has_user_status(c, cu->user, CUS_PROTECT); + isown = chan_has_user_status(c, cu->user, CUS_OWNER); + count = (isop ? 1 : 0) + (isadmin ? 1 : 0) + (isown ? 1 : 0); + + if (!isop && !isadmin && !isown) + continue; + + snprintf(tmp, BUFSIZE, "-%s%s%s", (isop ? "o" : ""), (isadmin ? + ircd->adminunset+1 : ""), (isown ? ircd->ownerunset+1 : "")); + /* We need to send the IRCd a nick for every mode.. - Viper */ + snprintf(tmp2, BUFSIZE, "%s %s %s", (isop ? cu->user->nick : ""), + (isadmin ? cu->user->nick : ""), (isown ? cu->user->nick : "")); + + if (ircdcap->tsmode) { + snprintf(buf, BUFSIZE - 1, "%ld", static_cast<long>(time(NULL))); + av[1] = buf; + av[2] = tmp; + /* We have to give as much nicks as modes.. - Viper */ + for (i = 0; i < count; i++) + av[i+3] = cu->user->nick; + ac = 3 + i; + + ircdproto->SendMode(whosends(ci), av[0], "%s %s", av[2], tmp2); + } else { + av[1] = tmp; + /* We have to give as much nicks as modes.. - Viper */ + for (i = 0; i < count; i++) + av[i+2] = cu->user->nick; + ac = 2 + i; + + ircdproto->SendMode(whosends(ci), av[0], "%s %s", av[1], tmp2); + } + + do_cmode(s_ChanServ, ac, av); + } } - for (cu = c->users; cu; cu = next) { - next = cu->next; - isop = chan_has_user_status(c, cu->user, CUS_OP); - isadmin = chan_has_user_status(c, cu->user, CUS_PROTECT); - isown = chan_has_user_status(c, cu->user, CUS_OWNER); - count = (isop ? 1 : 0) + (isadmin ? 1 : 0) + (isown ? 1 : 0); - - if (!isop && !isadmin && !isown) + notice_lang(s_ChanServ, u, CHAN_CLEARED_OPS, chan); + } else if (ircd->halfop && stricmp(what, "hops") == 0) { + const char *av[4]; + int ac; + char buf[BUFSIZE]; + struct c_userlist *cu, *bnext; + + for (cu = c->users; cu; cu = bnext) { + bnext = cu->next; + if (!chan_has_user_status(c, cu->user, CUS_HALFOP)) continue; - snprintf(tmp, BUFSIZE, "-%s%s%s", (isop ? "o" : ""), (isadmin ? - ircd->adminunset+1 : ""), (isown ? ircd->ownerunset+1 : "")); - if (ircdcap->tsmode) { snprintf(buf, BUFSIZE - 1, "%ld", static_cast<long>(time(NULL))); + av[0] = chan; av[1] = buf; - av[2] = tmp; - /* We have to give as much nicks as modes.. - Viper */ - for (i = 0; i < count; i++) - av[i+3] = cu->user->nick; - ac = 3 + i; + av[2] = "-h"; + av[3] = cu->user->nick; + ac = 4; } else { - av[1] = tmp; - /* We have to give as much nicks as modes.. - Viper */ - for (i = 0; i < count; i++) - av[i+2] = cu->user->nick; - ac = 2 + i; + av[0] = chan; + av[1] = "-h"; + av[2] = cu->user->nick; + ac = 3; } + if (ircd->svsmode_ucmode) { + if (ircdcap->tsmode) + ircdproto->SendSVSModeChan(av[0], av[2], NULL); + else + ircdproto->SendSVSModeChan(av[0], av[1], NULL); + + do_cmode(s_ChanServ, ac, av); + break; + } else { + if (ircdcap->tsmode) + ircdproto->SendMode(whosends(ci), av[0], "%s %s", av[2], + av[3]); + else + ircdproto->SendMode(whosends(ci), av[0], "%s %s", av[1], + av[2]); + } do_cmode(s_ChanServ, ac, av); } - } else { - av[0] = chan; - for (cu = c->users; cu; cu = next) { - next = cu->next; - isop = chan_has_user_status(c, cu->user, CUS_OP); - isadmin = chan_has_user_status(c, cu->user, CUS_PROTECT); - isown = chan_has_user_status(c, cu->user, CUS_OWNER); - count = (isop ? 1 : 0) + (isadmin ? 1 : 0) + (isown ? 1 : 0); - - if (!isop && !isadmin && !isown) + notice_lang(s_ChanServ, u, CHAN_CLEARED_HOPS, chan); + } else if (stricmp(what, "voices") == 0) { + const char *av[4]; + int ac; + char buf[BUFSIZE]; + struct c_userlist *cu, *bnext; + + for (cu = c->users; cu; cu = bnext) { + bnext = cu->next; + if (!chan_has_user_status(c, cu->user, CUS_VOICE)) continue; - snprintf(tmp, BUFSIZE, "-%s%s%s", (isop ? "o" : ""), (isadmin ? - ircd->adminunset+1 : ""), (isown ? ircd->ownerunset+1 : "")); - /* We need to send the IRCd a nick for every mode.. - Viper */ - snprintf(tmp2, BUFSIZE, "%s %s %s", (isop ? cu->user->nick : ""), - (isadmin ? cu->user->nick : ""), (isown ? cu->user->nick : "")); - if (ircdcap->tsmode) { - snprintf(buf, BUFSIZE - 1, "%ld", static_cast<long>(time(NULL))); + snprintf(buf, BUFSIZE - 1, "%ld", static_cast<long int>(time(NULL))); + av[0] = chan; av[1] = buf; - av[2] = tmp; - /* We have to give as much nicks as modes.. - Viper */ - for (i = 0; i < count; i++) - av[i+3] = cu->user->nick; - ac = 3 + i; - - ircdproto->SendMode(whosends(ci), av[0], "%s %s", av[2], tmp2); + av[2] = "-v"; + av[3] = cu->user->nick; + ac = 4; } else { - av[1] = tmp; - /* We have to give as much nicks as modes.. - Viper */ - for (i = 0; i < count; i++) - av[i+2] = cu->user->nick; - ac = 2 + i; - - ircdproto->SendMode(whosends(ci), av[0], "%s %s", av[1], tmp2); + av[0] = chan; + av[1] = "-v"; + av[2] = cu->user->nick; + ac = 3; } - do_cmode(s_ChanServ, ac, av); - } - } - notice_lang(s_ChanServ, u, CHAN_CLEARED_OPS, chan); - } else if (ircd->halfop && stricmp(what, "hops") == 0) { - const char *av[4]; - int ac; - char buf[BUFSIZE]; - struct c_userlist *cu, *next; - - for (cu = c->users; cu; cu = next) { - next = cu->next; - if (!chan_has_user_status(c, cu->user, CUS_HALFOP)) - continue; - - if (ircdcap->tsmode) { - snprintf(buf, BUFSIZE - 1, "%ld", static_cast<long>(time(NULL))); - av[0] = chan; - av[1] = buf; - av[2] = "-h"; - av[3] = cu->user->nick; - ac = 4; - } else { - av[0] = chan; - av[1] = "-h"; - av[2] = cu->user->nick; - ac = 3; - } - - if (ircd->svsmode_ucmode) { - if (ircdcap->tsmode) - ircdproto->SendSVSModeChan(av[0], av[2], NULL); - else - ircdproto->SendSVSModeChan(av[0], av[1], NULL); + if (ircd->svsmode_ucmode) { + if (ircdcap->tsmode) + ircdproto->SendSVSModeChan(av[0], av[2], NULL); + else + ircdproto->SendSVSModeChan(av[0], av[1], NULL); + do_cmode(s_ChanServ, ac, av); + break; + } else { + if (ircdcap->tsmode) { + ircdproto->SendMode(whosends(ci), av[0], "%s %s", av[2], + av[3]); + } else { + ircdproto->SendMode(whosends(ci), av[0], "%s %s", av[1], + av[2]); + } + } do_cmode(s_ChanServ, ac, av); - break; - } else { - if (ircdcap->tsmode) - ircdproto->SendMode(whosends(ci), av[0], "%s %s", av[2], - av[3]); - else - ircdproto->SendMode(whosends(ci), av[0], "%s %s", av[1], - av[2]); } - do_cmode(s_ChanServ, ac, av); - } - notice_lang(s_ChanServ, u, CHAN_CLEARED_HOPS, chan); - } else if (stricmp(what, "voices") == 0) { - const char *av[4]; - int ac; - char buf[BUFSIZE]; - struct c_userlist *cu, *next; - - for (cu = c->users; cu; cu = next) { - next = cu->next; - if (!chan_has_user_status(c, cu->user, CUS_VOICE)) - continue; - - if (ircdcap->tsmode) { - snprintf(buf, BUFSIZE - 1, "%ld", static_cast<long int>(time(NULL))); - av[0] = chan; - av[1] = buf; - av[2] = "-v"; - av[3] = cu->user->nick; - ac = 4; - } else { - av[0] = chan; - av[1] = "-v"; - av[2] = cu->user->nick; - ac = 3; + notice_lang(s_ChanServ, u, CHAN_CLEARED_VOICES, chan); + } else if (stricmp(what, "users") == 0) { + const char *av[3]; + struct c_userlist *cu, *bnext; + char buf[256]; + + snprintf(buf, sizeof(buf), "CLEAR USERS command from %s", u->nick); + + for (cu = c->users; cu; cu = bnext) { + bnext = cu->next; + av[0] = sstrdup(chan); + av[1] = sstrdup(cu->user->nick); + av[2] = sstrdup(buf); + ircdproto->SendKick(whosends(ci), av[0], av[1], av[2]); + do_kick(s_ChanServ, 3, av); + delete [] av[2]; + delete [] av[1]; + delete [] av[0]; } + notice_lang(s_ChanServ, u, CHAN_CLEARED_USERS, chan); + } else { + syntax_error(s_ChanServ, u, "CLEAR", CHAN_CLEAR_SYNTAX); + } + return MOD_CONT; + } - if (ircd->svsmode_ucmode) { - if (ircdcap->tsmode) - ircdproto->SendSVSModeChan(av[0], av[2], NULL); - else - ircdproto->SendSVSModeChan(av[0], av[1], NULL); + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_ChanServ, u, CHAN_HELP_CLEAR); + return true; + } - do_cmode(s_ChanServ, ac, av); - break; - } else { - if (ircdcap->tsmode) { - ircdproto->SendMode(whosends(ci), av[0], "%s %s", av[2], - av[3]); - } else { - ircdproto->SendMode(whosends(ci), av[0], "%s %s", av[1], - av[2]); - } - } - do_cmode(s_ChanServ, ac, av); - } - notice_lang(s_ChanServ, u, CHAN_CLEARED_VOICES, chan); - } else if (stricmp(what, "users") == 0) { - const char *av[3]; - struct c_userlist *cu, *next; - char buf[256]; - - snprintf(buf, sizeof(buf), "CLEAR USERS command from %s", u->nick); - - for (cu = c->users; cu; cu = next) { - next = cu->next; - av[0] = sstrdup(chan); - av[1] = sstrdup(cu->user->nick); - av[2] = sstrdup(buf); - ircdproto->SendKick(whosends(ci), av[0], av[1], av[2]); - do_kick(s_ChanServ, 3, av); - delete [] av[2]; - delete [] av[1]; - delete [] av[0]; - } - notice_lang(s_ChanServ, u, CHAN_CLEARED_USERS, chan); - } else { + void OnSyntaxError(User *u) + { syntax_error(s_ChanServ, u, "CLEAR", CHAN_CLEAR_SYNTAX); } - return MOD_CONT; -} +}; + +class CSClear : public Module +{ + public: + CSClear(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(CHANSERV, new CommandCSClear(), MOD_UNIQUE); + + this->SetChanHelp(myChanServHelp); + } +}; MODULE_INIT("cs_clear", CSClear) diff --git a/src/core/cs_drop.c b/src/core/cs_drop.c index 21293b025..b44499f0e 100644 --- a/src/core/cs_drop.c +++ b/src/core/cs_drop.c @@ -15,29 +15,8 @@ #include "module.h" -int do_drop(User * u); void myChanServHelp(User * u); -class CSDrop : public Module -{ - public: - CSDrop(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("DROP", do_drop, NULL, -1, CHAN_HELP_DROP, -1, CHAN_SERVADMIN_HELP_DROP, CHAN_SERVADMIN_HELP_DROP); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - - this->SetChanHelp(myChanServHelp); - } -}; - - - /** * Add the help response to anopes /cs help output. @@ -48,55 +27,67 @@ void myChanServHelp(User * u) notice_lang(s_ChanServ, u, CHAN_HELP_CMD_DROP); } -/** - * The /cs command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_drop(User * u) +class CommandCSDrop : public Command { - char *chan = strtok(NULL, " "); - ChannelInfo *ci; - int is_servadmin = is_services_admin(u); - - if (readonly && !is_servadmin) { - notice_lang(s_ChanServ, u, CHAN_DROP_DISABLED); - return MOD_CONT; + public: + CommandCSDrop() : Command("DROP", 1, 1) + { } - if (!chan) { - syntax_error(s_ChanServ, u, "DROP", CHAN_DROP_SYNTAX); - } else if (!(ci = cs_findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (!is_servadmin && (ci->flags & CI_VERBOTEN)) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - } else if (!is_servadmin && (ci->flags & CI_SUSPENDED)) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - } else if (!is_servadmin - && (ci-> - flags & CI_SECUREFOUNDER ? !is_real_founder(u, - ci) : - !is_founder(u, ci))) { - notice_lang(s_ChanServ, u, ACCESS_DENIED); - } else { - int level = get_access(u, ci); + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + char *chan = strtok(NULL, " "); + ChannelInfo *ci; + int is_servadmin = is_services_admin(u); + + if (readonly) + { + notice_lang(s_ChanServ, u, CHAN_DROP_DISABLED); // XXX: READ_ONLY_MODE? + return MOD_CONT; + } + + if (!(ci = cs_findchan(chan))) + { + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + return MOD_CONT; + } - if (readonly) /* in this case we know they're a Services admin */ - notice_lang(s_ChanServ, u, READ_ONLY_MODE); + if (!is_servadmin && (ci->flags & CI_VERBOTEN)) + { + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } + + if (!is_servadmin && (ci->flags & CI_SUSPENDED)) + { + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } - if (ci->c) { - if (ircd->regmode) { + if (!is_servadmin && (ci->flags & CI_SECUREFOUNDER ? !is_real_founder(u, ci) : !is_founder(u, ci))) + { + notice_lang(s_ChanServ, u, ACCESS_DENIED); + return MOD_CONT; + } + + int level = get_access(u, ci); + + if (ci->c) + { + if (ircd->regmode) + { ci->c->mode &= ~ircd->regmode; ircdproto->SendMode(whosends(ci), ci->name, "-r"); } } - if (ircd->chansqline && (ci->flags & CI_VERBOTEN)) { + if (ircd->chansqline && (ci->flags & CI_VERBOTEN)) + { ircdproto->SendSQLineDel(ci->name); } alog("%s: Channel %s dropped by %s!%s@%s (founder: %s)", - s_ChanServ, ci->name, u->nick, u->username, + s_ChanServ, ci->name, u->nick, u->GetIdent().c_str(), u->host, (ci->founder ? ci->founder->display : "(none)")); delchan(ci); @@ -105,14 +96,46 @@ int do_drop(User * u) * drop the channel before issuing the wallops. */ if (WallDrop && is_servadmin && level < ACCESS_FOUNDER) - ircdproto->SendGlobops(s_ChanServ, - "\2%s\2 used DROP on channel \2%s\2", u->nick, - chan); + ircdproto->SendGlobops(s_ChanServ, "\2%s\2 used DROP on channel \2%s\2", u->nick, chan); notice_lang(s_ChanServ, u, CHAN_DROPPED, chan); send_event(EVENT_CHAN_DROP, 1, chan); + return MOD_CONT; } - return MOD_CONT; -} + + bool OnHelp(User *u, const std::string &subcommand) + { + if (is_services_admin(u) || is_services_root(u)) + notice_lang(s_ChanServ, u, CHAN_SERVADMIN_HELP_DROP); + else + notice_lang(s_ChanServ, u, CHAN_HELP_DROP); + + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_ChanServ, u, "DROP", CHAN_DROP_SYNTAX); + } +}; + + + +class CSDrop : public Module +{ + public: + CSDrop(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(CHANSERV, new CommandCSDrop(), MOD_UNIQUE); + + this->SetChanHelp(myChanServHelp); + } +}; + + + MODULE_INIT("cs_drop", CSDrop) diff --git a/src/core/cs_forbid.c b/src/core/cs_forbid.c index 5b19f0bfd..936e98a91 100644 --- a/src/core/cs_forbid.c +++ b/src/core/cs_forbid.c @@ -15,28 +15,8 @@ #include "module.h" -int do_forbid(User * u); void myChanServHelp(User * u); -class CSForbid : public Module -{ - public: - CSForbid(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("FORBID", do_forbid, is_services_admin, -1, -1, -1, CHAN_SERVADMIN_HELP_FORBID, CHAN_SERVADMIN_HELP_FORBID); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - - this->SetChanHelp(myChanServHelp); - } -}; - - /** * Add the help response to anopes /cs help output. * @param u The user who is requesting help @@ -48,50 +28,71 @@ void myChanServHelp(User * u) } } -/** - * The /cs forbid command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_forbid(User * u) +class CommandCSForbid : public Command { - ChannelInfo *ci; - char *chan = strtok(NULL, " "); - char *reason = strtok(NULL, ""); - - Channel *c; + public: + CommandCSForbid() : Command("FORBID", 1, 2) + { - /* Assumes that permission checking has already been done. */ - if (!chan || (ForceForbidReason && !reason)) { - syntax_error(s_ChanServ, u, "FORBID", - (ForceForbidReason ? CHAN_FORBID_SYNTAX_REASON : - CHAN_FORBID_SYNTAX)); - return MOD_CONT; - } - if (*chan != '#') { - notice_lang(s_ChanServ, u, CHAN_SYMBOL_REQUIRED); - return MOD_CONT; - } else if (!ircdproto->IsChannelValid(chan)) { - notice_lang(s_ChanServ, u, CHAN_X_INVALID, chan); - return MOD_CONT; } - if (readonly) - notice_lang(s_ChanServ, u, READ_ONLY_MODE); - if ((ci = cs_findchan(chan)) != NULL) - delchan(ci); - ci = makechan(chan); - if (ci) { + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + ChannelInfo *ci; + const char *chan = params[0].c_str(); + const char *reason = params[1].c_str(); + + Channel *c; + + if (ForceForbidReason && !reason) + { + syntax_error(s_ChanServ, u, "FORBID", CHAN_FORBID_SYNTAX_REASON); + return MOD_CONT; + } + + if (*chan != '#') + { + notice_lang(s_ChanServ, u, CHAN_SYMBOL_REQUIRED); + return MOD_CONT; + } + + if (!ircdproto->IsChannelValid(chan)) + { + notice_lang(s_ChanServ, u, CHAN_X_INVALID, chan); + return MOD_CONT; + } + + if (readonly) + { + notice_lang(s_ChanServ, u, READ_ONLY_MODE); + return MOD_CONT; + + } + + if ((ci = cs_findchan(chan)) != NULL) + delchan(ci); + + ci = makechan(chan); + if (!ci) + { + alog("%s: Valid FORBID for %s by %s failed", s_ChanServ, ci->name, u->nick); + notice_lang(s_ChanServ, u, CHAN_FORBID_FAILED, chan); + return MOD_CONT; + } + ci->flags |= CI_VERBOTEN; ci->forbidby = sstrdup(u->nick); if (reason) ci->forbidreason = sstrdup(reason); - if ((c = findchan(ci->name))) { - struct c_userlist *cu, *next; + if ((c = findchan(ci->name))) + { + struct c_userlist *cu, *nextu; const char *av[3]; - for (cu = c->users; cu; cu = next) { - next = cu->next; + for (cu = c->users; cu; cu = nextu) + { + nextu = cu->next; if (is_oper(cu->user)) continue; @@ -105,24 +106,44 @@ int do_forbid(User * u) } if (WallForbid) - ircdproto->SendGlobops(s_ChanServ, - "\2%s\2 used FORBID on channel \2%s\2", - u->nick, ci->name); + ircdproto->SendGlobops(s_ChanServ, "\2%s\2 used FORBID on channel \2%s\2", u->nick, ci->name); - if (ircd->chansqline) { + if (ircd->chansqline) + { ircdproto->SendSQLine(ci->name, ((reason) ? reason : "Forbidden")); } - alog("%s: %s set FORBID for channel %s", s_ChanServ, u->nick, - ci->name); + alog("%s: %s set FORBID for channel %s", s_ChanServ, u->nick, ci->name); notice_lang(s_ChanServ, u, CHAN_FORBID_SUCCEEDED, chan); send_event(EVENT_CHAN_FORBIDDEN, 1, chan); - } else { - alog("%s: Valid FORBID for %s by %s failed", s_ChanServ, ci->name, - u->nick); - notice_lang(s_ChanServ, u, CHAN_FORBID_FAILED, chan); + return MOD_CONT; } - return MOD_CONT; -} + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_ChanServ, u, CHAN_SERVADMIN_HELP_FORBID); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_ChanServ, u, "FORBID", CHAN_FORBID_SYNTAX); + } +}; + +class CSForbid : public Module +{ + public: + CSForbid(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(CHANSERV, new CommandCSForbid(), MOD_UNIQUE); + + this->SetChanHelp(myChanServHelp); + } +}; + MODULE_INIT("cs_forbid", CSForbid) diff --git a/src/core/cs_getkey.c b/src/core/cs_getkey.c index 5b30c18aa..17659df5d 100644 --- a/src/core/cs_getkey.c +++ b/src/core/cs_getkey.c @@ -15,28 +15,6 @@ #include "module.h" -int do_getkey(User * u); -void myChanServHelp(User * u); - -class CSGetKey : public Module -{ - public: - CSGetKey(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("GETKEY", do_getkey, NULL, CHAN_HELP_GETKEY, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - - this->SetChanHelp(myChanServHelp); - } -}; - - /** * Add the help response to anopes /cs help output. @@ -47,31 +25,72 @@ void myChanServHelp(User * u) notice_lang(s_ChanServ, u, CHAN_HELP_CMD_GETKEY); } -/** - * The /cs getkey command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_getkey(User * u) +class CommandCSGetKey : public Command { - char *chan = strtok(NULL, " "); - ChannelInfo *ci; + public: + CommandCSGetKey() : Command("GETKEY", 1, 1) + { + + } + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + ChannelInfo *ci; + + if (!(ci = cs_findchan(chan))) + { + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + return MOD_CONT; + } + + if (ci->flags & CI_VERBOTEN) + { + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } + + if (!check_access(u, ci, CA_GETKEY)) + { + notice_lang(s_ChanServ, u, ACCESS_DENIED); + return MOD_CONT; + } + + if (!ci->c || !ci->c->key) + { + notice_lang(s_ChanServ, u, CHAN_GETKEY_NOKEY, chan); + return MOD_CONT; + } - if (!chan) { - syntax_error(s_ChanServ, u, "GETKEY", CHAN_GETKEY_SYNTAX); - } else if (!(ci = cs_findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - } else if (!check_access(u, ci, CA_GETKEY)) { - notice_lang(s_ChanServ, u, ACCESS_DENIED); - } else if (!ci->c || !ci->c->key) { - notice_lang(s_ChanServ, u, CHAN_GETKEY_NOKEY, chan); - } else { notice_lang(s_ChanServ, u, CHAN_GETKEY_KEY, chan, ci->c->key); + return MOD_CONT; } - return MOD_CONT; -} + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_ChanServ, u, CHAN_HELP_GETKEY); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_ChanServ, u, "GETKEY", CHAN_GETKEY_SYNTAX); + } +}; + + +class CSGetKey : public Module +{ + public: + CSGetKey(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(CHANSERV, new CommandCSGetKey(), MOD_UNIQUE); + + this->SetChanHelp(myChanServHelp); + } +}; MODULE_INIT("cs_getkey", CSGetKey) diff --git a/src/core/cs_getpass.c b/src/core/cs_getpass.c index 5e0b53876..1dc6aa5dc 100644 --- a/src/core/cs_getpass.c +++ b/src/core/cs_getpass.c @@ -15,29 +15,6 @@ #include "module.h" -int do_getpass(User * u); -void myChanServHelp(User * u); - -class CSGetPass : public Module -{ - public: - CSGetPass(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("GETPASS", do_getpass, is_services_admin, -1, -1, -1, CHAN_SERVADMIN_HELP_GETPASS, CHAN_SERVADMIN_HELP_GETPASS); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - - this->SetChanHelp(myChanServHelp); - } -}; - - - /** * Add the help response to anopes /cs help output. * @param u The user who is requesting help @@ -49,42 +26,79 @@ void myChanServHelp(User * u) } } -/** - * The /cs getpass command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ - -int do_getpass(User * u) +class CommandCSGetPass : public Command { - char *chan = strtok(NULL, " "); - char tmp_pass[PASSMAX]; - ChannelInfo *ci; + public: + CommandCSGetPass() : Command("GETPASS", 1, 1) + { + this->has_priv = is_services_admin; + } - if (!chan) { - syntax_error(s_ChanServ, u, "GETPASS", CHAN_GETPASS_SYNTAX); - } else if (!(ci = cs_findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - } else if (CSRestrictGetPass && !is_services_root(u)) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - } else { - if(enc_decrypt(ci->founderpass, tmp_pass, PASSMAX - 1)==1) { - alog("%s: %s!%s@%s used GETPASS on %s", - s_ChanServ, u->nick, u->username, u->host, ci->name); - if (WallGetpass) { - ircdproto->SendGlobops(s_ChanServ, - "\2%s\2 used GETPASS on channel \2%s\2", - u->nick, chan); - } - notice_lang(s_ChanServ, u, CHAN_GETPASS_PASSWORD_IS, - chan, tmp_pass); - } else { + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + char tmp_pass[PASSMAX]; + ChannelInfo *ci; + + if (!(ci = cs_findchan(chan))) + { + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + return MOD_CONT; + } + if (ci->flags & CI_VERBOTEN) + { + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } + if (CSRestrictGetPass && !is_services_root(u)) + { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + return MOD_CONT; + } + if(!enc_decrypt(ci->founderpass, tmp_pass, PASSMAX - 1)==1) + { notice_lang(s_ChanServ, u, CHAN_GETPASS_UNAVAILABLE); + return MOD_CONT; + } + + alog("%s: %s!%s@%s used GETPASS on %s", s_ChanServ, u->nick, u->GetIdent().c_str(), u->host, ci->name); + if (WallGetpass) + { + ircdproto->SendGlobops(s_ChanServ, "\2%s\2 used GETPASS on channel \2%s\2", u->nick, chan); } + notice_lang(s_ChanServ, u, CHAN_GETPASS_PASSWORD_IS, chan, tmp_pass); + return MOD_CONT; } - return MOD_CONT; -} + + bool OnHelp(User *u, const std::string &subcommand) + { + if (is_services_admin(u)) + { + notice_lang(s_ChanServ, u, CHAN_SERVADMIN_HELP_GETPASS); + return true; + } + + return false; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_ChanServ, u, "GETPASS", CHAN_GETPASS_SYNTAX); + } +}; + +class CSGetPass : public Module +{ + public: + CSGetPass(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(CHANSERV, new CommandCSGetPass(), MOD_UNIQUE); + + this->SetChanHelp(myChanServHelp); + } +}; MODULE_INIT("cs_getpass", CSGetPass) diff --git a/src/core/cs_help.c b/src/core/cs_help.c index e2329c8ee..b27c6a7c2 100644 --- a/src/core/cs_help.c +++ b/src/core/cs_help.c @@ -15,60 +15,66 @@ #include "module.h" -int do_help(User * u); - -class CSHelp : public Module +class CommandCSHelp : public Command { public: - CSHelp(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandCSHelp() : Command("HELP", 0, 2) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - c = createCommand("HELP", do_help, NULL, -1, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); } -}; -/** - * The /cs help command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_help(User * u) -{ - char *cmd = strtok(NULL, ""); + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + const char *subcmd = params[1].c_str(); - if (!cmd) { - notice_help(s_ChanServ, u, CHAN_HELP); - moduleDisplayHelp(2, u); - if (CSExpire >= 86400) - notice_help(s_ChanServ, u, CHAN_HELP_EXPIRES, - CSExpire / 86400); - if (is_services_oper(u)) - notice_help(s_ChanServ, u, CHAN_SERVADMIN_HELP); - } else if (stricmp(cmd, "LEVELS DESC") == 0) { - int i; - notice_help(s_ChanServ, u, CHAN_HELP_LEVELS_DESC); - if (!levelinfo_maxwidth) { - for (i = 0; levelinfo[i].what >= 0; i++) { - int len = strlen(levelinfo[i].name); - if (len > levelinfo_maxwidth) - levelinfo_maxwidth = len; + if (!cmd) + { + notice_help(s_ChanServ, u, CHAN_HELP); + moduleDisplayHelp(2, u); + if (CSExpire >= 86400) + notice_help(s_ChanServ, u, CHAN_HELP_EXPIRES, CSExpire / 86400); + if (is_services_oper(u)) + notice_help(s_ChanServ, u, CHAN_SERVADMIN_HELP); + } + else if (stricmp(cmd, "LEVELS DESC") == 0) + { + int i; + notice_help(s_ChanServ, u, CHAN_HELP_LEVELS_DESC); + if (!levelinfo_maxwidth) { + for (i = 0; levelinfo[i].what >= 0; i++) + { + int len = strlen(levelinfo[i].name); + if (len > levelinfo_maxwidth) + levelinfo_maxwidth = len; + } + } + for (i = 0; levelinfo[i].what >= 0; i++) + { + notice_help(s_ChanServ, u, CHAN_HELP_LEVELS_DESC_FORMAT, + levelinfo_maxwidth, levelinfo[i].name, + getstring(u->na, levelinfo[i].desc)); } } - for (i = 0; levelinfo[i].what >= 0; i++) { - notice_help(s_ChanServ, u, CHAN_HELP_LEVELS_DESC_FORMAT, - levelinfo_maxwidth, levelinfo[i].name, - getstring(u->na, levelinfo[i].desc)); + else + { + mod_help_cmd(s_ChanServ, u, CHANSERV, cmd); } - } else { - mod_help_cmd(s_ChanServ, u, CHANSERV, cmd); + return MOD_CONT; } - return MOD_CONT; -} +}; + + +class CSHelp : public Module +{ + public: + CSHelp(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(CHANSERV, new CommandCSHelp(), MOD_UNIQUE); + } +}; MODULE_INIT("cs_help", CSHelp) diff --git a/src/core/cs_identify.c b/src/core/cs_identify.c index 20e6c2e7f..a9bd1926f 100644 --- a/src/core/cs_identify.c +++ b/src/core/cs_identify.c @@ -15,29 +15,6 @@ #include "module.h" -int do_identify(User * u); -void myChanServHelp(User * u); - -class CSIdentify : public Module -{ - public: - CSIdentify(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("IDENTIFY", do_identify, NULL, CHAN_HELP_IDENTIFY, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - - c = createCommand("ID", do_identify, NULL, CHAN_HELP_IDENTIFY, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - - this->SetChanHelp(myChanServHelp); - } -}; @@ -50,33 +27,51 @@ void myChanServHelp(User * u) notice_lang(s_ChanServ, u, CHAN_HELP_CMD_IDENTIFY); } -/** - * The /cs command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_identify(User * u) +class CommandCSIdentify : public Command { - char *chan = strtok(NULL, " "); - char *pass = strtok(NULL, " "); - ChannelInfo *ci; - struct u_chaninfolist *uc; + public: + CommandCSIdentify(const std::string &cname) : Command(cname, 2, 2) + { + + } + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + const char *pass = params[1].c_str(); + ChannelInfo *ci; + struct u_chaninfolist *uc; + + if (!(ci = cs_findchan(chan))) + { + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + return MOD_CONT; + } + + if (ci->flags & CI_VERBOTEN) + { + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } + + if (!nick_identified(u)) + { + notice_lang(s_ChanServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + return MOD_CONT; + } + + if (is_founder(u, ci)) + { + notice_lang(s_ChanServ, u, NICK_ALREADY_IDENTIFIED); + return MOD_CONT; + } - if (!pass) { - syntax_error(s_ChanServ, u, "IDENTIFY", CHAN_IDENTIFY_SYNTAX); - } else if (!(ci = cs_findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - } else if (!nick_identified(u)) { - notice_lang(s_ChanServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); - } else if (is_founder(u, ci)) { - notice_lang(s_ChanServ, u, NICK_ALREADY_IDENTIFIED); - } else { int res; - if ((res = enc_check_password(pass, ci->founderpass)) == 1) { - if (!is_identified(u, ci)) { + if ((res = enc_check_password(pass, ci->founderpass)) == 1) + { + if (!is_identified(u, ci)) + { uc = new u_chaninfolist; uc->prev = NULL; uc->next = u->founder_chans; @@ -85,22 +80,54 @@ int do_identify(User * u) u->founder_chans = uc; uc->chan = ci; alog("%s: %s!%s@%s identified for %s", s_ChanServ, u->nick, - u->username, u->host, ci->name); + u->GetIdent().c_str(), u->host, ci->name); } notice_lang(s_ChanServ, u, CHAN_IDENTIFY_SUCCEEDED, chan); - } else if (res < 0) { + } + else if (res < 0) + { alog("%s: check_password failed for %s", s_ChanServ, ci->name); notice_lang(s_ChanServ, u, CHAN_IDENTIFY_FAILED); - } else { + } + else + { alog("%s: Failed IDENTIFY for %s by %s!%s@%s", - s_ChanServ, ci->name, u->nick, u->username, u->host); + s_ChanServ, ci->name, u->nick, u->GetIdent().c_str(), u->host); notice_lang(s_ChanServ, u, PASSWORD_INCORRECT); bad_password(u); } + return MOD_CONT; } - return MOD_CONT; -} + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_ChanServ, u, CHAN_HELP_IDENTIFY); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_ChanServ, u, "IDENTIFY", CHAN_IDENTIFY_SYNTAX); + } +}; + +class CSIdentify : public Module +{ + public: + CSIdentify(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(CHANSERV, new CommandCSIdentify("IDENTIFY"), MOD_UNIQUE); + // XXX: we need aliases. + this->AddCommand(CHANSERV, new CommandCSIdentify("ID"), MOD_UNIQUE); + + this->SetChanHelp(myChanServHelp); + } +}; + MODULE_INIT("cs_identify", CSIdentify) diff --git a/src/core/cs_info.c b/src/core/cs_info.c index 3e8284f97..8aca84b25 100644 --- a/src/core/cs_info.c +++ b/src/core/cs_info.c @@ -15,28 +15,6 @@ #include "module.h" -int do_info(User * u); -void myChanServHelp(User * u); - -class CSInfo : public Module -{ - public: - CSInfo(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("INFO", do_info, NULL, CHAN_HELP_INFO, -1, CHAN_SERVADMIN_HELP_INFO, CHAN_SERVADMIN_HELP_INFO, CHAN_SERVADMIN_HELP_INFO); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - - this->SetChanHelp(myChanServHelp); - } -}; - - /** * Add the help response to anopes /cs help output. @@ -47,59 +25,67 @@ void myChanServHelp(User * u) notice_lang(s_ChanServ, u, CHAN_HELP_CMD_INFO); } -/** - * The /cs info command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_info(User * u) -{ -/* SADMINS and users, who have identified for a channel, can now cause it's - * Enstry Message and Successor to be displayed by supplying the ALL parameter. - * Syntax: INFO channel [ALL] - * -TheShadow (29 Mar 1999) - */ - char *chan = strtok(NULL, " "); - char *param = strtok(NULL, " "); - ChannelInfo *ci; - char buf[BUFSIZE], *end; - struct tm *tm; - int need_comma = 0; - const char *commastr = getstring(u->na, COMMA_SPACE); - int is_servadmin = is_services_admin(u); - int show_all = 0; - time_t expt; - - if (!chan) { - syntax_error(s_ChanServ, u, "INFO", CHAN_INFO_SYNTAX); - } else if (!(ci = cs_findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (ci->flags & CI_VERBOTEN) { - if (is_oper(u) && ci->forbidby) - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN_OPER, chan, - ci->forbidby, - (ci->forbidreason ? ci-> - forbidreason : getstring(u->na, NO_REASON))); - else - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - } else if (!ci->founder) { - /* Paranoia... this shouldn't be able to happen */ - delchan(ci); - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else { + +class CommandCSInfo : public Command +{ // cannot be const, as it is modified. + void CheckOptStr(std::string &buf, int opt, const std::string &str, ChannelInfo *ci, NickAlias *na) + { + if (ci->flags & opt) + { + const char *commastr = getstring(na, COMMA_SPACE); + if (!buf.empty()) + buf += commastr; + + buf += str; + } + } + + public: + CommandCSInfo() : Command("INFO", 1, 2) + { + + } + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + char *chan = strtok(NULL, " "); + char *param = strtok(NULL, " "); + ChannelInfo *ci; + char buf[BUFSIZE]; + struct tm *tm; + int is_servadmin = is_services_admin(u); + int show_all = 0; + time_t expt; + + if (!(ci = cs_findchan(chan))) + { + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + return MOD_CONT; + } + + if (ci->flags & CI_VERBOTEN) + { + if (is_oper(u) && ci->forbidby) + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN_OPER, chan, + ci->forbidby, + (ci->forbidreason ? ci-> + forbidreason : getstring(u->na, NO_REASON))); + else + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + + return MOD_CONT; + } + /* Should we show all fields? Only for sadmins and identified users */ - if (param && stricmp(param, "ALL") == 0 && - (check_access(u, ci, CA_INFO) || is_servadmin)) + if (param && stricmp(param, "ALL") == 0 && (check_access(u, ci, CA_INFO) || is_servadmin)) show_all = 1; notice_lang(s_ChanServ, u, CHAN_INFO_HEADER, chan); - notice_lang(s_ChanServ, u, CHAN_INFO_NO_FOUNDER, - ci->founder->display); + notice_lang(s_ChanServ, u, CHAN_INFO_NO_FOUNDER, ci->founder->display); if (show_all && ci->successor) - notice_lang(s_ChanServ, u, CHAN_INFO_NO_SUCCESSOR, - ci->successor->display); + notice_lang(s_ChanServ, u, CHAN_INFO_NO_SUCCESSOR, ci->successor->display); notice_lang(s_ChanServ, u, CHAN_INFO_DESCRIPTION, ci->desc); tm = localtime(&ci->time_registered); @@ -108,130 +94,101 @@ int do_info(User * u) tm = localtime(&ci->last_used); strftime_lang(buf, sizeof(buf), u, STRFTIME_DATE_TIME_FORMAT, tm); notice_lang(s_ChanServ, u, CHAN_INFO_LAST_USED, buf); - if (ci->last_topic - && (show_all || (!(ci->mlock_on & anope_get_secret_mode()) - && (!ci->c - || !(ci->c-> - mode & anope_get_secret_mode()))))) { - notice_lang(s_ChanServ, u, CHAN_INFO_LAST_TOPIC, - ci->last_topic); - notice_lang(s_ChanServ, u, CHAN_INFO_TOPIC_SET_BY, - ci->last_topic_setter); + // XXX: yuck. + if (ci->last_topic && + (show_all || (!(ci->mlock_on & anope_get_secret_mode()) + && (!ci->c || !(ci->c->mode & anope_get_secret_mode()))))) + { + notice_lang(s_ChanServ, u, CHAN_INFO_LAST_TOPIC, ci->last_topic); + notice_lang(s_ChanServ, u, CHAN_INFO_TOPIC_SET_BY, ci->last_topic_setter); } if (ci->entry_message && show_all) - notice_lang(s_ChanServ, u, CHAN_INFO_ENTRYMSG, - ci->entry_message); + notice_lang(s_ChanServ, u, CHAN_INFO_ENTRYMSG, ci->entry_message); if (ci->url) notice_lang(s_ChanServ, u, CHAN_INFO_URL, ci->url); if (ci->email) notice_lang(s_ChanServ, u, CHAN_INFO_EMAIL, ci->email); - if (show_all) { + if (show_all) + { notice_lang(s_ChanServ, u, CHAN_INFO_BANTYPE, ci->bantype); - - end = buf; - *end = 0; - if (ci->flags & CI_KEEPTOPIC) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s", - getstring(u->na, CHAN_INFO_OPT_KEEPTOPIC)); - need_comma = 1; - } - if (ci->flags & CI_OPNOTICE) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, CHAN_INFO_OPT_OPNOTICE)); - need_comma = 1; - } - if (ci->flags & CI_PEACE) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, CHAN_INFO_OPT_PEACE)); - need_comma = 1; - } - if (ci->flags & CI_PRIVATE) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, CHAN_INFO_OPT_PRIVATE)); - need_comma = 1; - } - if (ci->flags & CI_RESTRICTED) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, - CHAN_INFO_OPT_RESTRICTED)); - need_comma = 1; - } - if (ci->flags & CI_SECURE) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, CHAN_INFO_OPT_SECURE)); - need_comma = 1; - } - if (ci->flags & CI_SECUREOPS) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, CHAN_INFO_OPT_SECUREOPS)); - need_comma = 1; - } - if (ci->flags & CI_SECUREFOUNDER) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, - CHAN_INFO_OPT_SECUREFOUNDER)); - need_comma = 1; - } - if ((ci->flags & CI_SIGNKICK) - || (ci->flags & CI_SIGNKICK_LEVEL)) { - end += - snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", getstring(u->na, - CHAN_INFO_OPT_SIGNKICK)); - need_comma = 1; - } - if (ci->flags & CI_TOPICLOCK) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, CHAN_INFO_OPT_TOPICLOCK)); - need_comma = 1; - } - if (ci->flags & CI_XOP) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, CHAN_INFO_OPT_XOP)); - need_comma = 1; - } - notice_lang(s_ChanServ, u, CHAN_INFO_OPTIONS, - *buf ? buf : getstring(u->na, CHAN_INFO_OPT_NONE)); - notice_lang(s_ChanServ, u, CHAN_INFO_MODE_LOCK, - get_mlock_modes(ci, 1)); - - } - if (show_all) { - if (ci->flags & CI_NO_EXPIRE) { + std::string optbuf; + + CheckOptStr(optbuf, CI_KEEPTOPIC, getstring(u->na, CHAN_INFO_OPT_KEEPTOPIC), ci, u->na); + CheckOptStr(optbuf, CI_OPNOTICE, getstring(u->na, CHAN_INFO_OPT_OPNOTICE), ci, u->na); + CheckOptStr(optbuf, CI_PEACE, getstring(u->na, CHAN_INFO_OPT_PEACE), ci, u->na); + CheckOptStr(optbuf, CI_PRIVATE, getstring(u->na, CHAN_INFO_OPT_PRIVATE), ci, u->na); + CheckOptStr(optbuf, CI_RESTRICTED, getstring(u->na, CHAN_INFO_OPT_RESTRICTED), ci, u->na); + CheckOptStr(optbuf, CI_SECURE, getstring(u->na, CHAN_INFO_OPT_SECURE), ci, u->na); + CheckOptStr(optbuf, CI_SECUREFOUNDER, getstring(u->na, CHAN_INFO_OPT_SECUREFOUNDER), ci, u->na); + CheckOptStr(optbuf, CI_SECUREOPS, getstring(u->na, CHAN_INFO_OPT_SECUREOPS), ci, u->na); + CheckOptStr(optbuf, CI_SIGNKICK | CI_SIGNKICK_LEVEL, getstring(u->na, CHAN_INFO_OPT_SIGNKICK), ci, u->na); + CheckOptStr(optbuf, CI_TOPICLOCK, getstring(u->na, CHAN_INFO_OPT_TOPICLOCK), ci, u->na); + CheckOptStr(optbuf, CI_XOP, getstring(u->na, CHAN_INFO_OPT_XOP), ci, u->na); + + notice_lang(s_ChanServ, u, CHAN_INFO_OPTIONS, optbuf.empty() ? getstring(u->na, CHAN_INFO_OPT_NONE) : optbuf.c_str()); + notice_lang(s_ChanServ, u, CHAN_INFO_MODE_LOCK, get_mlock_modes(ci, 1)); + + // XXX: we could just as easily (and tidily) merge this in with the flags display above. + if (ci->flags & CI_NO_EXPIRE) + { notice_lang(s_ChanServ, u, CHAN_INFO_NO_EXPIRE); - } else { - if (is_servadmin) { + } + else + { + if (is_servadmin) + { expt = ci->last_used + CSExpire; tm = localtime(&expt); - strftime_lang(buf, sizeof(buf), u, - STRFTIME_DATE_TIME_FORMAT, tm); + strftime_lang(buf, sizeof(buf), u, STRFTIME_DATE_TIME_FORMAT, tm); notice_lang(s_ChanServ, u, CHAN_INFO_EXPIRE, buf); } } } - if (ci->flags & CI_SUSPENDED) { - notice_lang(s_ChanServ, u, CHAN_X_SUSPENDED, ci->forbidby, - (ci->forbidreason ? ci-> - forbidreason : getstring(u->na, NO_REASON))); + if (ci->flags & CI_SUSPENDED) + { + notice_lang(s_ChanServ, u, CHAN_X_SUSPENDED, ci->forbidby, (ci->forbidreason ? ci->forbidreason : getstring(u->na, NO_REASON))); } if (!show_all && (check_access(u, ci, CA_INFO) || is_servadmin)) - notice_lang(s_ChanServ, u, NICK_INFO_FOR_MORE, s_ChanServ, - ci->name); + notice_lang(s_ChanServ, u, NICK_INFO_FOR_MORE, s_ChanServ, ci->name); + return MOD_CONT; + } + + bool OnUserHelp(User *u) + { + if (is_services_admin(u) || is_services_root(u)) + notice_lang(s_ChanServ, u, CHAN_SERVADMIN_HELP_INFO); + else + notice_lang(s_NickServ, u, CHAN_HELP_INFO); + return true; } - return MOD_CONT; -} + + void OnSyntaxError(User *u) + { + syntax_error(s_ChanServ, u, "INFO", CHAN_INFO_SYNTAX); + } +}; + + + +class CSInfo : public Module +{ + public: + CSInfo(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(CHANSERV, new CommandCSInfo(), MOD_UNIQUE); + + this->SetChanHelp(myChanServHelp); + } +}; + + + MODULE_INIT("cs_info", CSInfo) diff --git a/src/core/cs_invite.c b/src/core/cs_invite.c index 4fbe90c54..b50716a0c 100644 --- a/src/core/cs_invite.c +++ b/src/core/cs_invite.c @@ -15,65 +15,88 @@ #include "module.h" -void myChanServHelp(User * u); -int do_invite(User * u); -class CSInvite : public Module +/** + * Add the help response to anopes /cs help output. + * @param u The user who is requesting help + **/ +void myChanServHelp(User * u) +{ + notice_lang(s_ChanServ, u, CHAN_HELP_CMD_INVITE); +} + +class CommandCSInvite : public Command { public: - CSInvite(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandCSInvite() : Command("INVITE", 1, 1) { - Command *c; - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); + } + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + Channel *c; + ChannelInfo *ci; - c = createCommand("INVITE", do_invite, NULL, CHAN_HELP_INVITE, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); + if (!(c = findchan(chan))) + { + notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); + return MOD_CONT; + } + else if (!(ci = c->ci)) + { + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + return MOD_CONT; + } + else if (ci->flags & CI_VERBOTEN) + { + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } + else if (ci->flags & CI_SUSPENDED) + { + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } + else if (!u || !check_access(u, ci, CA_INVITE)) + { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + return MOD_CONT; + } - this->SetChanHelp(myChanServHelp); + ircdproto->SendInvite(whosends(ci), chan, u->nick); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_ChanServ, u, CHAN_HELP_INVITE); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_ChanServ, u, "INVITE", CHAN_INVITE_SYNTAX); } }; -/** - * Add the help response to anopes /cs help output. - * @param u The user who is requesting help - **/ -void myChanServHelp(User * u) -{ - notice_lang(s_ChanServ, u, CHAN_HELP_CMD_INVITE); -} -/** - * The /cs invite command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_invite(User * u) +class CSInvite : public Module { - char *chan = strtok(NULL, " "); - Channel *c; - ChannelInfo *ci; + public: + CSInvite(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(CHANSERV, new CommandCSInvite(), MOD_UNIQUE); - if (!chan) { - syntax_error(s_ChanServ, u, "INVITE", CHAN_INVITE_SYNTAX); - } else if (!(c = findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); - } else if (!(ci = c->ci)) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - } else if (ci->flags & CI_SUSPENDED) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - } else if (!u || !check_access(u, ci, CA_INVITE)) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - } else { - ircdproto->SendInvite(whosends(ci), chan, u->nick); + this->SetChanHelp(myChanServHelp); } - return MOD_CONT; -} +}; + + MODULE_INIT("cs_invite", CSInvite) diff --git a/src/core/cs_kick.c b/src/core/cs_kick.c index e3fd1069d..c0b5f8b47 100644 --- a/src/core/cs_kick.c +++ b/src/core/cs_kick.c @@ -15,27 +15,6 @@ #include "module.h" -int do_cs_kick(User * u); -void myChanServHelp(User * u); - -class CSKick : public Module -{ - public: - CSKick(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("KICK", do_cs_kick, NULL, CHAN_HELP_KICK, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_UNIQUE); - - this->SetChanHelp(myChanServHelp); - } -}; - /** * Add the help response to anopes /cs help output. * @param u The user who is requesting help @@ -45,97 +24,91 @@ void myChanServHelp(User * u) notice_lang(s_ChanServ, u, CHAN_HELP_CMD_KICK); } -/** - * The /cs kick command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_cs_kick(User * u) +class CommandCSKick : public Command { - char *chan = strtok(NULL, " "); - char *params = strtok(NULL, " "); - char *reason = strtok(NULL, ""); - - Channel *c; - ChannelInfo *ci; - User *u2; - - int is_same; + public: + CommandCSKick() : Command("KICK", 1, 3) + { - if (!reason) { - reason = "Requested"; - } else { - if (strlen(reason) > 200) - reason[200] = '\0'; } - if (!chan) { - struct u_chanlist *uc, *next; - - /* Kicks the user on every channels he is on. */ - - for (uc = u->chans; uc; uc = next) { - next = uc->next; - if ((ci = uc->chan->ci) && !(ci->flags & CI_VERBOTEN) - && check_access(u, ci, CA_KICKME)) { - const char *av[3]; + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + const char *target = params[1].c_str(); + params[2].resize(200); + const char *reason = params[2].c_str(); + Channel *c; + ChannelInfo *ci; + User *u2; + + int is_same; + + if (!reason) { + reason = "Requested"; + } - if ((ci->flags & CI_SIGNKICK) - || ((ci->flags & CI_SIGNKICK_LEVEL) - && !check_access(u, ci, CA_SIGNKICK))) - ircdproto->SendKick(whosends(ci), ci->name, u->nick, - "%s (%s)", reason, u->nick); - else - ircdproto->SendKick(whosends(ci), ci->name, u->nick, "%s", - reason); - av[0] = ci->name; - av[1] = u->nick; - av[2] = reason; - do_kick(s_ChanServ, 3, av); - } + if (!target) { + target = u->nick; } + is_same = (target == u->nick) ? 1 : (stricmp(target, u->nick) == 0); + + if (!(c = findchan(chan))) { + notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); + } else if (!(ci = c->ci)) { + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + } else if (ci->flags & CI_VERBOTEN) { + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); + } else if (is_same ? !(u2 = u) : !(u2 = finduser(target))) { + notice_lang(s_ChanServ, u, NICK_X_NOT_IN_USE, target); + } else if (!is_on_chan(c, u2)) { + notice_lang(s_ChanServ, u, NICK_X_NOT_ON_CHAN, u2->nick, c->name); + } else if (!is_same ? !check_access(u, ci, CA_KICK) : + !check_access(u, ci, CA_KICKME)) { + notice_lang(s_ChanServ, u, ACCESS_DENIED); + } else if (!is_same && (ci->flags & CI_PEACE) + && (get_access(u2, ci) >= get_access(u, ci))) { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + } else if (is_protected(u2)) { + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + } else { + const char *av[3]; + + if ((ci->flags & CI_SIGNKICK) + || ((ci->flags & CI_SIGNKICK_LEVEL) + && !check_access(u, ci, CA_SIGNKICK))) + ircdproto->SendKick(whosends(ci), ci->name, target, "%s (%s)", + reason, u->nick); + else + ircdproto->SendKick(whosends(ci), ci->name, target, "%s", reason); + av[0] = ci->name; + av[1] = target; + av[2] = reason; + do_kick(s_ChanServ, 3, av); + } return MOD_CONT; - } else if (!params) { - params = u->nick; } - is_same = (params == u->nick) ? 1 : (stricmp(params, u->nick) == 0); + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_ChanServ, u, CHAN_HELP_KICK); + return true; + } +}; - if (!(c = findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); - } else if (!(ci = c->ci)) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, chan); - } else if (is_same ? !(u2 = u) : !(u2 = finduser(params))) { - notice_lang(s_ChanServ, u, NICK_X_NOT_IN_USE, params); - } else if (!is_on_chan(c, u2)) { - notice_lang(s_ChanServ, u, NICK_X_NOT_ON_CHAN, u2->nick, c->name); - } else if (!is_same ? !check_access(u, ci, CA_KICK) : - !check_access(u, ci, CA_KICKME)) { - notice_lang(s_ChanServ, u, ACCESS_DENIED); - } else if (!is_same && (ci->flags & CI_PEACE) - && (get_access(u2, ci) >= get_access(u, ci))) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - } else if (is_protected(u2)) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - } else { - const char *av[3]; +class CSKick : public Module +{ + public: + CSKick(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(CHANSERV, new CommandCSKick(), MOD_UNIQUE); - if ((ci->flags & CI_SIGNKICK) - || ((ci->flags & CI_SIGNKICK_LEVEL) - && !check_access(u, ci, CA_SIGNKICK))) - ircdproto->SendKick(whosends(ci), ci->name, params, "%s (%s)", - reason, u->nick); - else - ircdproto->SendKick(whosends(ci), ci->name, params, "%s", reason); - av[0] = ci->name; - av[1] = params; - av[2] = reason; - do_kick(s_ChanServ, 3, av); + this->SetChanHelp(myChanServHelp); } - return MOD_CONT; -} +}; MODULE_INIT("cs_kick", CSKick) diff --git a/src/core/cs_logout.c b/src/core/cs_logout.c index 488d5325f..96257e72a 100644 --- a/src/core/cs_logout.c +++ b/src/core/cs_logout.c @@ -80,7 +80,7 @@ int do_logout(User * u) make_unidentified(u2, ci); notice_lang(s_ChanServ, u, CHAN_LOGOUT_SUCCEEDED, nick, chan); alog("%s: User %s!%s@%s has been logged out of channel %s.", - s_ChanServ, u2->nick, u2->username, u2->host, chan); + s_ChanServ, u2->nick, u2->GetIdent().c_str(), u2->host, chan); } else { int i; for (i = 0; i < 1024; i++) diff --git a/src/core/cs_register.c b/src/core/cs_register.c index 5d63854a9..d957f1a38 100644 --- a/src/core/cs_register.c +++ b/src/core/cs_register.c @@ -93,7 +93,7 @@ int do_register(User * u) notice_lang(s_ChanServ, u, CHAN_REGISTER_NONE_CHANNEL, chan); } else if ((ci = cs_findchan(chan)) != NULL) { if (ci->flags & CI_VERBOTEN) { - alog("%s: Attempt to register FORBIDden channel %s by %s!%s@%s", s_ChanServ, ci->name, u->nick, u->username, u->host); + alog("%s: Attempt to register FORBIDden channel %s by %s!%s@%s", s_ChanServ, ci->name, u->nick, u->GetIdent().c_str(), u->host); notice_lang(s_ChanServ, u, CHAN_MAY_NOT_BE_REGISTERED, chan); } else { notice_lang(s_ChanServ, u, CHAN_ALREADY_REGISTERED, chan); @@ -146,7 +146,7 @@ int do_register(User * u) ci->botflags = BSDefFlags; ci->founder->channelcount++; alog("%s: Channel '%s' registered by %s!%s@%s", s_ChanServ, chan, - u->nick, u->username, u->host); + u->nick, u->GetIdent().c_str(), u->host); notice_lang(s_ChanServ, u, CHAN_REGISTERED, chan, u->nick); if(enc_decrypt(ci->founderpass,tmp_pass,PASSMAX - 1) == 1) { diff --git a/src/core/cs_sendpass.c b/src/core/cs_sendpass.c index fbcf68ef1..932b246ca 100644 --- a/src/core/cs_sendpass.c +++ b/src/core/cs_sendpass.c @@ -105,7 +105,7 @@ int do_sendpass(User * u) MailEnd(mail); alog("%s: %s!%s@%s used SENDPASS on %s", s_ChanServ, u->nick, - u->username, u->host, chan); + u->GetIdent().c_str(), u->host, chan); notice_lang(s_ChanServ, u, CHAN_SENDPASS_OK, chan); } else { notice_lang(s_ChanServ, u, CHAN_SENDPASS_UNAVAILABLE); diff --git a/src/core/cs_set.c b/src/core/cs_set.c index bc2b87c59..6b6e26ffd 100644 --- a/src/core/cs_set.c +++ b/src/core/cs_set.c @@ -269,7 +269,7 @@ int do_set_founder(User * u, ChannelInfo * ci, char *param) alog("%s: Changing founder of %s from %s to %s by %s!%s@%s", s_ChanServ, ci->name, ci->founder->display, nc->display, u->nick, - u->username, u->host); + u->GetIdent().c_str(), u->host); /* Founder and successor must not be the same group */ if (nc == ci->successor) @@ -315,7 +315,7 @@ int do_set_successor(User * u, ChannelInfo * ci, char *param) alog("%s: Changing successor of %s from %s to %s by %s!%s@%s", s_ChanServ, ci->name, (ci->successor ? ci->successor->display : "none"), - (nc ? nc->display : "none"), u->nick, u->username, u->host); + (nc ? nc->display : "none"), u->nick, u->GetIdent().c_str(), u->host); ci->successor = nc; @@ -356,14 +356,14 @@ int do_set_password(User * u, ChannelInfo * ci, char *param) if (get_access(u, ci) < ACCESS_FOUNDER) { alog("%s: %s!%s@%s set password as Services admin for %s", - s_ChanServ, u->nick, u->username, u->host, ci->name); + s_ChanServ, u->nick, u->GetIdent().c_str(), u->host, ci->name); if (WallSetpass) ircdproto->SendGlobops(s_ChanServ, "\2%s\2 set password as Services admin for channel \2%s\2", u->nick, ci->name); } else { alog("%s: %s!%s@%s changed password of %s (founder: %s)", - s_ChanServ, u->nick, u->username, u->host, + s_ChanServ, u->nick, u->GetIdent().c_str(), u->host, ci->name, ci->founder->display); } return MOD_CONT; @@ -748,13 +748,13 @@ int do_set_xop(User * u, ChannelInfo * ci, char *param) } alog("%s: %s!%s@%s enabled XOP for %s", s_ChanServ, u->nick, - u->username, u->host, ci->name); + u->GetIdent().c_str(), u->host, ci->name); notice_lang(s_ChanServ, u, CHAN_SET_XOP_ON, ci->name); } else if (stricmp(param, "OFF") == 0) { ci->flags &= ~CI_XOP; alog("%s: %s!%s@%s disabled XOP for %s", s_ChanServ, u->nick, - u->username, u->host, ci->name); + u->GetIdent().c_str(), u->host, ci->name); notice_lang(s_ChanServ, u, CHAN_SET_XOP_OFF, ci->name); } else { syntax_error(s_ChanServ, u, "SET XOP", CHAN_SET_XOP_SYNTAX); diff --git a/src/core/cs_topic.c b/src/core/cs_topic.c index 2e6dda2a1..18bc50ff7 100644 --- a/src/core/cs_topic.c +++ b/src/core/cs_topic.c @@ -88,7 +88,7 @@ int do_cs_topic(User * u) if (is_services_admin(u) && !check_access(u, ci, CA_TOPIC)) alog("%s: %s!%s@%s changed topic of %s as services admin.", - s_ChanServ, u->nick, u->username, u->host, c->name); + s_ChanServ, u->nick, u->GetIdent().c_str(), u->host, c->name); if (ircd->join2set) { if (whosends(ci) == findbot(s_ChanServ)) { ircdproto->SendJoin(findbot(s_ChanServ), c->name, c->creation_time); diff --git a/src/core/cs_xop.c b/src/core/cs_xop.c index 6da5bf7ed..abbddb75b 100644 --- a/src/core/cs_xop.c +++ b/src/core/cs_xop.c @@ -317,7 +317,7 @@ int do_xop(User * u, const char *xname, int xlev, int *xmsgs) access->level = xlev; access->last_seen = 0; - alog("%s: %s!%s@%s (level %d) %s access level %d to %s (group %s) on channel %s", s_ChanServ, u->nick, u->username, u->host, ulev, change ? "changed" : "set", access->level, na->nick, nc->display, ci->name); + alog("%s: %s!%s@%s (level %d) %s access level %d to %s (group %s) on channel %s", s_ChanServ, u->nick, u->GetIdent().c_str(), u->host, ulev, change ? "changed" : "set", access->level, na->nick, nc->display, ci->name); snprintf(event_access, BUFSIZE, "%d", access->level); diff --git a/src/core/he_help.c b/src/core/he_help.c index 6b8741353..5b3f4a129 100644 --- a/src/core/he_help.c +++ b/src/core/he_help.c @@ -6,8 +6,8 @@ * Please read COPYING and README for further details. * * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * + * Based on the original code of Services by Andy Church. + * * $Id$ * */ @@ -15,52 +15,41 @@ #include "module.h" -int do_help(User * u); +class CommandHEHelp : public Command +{ + public: + CommandHEHelp() : Command("HELP", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + mod_help_cmd(s_HelpServ, u, HELPSERV, params[0].c_str()); + return MOD_CONT; + } + + void OnSyntaxError(User *u) + { + notice_help(s_HelpServ, u, HELP_HELP, s_NickServ, s_ChanServ, s_MemoServ); + if (s_BotServ) + notice_help(s_HelpServ, u, HELP_HELP_BOT, s_BotServ); + if (s_HostServ) + notice_help(s_HelpServ, u, HELP_HELP_HOST, s_HostServ); + moduleDisplayHelp(7, u); + } +}; class HEHelp : public Module { public: HEHelp(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("HELP", do_help, NULL, -1, -1, -1, -1, -1); - this->AddCommand(HELPSERV, c, MOD_UNIQUE); + this->AddCommand(HELPSERV, new CommandHEHelp(), MOD_UNIQUE); } }; - - -/** - * Display the HelpServ help. - * This core function has been embed in the source for a long time, but - * it moved into it's own file so we now all can enjoy the joy of - * modules for HelpServ. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - */ -int do_help(User * u) -{ - char *cmd = strtok(NULL, ""); - - if (!cmd) { - notice_help(s_HelpServ, u, HELP_HELP, s_NickServ, s_ChanServ, - s_MemoServ); - if (s_BotServ) { - notice_help(s_HelpServ, u, HELP_HELP_BOT, s_BotServ); - } - if (s_HostServ) { - notice_help(s_HelpServ, u, HELP_HELP_HOST, s_HostServ); - } - moduleDisplayHelp(7, u); - } else { - mod_help_cmd(s_HelpServ, u, HELPSERV, cmd); - } - return MOD_CONT; -} - MODULE_INIT("he_help", HEHelp) diff --git a/src/core/hs_del.c b/src/core/hs_del.c index 5f5c41acd..2e80bf77e 100644 --- a/src/core/hs_del.c +++ b/src/core/hs_del.c @@ -15,67 +15,73 @@ #include "module.h" -int do_del(User * u); -void myHostServHelp(User * u); +void myHostServHelp(User *u); + +class CommandHSDel : public Command +{ + public: + CommandHSDel() : Command("DEL", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + NickAlias *na; + const char *nick = params[0].c_str(); + if ((na = findnick(nick))) + { + if (na->status & NS_VERBOTEN) + { + notice_lang(s_HostServ, u, NICK_X_FORBIDDEN, nick); + return MOD_CONT; + } + alog("vHost for user \002%s\002 deleted by oper \002%s\002", nick, u->nick); + delHostCore(nick); + notice_lang(s_HostServ, u, HOST_DEL, nick); + } + else + notice_lang(s_HostServ, u, HOST_NOREG, nick); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_host_remover(u)) + return false; + + notice_lang(s_HostServ, u, HOST_HELP_DEL); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_HostServ, u, "DEL", HOST_DEL_SYNTAX, s_HostServ); + } +}; class HSDel : public Module { public: HSDel(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("DEL", do_del, is_host_remover, HOST_HELP_DEL, -1, -1, -1, -1); - this->AddCommand(HOSTSERV, c, MOD_UNIQUE); + this->AddCommand(HOSTSERV, new CommandHSDel(), MOD_UNIQUE); this->SetHostHelp(myHostServHelp); } }; - - - /** * Add the help response to anopes /hs help output. * @param u The user who is requesting help **/ -void myHostServHelp(User * u) +void myHostServHelp(User *u) { - if (is_host_remover(u)) { + if (is_host_remover(u)) notice_lang(s_HostServ, u, HOST_HELP_CMD_DEL); - } -} - -/** - * The /hs del command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_del(User * u) -{ - NickAlias *na; - char *nick = strtok(NULL, " "); - if (nick) { - if ((na = findnick(nick))) { - if (na->status & NS_VERBOTEN) { - notice_lang(s_HostServ, u, NICK_X_FORBIDDEN, nick); - return MOD_CONT; - } - alog("vHost for user \002%s\002 deleted by oper \002%s\002", - nick, u->nick); - delHostCore(nick); - notice_lang(s_HostServ, u, HOST_DEL, nick); - } else { - notice_lang(s_HostServ, u, HOST_NOREG, nick); - } - } else { - notice_lang(s_HostServ, u, HOST_DEL_SYNTAX, s_HostServ); - } - return MOD_CONT; } MODULE_INIT("hs_del", HSDel) diff --git a/src/core/hs_delall.c b/src/core/hs_delall.c index 91f24f4ae..cfce2fdf5 100644 --- a/src/core/hs_delall.c +++ b/src/core/hs_delall.c @@ -15,72 +15,80 @@ #include "module.h" -int do_delall(User * u); -void myHostServHelp(User * u); +void myHostServHelp(User *u); + +class CommandHSDelAll : public Command +{ + public: + CommandHSDelAll() : Command("DELALL", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + int i; + const char *nick = params[0].c_str(); + NickAlias *na; + NickCore *nc; + if ((na = findnick(nick))) + { + if (na->status & NS_VERBOTEN) + { + notice_lang(s_HostServ, u, NICK_X_FORBIDDEN, nick); + return MOD_CONT; + } + nc = na->nc; + for (i = 0; i < nc->aliases.count; ++i) + { + na = static_cast<NickAlias *>(nc->aliases.list[i]); + delHostCore(na->nick); + } + alog("vHosts for all nicks in group \002%s\002 deleted by oper \002%s\002", nc->display, u->nick); + notice_lang(s_HostServ, u, HOST_DELALL, nc->display); + } + else + notice_lang(s_HostServ, u, HOST_NOREG, nick); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_host_remover(u)) + return false; + + notice_lang(s_HostServ, u, HOST_HELP_ALL); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_HostServ, u, "DELALL", HOST_DELALL_SYNTAX, s_HostServ); + } +}; class HSDelAll : public Module { public: HSDelAll(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("DELALL", do_delall, is_host_remover, HOST_HELP_DELALL, -1, -1, -1, -1); - this->AddCommand(HOSTSERV, c, MOD_UNIQUE); + this->AddCommand(HOSTSERV, new CommandHSDelAll(), MOD_UNIQUE); this->SetHostHelp(myHostServHelp); } }; - - - /** * Add the help response to anopes /hs help output. * @param u The user who is requesting help **/ -void myHostServHelp(User * u) +void myHostServHelp(User *u) { - if (is_host_remover(u)) { + if (is_host_remover(u)) notice_lang(s_HostServ, u, HOST_HELP_CMD_DELALL); - } -} - -/** - * The /hs delall command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_delall(User * u) -{ - int i; - char *nick = strtok(NULL, " "); - NickAlias *na; - NickCore *nc; - if (!nick) { - notice_lang(s_HostServ, u, HOST_DELALL_SYNTAX, s_HostServ); - return MOD_CONT; - } - if ((na = findnick(nick))) { - if (na->status & NS_VERBOTEN) { - notice_lang(s_HostServ, u, NICK_X_FORBIDDEN, nick); - return MOD_CONT; - } - nc = na->nc; - for (i = 0; i < nc->aliases.count; i++) { - na = static_cast<NickAlias *>(nc->aliases.list[i]); - delHostCore(na->nick); - } - alog("vHosts for all nicks in group \002%s\002 deleted by oper \002%s\002", nc->display, u->nick); - notice_lang(s_HostServ, u, HOST_DELALL, nc->display); - } else { - notice_lang(s_HostServ, u, HOST_NOREG, nick); - } - return MOD_CONT; } MODULE_INIT("hs_delall", HSDelAll) diff --git a/src/core/hs_group.c b/src/core/hs_group.c index 6e361d308..2a7dd5a57 100644 --- a/src/core/hs_group.c +++ b/src/core/hs_group.c @@ -15,99 +15,97 @@ #include "module.h" -int do_group(User * u); -void myHostServHelp(User * u); -extern int do_hs_sync(NickCore * nc, char *vIdent, char *hostmask, - char *creator, time_t time); +void myHostServHelp(User *u); +extern int do_hs_sync(NickCore *nc, char *vIdent, char *hostmask, char *creator, time_t time); +class CommandHSGroup : public Command +{ + public: + CommandHSGroup() : Command("GROUP", 0, 0) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + NickAlias *na; + HostCore *tmp; + char *vHost = NULL; + char *vIdent = NULL; + char *creator = NULL; + HostCore *head = NULL; + time_t time; + bool found = false; + + head = hostCoreListHead(); + + if ((na = findnick(u->nick))) + { + if (na->status & NS_IDENTIFIED) + { + tmp = findHostCore(head, u->nick, &found); + if (found) + { + if (!tmp) + tmp = head; /* incase first in list */ + else if (tmp->next) /* we dont want the previous entry were not inserting! */ + tmp = tmp->next; /* jump to the next */ + + vHost = sstrdup(tmp->vHost); + if (tmp->vIdent) + vIdent = sstrdup(tmp->vIdent); + creator = sstrdup(tmp->creator); + time = tmp->time; + + do_hs_sync(na->nc, vIdent, vHost, creator, time); + if (tmp->vIdent) + notice_lang(s_HostServ, u, HOST_IDENT_GROUP, na->nc->display, vIdent, vHost); + else + notice_lang(s_HostServ, u, HOST_GROUP, na->nc->display, vHost); + delete [] vHost; + if (vIdent) + delete [] vIdent; + delete [] creator; + } + else + notice_lang(s_HostServ, u, HOST_NOT_ASSIGNED); + } + else + notice_lang(s_HostServ, u, HOST_ID); + } + else + notice_lang(s_HostServ, u, HOST_NOT_REGED); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_HostServ, u, HOST_HELP_GROUP); + return true; + } +}; class HSGroup : public Module { public: HSGroup(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("GROUP", do_group, NULL, HOST_HELP_GROUP, -1, -1, -1, -1); - this->AddCommand(HOSTSERV, c, MOD_UNIQUE); + this->AddCommand(HOSTSERV, new CommandHSGroup(), MOD_UNIQUE); this->SetHostHelp(myHostServHelp); } }; - - /** * Add the help response to anopes /hs help output. * @param u The user who is requesting help **/ -void myHostServHelp(User * u) +void myHostServHelp(User *u) { notice_lang(s_HostServ, u, HOST_HELP_CMD_GROUP); } -/** - * The /hs group command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_group(User * u) -{ - NickAlias *na; - HostCore *tmp; - char *vHost = NULL; - char *vIdent = NULL; - char *creator = NULL; - HostCore *head = NULL; - time_t time; - bool found = false; - - head = hostCoreListHead(); - - if ((na = findnick(u->nick))) { - if (na->status & NS_IDENTIFIED) { - - tmp = findHostCore(head, u->nick, &found); - if (found) { - if (tmp == NULL) { - tmp = head; /* incase first in list */ - } else if (tmp->next) { /* we dont want the previous entry were not inserting! */ - tmp = tmp->next; /* jump to the next */ - } - - vHost = sstrdup(tmp->vHost); - if (tmp->vIdent) - vIdent = sstrdup(tmp->vIdent); - creator = sstrdup(tmp->creator); - time = tmp->time; - - do_hs_sync(na->nc, vIdent, vHost, creator, time); - if (tmp->vIdent) { - notice_lang(s_HostServ, u, HOST_IDENT_GROUP, - na->nc->display, vIdent, vHost); - } else { - notice_lang(s_HostServ, u, HOST_GROUP, na->nc->display, - vHost); - } - delete [] vHost; - if (vIdent) - delete [] vIdent; - delete [] creator; - - } else { - notice_lang(s_HostServ, u, HOST_NOT_ASSIGNED); - } - } else { - notice_lang(s_HostServ, u, HOST_ID); - } - } else { - notice_lang(s_HostServ, u, HOST_NOT_REGED); - } - return MOD_CONT; -} - MODULE_INIT("hs_group", HSGroup) diff --git a/src/core/hs_help.c b/src/core/hs_help.c index c953c8218..5cc70213c 100644 --- a/src/core/hs_help.c +++ b/src/core/hs_help.c @@ -6,8 +6,8 @@ * Please read COPYING and README for further details. * * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * + * Based on the original code of Services by Andy Church. + * * $Id$ * */ @@ -15,42 +15,37 @@ #include "module.h" -int do_help(User * u); +class CommandHSHelp : public Command +{ + public: + CommandHSHelp() : Command("HELP", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + mod_help_cmd(s_HostServ, u, HOSTSERV, params[0].c_str()); + return MOD_CONT; + } + + void OnSyntaxError(User *u) + { + notice_help(s_HostServ, u, HOST_HELP, s_HostServ); + moduleDisplayHelp(6, u); + } +}; class HSHelp : public Module { public: HSHelp(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("HELP", do_help, NULL, -1, -1, -1, -1, -1); - this->AddCommand(HOSTSERV, c, MOD_UNIQUE); + this->AddCommand(HOSTSERV, new CommandHSHelp(), MOD_UNIQUE); } }; - - -/** - * The /hs help command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_help(User * u) -{ - char *cmd = strtok(NULL, ""); - - if (!cmd) { - notice_help(s_HostServ, u, HOST_HELP, s_HostServ); - moduleDisplayHelp(6, u); - } else { - mod_help_cmd(s_HostServ, u, HOSTSERV, cmd); - } - return MOD_CONT; -} - MODULE_INIT("hs_help", HSHelp) diff --git a/src/core/hs_list.c b/src/core/hs_list.c index a6169eb3d..ea7e08967 100644 --- a/src/core/hs_list.c +++ b/src/core/hs_list.c @@ -15,162 +15,160 @@ #include "module.h" -int listOut(User * u); -void myHostServHelp(User * u); +void myHostServHelp(User *u); -class HSList : public Module +class CommandHSList : public Command { public: - HSList(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandHSList() : Command("LIST", 0, 1) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("LIST", listOut, is_services_oper, -1, -1, HOST_HELP_LIST, HOST_HELP_LIST, HOST_HELP_LIST); - this->AddCommand(HOSTSERV, c, MOD_UNIQUE); - this->SetHostHelp(myHostServHelp); } -}; - + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *key = params.size() ? params[0].c_str() : NULL; + struct tm *tm; + char buf[BUFSIZE]; + int counter = 1; + int from = 0, to = 0; + char *tmp = NULL; + char *s = NULL; + unsigned display_counter = 0; + HostCore *head = NULL; + HostCore *current; -/** - * Add the help response to anopes /hs help output. - * @param u The user who is requesting help - **/ -void myHostServHelp(User * u) -{ - if (is_services_oper(u)) { - notice_lang(s_HostServ, u, HOST_HELP_CMD_LIST); - } -} - -/** - * The /hs list command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int listOut(User * u) -{ - char *key = strtok(NULL, ""); - struct tm *tm; - char buf[BUFSIZE]; - int counter = 1; - int from = 0, to = 0; - char *tmp = NULL; - char *s = NULL; - unsigned display_counter = 0; - HostCore *head = NULL; - HostCore *current; - - head = hostCoreListHead(); + head = hostCoreListHead(); - current = head; - if (current == NULL) - notice_lang(s_HostServ, u, HOST_EMPTY); - else { - /** - * Do a check for a range here, then in the next loop - * we'll only display what has been requested.. - **/ - if (key) { - if (key[0] == '#') { - tmp = myStrGetOnlyToken((key + 1), '-', 0); /* Read FROM out */ - if (!tmp) { - notice_lang(s_ChanServ, u, LIST_INCORRECT_RANGE); - return MOD_CONT; - } - for (s = tmp; *s; s++) { - if (!isdigit(*s)) { - delete [] tmp; + current = head; + if (!current) + notice_lang(s_HostServ, u, HOST_EMPTY); + else + { + /** + * Do a check for a range here, then in the next loop + * we'll only display what has been requested.. + **/ + if (key) + { + if (key[0] == '#') + { + tmp = myStrGetOnlyToken((key + 1), '-', 0); /* Read FROM out */ + if (!tmp) + { notice_lang(s_ChanServ, u, LIST_INCORRECT_RANGE); return MOD_CONT; } - } - from = atoi(tmp); - delete [] tmp; - tmp = myStrGetTokenRemainder(key, '-', 1); /* Read TO out */ - if (!tmp) { - notice_lang(s_ChanServ, u, LIST_INCORRECT_RANGE); - return MOD_CONT; - } - for (s = tmp; *s; s++) { - if (!isdigit(*s)) { - delete [] tmp; + for (s = tmp; *s; ++s) + { + if (!isdigit(*s)) + { + delete [] tmp; + notice_lang(s_ChanServ, u, LIST_INCORRECT_RANGE); + return MOD_CONT; + } + } + from = atoi(tmp); + delete [] tmp; + tmp = myStrGetTokenRemainder(key, '-', 1); /* Read TO out */ + if (!tmp) + { notice_lang(s_ChanServ, u, LIST_INCORRECT_RANGE); return MOD_CONT; } + for (s = tmp; *s; ++s) + { + if (!isdigit(*s)) + { + delete [] tmp; + notice_lang(s_ChanServ, u, LIST_INCORRECT_RANGE); + return MOD_CONT; + } + } + to = atoi(tmp); + delete [] tmp; + key = NULL; } - to = atoi(tmp); - delete [] tmp; - key = NULL; } - } - while (current != NULL) { - if (key) { - if (((match_wild_nocase(key, current->nick)) - || (match_wild_nocase(key, current->vHost))) - && (display_counter < NSListMax)) { - display_counter++; - tm = localtime(¤t->time); - strftime_lang(buf, sizeof(buf), u, - STRFTIME_DATE_TIME_FORMAT, tm); - if (current->vIdent) { - notice_lang(s_HostServ, u, HOST_IDENT_ENTRY, - counter, current->nick, - current->vIdent, current->vHost, - current->creator, buf); - } else { - notice_lang(s_HostServ, u, HOST_ENTRY, counter, - current->nick, current->vHost, - current->creator, buf); + while (current) + { + if (key) + { + if ((match_wild_nocase(key, current->nick) || match_wild_nocase(key, current->vHost)) && display_counter < NSListMax) + { + ++display_counter; + tm = localtime(¤t->time); + strftime_lang(buf, sizeof(buf), u, STRFTIME_DATE_TIME_FORMAT, tm); + if (current->vIdent) + notice_lang(s_HostServ, u, HOST_IDENT_ENTRY, counter, current->nick, current->vIdent, current->vHost, current->creator, buf); + else + notice_lang(s_HostServ, u, HOST_ENTRY, counter, current->nick, current->vHost, current->creator, buf); } } - } else { - /** - * List the host if its in the display range, and not more - * than NSListMax records have been displayed... - **/ - if ((((counter >= from) && (counter <= to)) - || ((from == 0) && (to == 0))) - && (display_counter < NSListMax)) { - display_counter++; - tm = localtime(¤t->time); - strftime_lang(buf, sizeof(buf), u, - STRFTIME_DATE_TIME_FORMAT, tm); - if (current->vIdent) { - notice_lang(s_HostServ, u, HOST_IDENT_ENTRY, - counter, current->nick, - current->vIdent, current->vHost, - current->creator, buf); - } else { - notice_lang(s_HostServ, u, HOST_ENTRY, counter, - current->nick, current->vHost, - current->creator, buf); + else + { + /** + * List the host if its in the display range, and not more + * than NSListMax records have been displayed... + **/ + if (((counter >= from && counter <= to) || (!from && !to)) && display_counter < NSListMax) + { + ++display_counter; + tm = localtime(¤t->time); + strftime_lang(buf, sizeof(buf), u, STRFTIME_DATE_TIME_FORMAT, tm); + if (current->vIdent) + notice_lang(s_HostServ, u, HOST_IDENT_ENTRY, counter, current->nick, current->vIdent, current->vHost, current->creator, buf); + else + notice_lang(s_HostServ, u, HOST_ENTRY, counter, current->nick, current->vHost, current->creator, buf); } } + ++counter; + current = current->next; } - counter++; - current = current->next; - } - if (key) { - notice_lang(s_HostServ, u, HOST_LIST_KEY_FOOTER, key, - display_counter); - } else { - if (from != 0) { - notice_lang(s_HostServ, u, HOST_LIST_RANGE_FOOTER, from, - to); - } else { - notice_lang(s_HostServ, u, HOST_LIST_FOOTER, - display_counter); + if (key) + notice_lang(s_HostServ, u, HOST_LIST_KEY_FOOTER, key, display_counter); + else { + if (from) + notice_lang(s_HostServ, u, HOST_LIST_RANGE_FOOTER, from, to); + else + notice_lang(s_HostServ, u, HOST_LIST_FOOTER, display_counter); } } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_oper(u)) + return false; + + notice_lang(s_HostServ, u, HOST_HELP_LIST); + return true; } - return MOD_CONT; +}; + +class HSList : public Module +{ + public: + HSList(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + + this->AddCommand(HOSTSERV, new CommandHSList(), MOD_UNIQUE); + this->SetHostHelp(myHostServHelp); + } +}; + +/** + * Add the help response to anopes /hs help output. + * @param u The user who is requesting help + **/ +void myHostServHelp(User *u) +{ + if (is_services_oper(u)) + notice_lang(s_HostServ, u, HOST_HELP_CMD_LIST); } MODULE_INIT("hs_list", HSList) diff --git a/src/core/hs_off.c b/src/core/hs_off.c index 2214353e1..84639a941 100644 --- a/src/core/hs_off.c +++ b/src/core/hs_off.c @@ -15,63 +15,68 @@ #include "module.h" -int do_off(User * u); -void myHostServHelp(User * u); +void myHostServHelp(User *u); + +class CommandHSOff : public Command +{ + public: + CommandHSOff() : Command("OFF", 0, 0) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + NickAlias *na; + char *vhost; + char *vident = NULL; + if ((na = findnick(u->nick))) + { + if (na->status & NS_IDENTIFIED) + { + vhost = getvHost(u->nick); + vident = getvIdent(u->nick); + if (!vhost && !vident) + notice_lang(s_HostServ, u, HOST_NOT_ASSIGNED); + else + ircdproto->SendVhostDel(u); + } + else + notice_lang(s_HostServ, u, HOST_ID); + } + else + notice_lang(s_HostServ, u, HOST_NOT_REGED); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_HostServ, u, HOST_HELP_OFF); + return true; + } +}; class HSOff : public Module { public: HSOff(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("OFF", do_off, NULL, HOST_HELP_OFF, -1, -1, -1, -1); - this->AddCommand(HOSTSERV, c, MOD_UNIQUE); + this->AddCommand(HOSTSERV, new CommandHSOff(), MOD_UNIQUE); this->SetHostHelp(myHostServHelp); } }; - - /** * Add the help response to anopes /hs help output. * @param u The user who is requesting help **/ -void myHostServHelp(User * u) +void myHostServHelp(User *u) { notice_lang(s_HostServ, u, HOST_HELP_CMD_OFF); } -/** - * The /hs off command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_off(User * u) -{ - NickAlias *na; - char *vhost; - char *vident = NULL; - if ((na = findnick(u->nick))) { - if (na->status & NS_IDENTIFIED) { - vhost = getvHost(u->nick); - vident = getvIdent(u->nick); - if (vhost == NULL && vident == NULL) - notice_lang(s_HostServ, u, HOST_NOT_ASSIGNED); - else - ircdproto->SendVhostDel(u); - } else { - notice_lang(s_HostServ, u, HOST_ID); - } - } else { - notice_lang(s_HostServ, u, HOST_NOT_REGED); - } - return MOD_CONT; -} - MODULE_INIT("hs_off", HSOff) diff --git a/src/core/hs_on.c b/src/core/hs_on.c index 6d539ce7e..1cad7a93c 100644 --- a/src/core/hs_on.c +++ b/src/core/hs_on.c @@ -15,78 +15,82 @@ #include "module.h" -int do_on(User * u); -void myHostServHelp(User * u); +void myHostServHelp(User *u); + +class CommandHSOn : public Command +{ + public: + CommandHSOn() : Command("ON", 0, 0) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + NickAlias *na; + char *vHost; + char *vIdent = NULL; + if ((na = findnick(u->nick))) + { + if (na->status & NS_IDENTIFIED) + { + vHost = getvHost(u->nick); + vIdent = getvIdent(u->nick); + if (!vHost) + notice_lang(s_HostServ, u, HOST_NOT_ASSIGNED); + else + { + if (vIdent) + notice_lang(s_HostServ, u, HOST_IDENT_ACTIVATED, vIdent, vHost); + else + notice_lang(s_HostServ, u, HOST_ACTIVATED, vHost); + ircdproto->SendVhost(u->nick, vIdent, vHost); + if (ircd->vhost) + u->vhost = sstrdup(vHost); + if (ircd->vident) + { + if (vIdent) + u->SetVIdent(vIdent); + } + set_lastmask(u); + } + } + else + notice_lang(s_HostServ, u, HOST_ID); + } + else + notice_lang(s_HostServ, u, HOST_NOT_REGED); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_HostServ, u, HOST_HELP_ON); + return true; + } +}; class HSOn : public Module { public: HSOn(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("ON", do_on, NULL, HOST_HELP_ON, -1, -1, -1, -1); - this->AddCommand(HOSTSERV, c, MOD_UNIQUE); + this->AddCommand(HOSTSERV, new CommandHSOn(), MOD_UNIQUE); this->SetHostHelp(myHostServHelp); } }; - - /** * Add the help response to anopes /hs help output. * @param u The user who is requesting help **/ -void myHostServHelp(User * u) +void myHostServHelp(User *u) { notice_lang(s_HostServ, u, HOST_HELP_CMD_ON); } -/** - * The /hs on command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_on(User * u) -{ - NickAlias *na; - char *vHost; - char *vIdent = NULL; - if ((na = findnick(u->nick))) { - if (na->status & NS_IDENTIFIED) { - vHost = getvHost(u->nick); - vIdent = getvIdent(u->nick); - if (vHost == NULL) { - notice_lang(s_HostServ, u, HOST_NOT_ASSIGNED); - } else { - if (vIdent) { - notice_lang(s_HostServ, u, HOST_IDENT_ACTIVATED, - vIdent, vHost); - } else { - notice_lang(s_HostServ, u, HOST_ACTIVATED, vHost); - } - ircdproto->SendVhost(u->nick, vIdent, vHost); - if (ircd->vhost) { - u->vhost = sstrdup(vHost); - } - if (ircd->vident) { - if (vIdent) - u->vident = sstrdup(vIdent); - } - set_lastmask(u); - } - } else { - notice_lang(s_HostServ, u, HOST_ID); - } - } else { - notice_lang(s_HostServ, u, HOST_NOT_REGED); - } - return MOD_CONT; -} - MODULE_INIT("hs_on", HSOn) diff --git a/src/core/hs_set.c b/src/core/hs_set.c index 9a472cc44..49b22b3c7 100644 --- a/src/core/hs_set.c +++ b/src/core/hs_set.c @@ -15,153 +15,170 @@ #include "module.h" -int myDoSet(User * u); -void myHostServHelp(User * u); +void myHostServHelp(User *u); -class HSSet : public Module +class CommandHSSet : public Command { public: - HSSet(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandHSSet() : Command("SET", 2, 2) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("SET", myDoSet, is_host_setter, HOST_HELP_SET, -1, -1, -1, -1); - this->AddCommand(HOSTSERV, c, MOD_UNIQUE); - - this->SetHostHelp(myHostServHelp); - } -}; - - - -/** - * Add the help response to anopes /hs help output. - * @param u The user who is requesting help - **/ -void myHostServHelp(User * u) -{ - if (is_host_setter(u)) { - notice_lang(s_HostServ, u, HOST_HELP_CMD_SET); } -} - -/** - * The /hs set command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int myDoSet(User * u) -{ - char *nick = strtok(NULL, " "); - char *rawhostmask = strtok(NULL, " "); - char *hostmask = new char[HOSTMAX]; - - NickAlias *na; - int32 tmp_time; - char *s; - char *vIdent = NULL; - - if (!nick || !rawhostmask) { - notice_lang(s_HostServ, u, HOST_SET_SYNTAX, s_HostServ); - delete [] hostmask; - return MOD_CONT; - } - - vIdent = myStrGetOnlyToken(rawhostmask, '@', 0); /* Get the first substring, @ as delimiter */ - if (vIdent) { - rawhostmask = myStrGetTokenRemainder(rawhostmask, '@', 1); /* get the remaining string */ - if (!rawhostmask) { - notice_lang(s_HostServ, u, HOST_SET_SYNTAX, s_HostServ); - delete [] vIdent; + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[0].c_str(); + const char *rawhostmask = params[1].c_str(); + char *hostmask = new char[HOSTMAX]; + + NickAlias *na; + int32 tmp_time; + char *s; + + char *vIdent = NULL; + + vIdent = myStrGetOnlyToken(rawhostmask, '@', 0); /* Get the first substring, @ as delimiter */ + if (vIdent) + { + rawhostmask = myStrGetTokenRemainder(rawhostmask, '@', 1); /* get the remaining string */ + if (!rawhostmask) + { + notice_lang(s_HostServ, u, HOST_SET_SYNTAX, s_HostServ); + delete [] vIdent; + delete [] hostmask; + return MOD_CONT; + } + if (strlen(vIdent) > USERMAX - 1) + { + notice_lang(s_HostServ, u, HOST_SET_IDENTTOOLONG, USERMAX); + delete [] vIdent; + delete [] rawhostmask; + delete [] hostmask; + return MOD_CONT; + } + else + { + for (s = vIdent; *s; ++s) + { + if (!isvalidchar(*s)) + { + notice_lang(s_HostServ, u, HOST_SET_IDENT_ERROR); + delete [] vIdent; + delete [] rawhostmask; + delete [] hostmask; + return MOD_CONT; + } + } + } + if (!ircd->vident) + { + notice_lang(s_HostServ, u, HOST_NO_VIDENT); + delete [] vIdent; + delete [] rawhostmask; + delete [] hostmask; + return MOD_CONT; + } + } + if (strlen(rawhostmask) < HOSTMAX - 1) + snprintf(hostmask, HOSTMAX - 1, "%s", rawhostmask); + else + { + notice_lang(s_HostServ, u, HOST_SET_TOOLONG, HOSTMAX); + if (vIdent) + { + delete [] vIdent; + delete [] rawhostmask; + } delete [] hostmask; return MOD_CONT; } - if (strlen(vIdent) > USERMAX - 1) { - notice_lang(s_HostServ, u, HOST_SET_IDENTTOOLONG, USERMAX); - delete [] vIdent; - delete [] rawhostmask; + + if (!isValidHost(hostmask, 3)) + { + notice_lang(s_HostServ, u, HOST_SET_ERROR); + if (vIdent) + { + delete [] vIdent; + delete [] rawhostmask; + } delete [] hostmask; return MOD_CONT; - } else { - for (s = vIdent; *s; s++) { - if (!isvalidchar(*s)) { - notice_lang(s_HostServ, u, HOST_SET_IDENT_ERROR); + } + + + tmp_time = time(NULL); + + if ((na = findnick(nick))) + { + if (na->status & NS_VERBOTEN) + { + notice_lang(s_HostServ, u, NICK_X_FORBIDDEN, nick); + if (vIdent) + { delete [] vIdent; delete [] rawhostmask; - delete [] hostmask; - return MOD_CONT; } + delete [] hostmask; + return MOD_CONT; } + if (vIdent && ircd->vident) + alog("vHost for user \002%s\002 set to \002%s@%s\002 by oper \002%s\002", nick, vIdent, hostmask, u->nick); + else + alog("vHost for user \002%s\002 set to \002%s\002 by oper \002%s\002", nick, hostmask, u->nick); + addHostCore(nick, vIdent, hostmask, u->nick, tmp_time); + if (vIdent) + notice_lang(s_HostServ, u, HOST_IDENT_SET, nick, vIdent, hostmask); + else + notice_lang(s_HostServ, u, HOST_SET, nick, hostmask); } - if (!ircd->vident) { - notice_lang(s_HostServ, u, HOST_NO_VIDENT); - delete [] vIdent; - delete [] rawhostmask; - delete [] hostmask; - return MOD_CONT; - } - } - if (strlen(rawhostmask) < HOSTMAX - 1) - snprintf(hostmask, HOSTMAX - 1, "%s", rawhostmask); - else { - notice_lang(s_HostServ, u, HOST_SET_TOOLONG, HOSTMAX); - if (vIdent) { - delete [] vIdent; - delete [] rawhostmask; - } + else + notice_lang(s_HostServ, u, HOST_NOREG, nick); delete [] hostmask; - return MOD_CONT; - } - - if (!isValidHost(hostmask, 3)) { - notice_lang(s_HostServ, u, HOST_SET_ERROR); - if (vIdent) { + if (vIdent) + { delete [] vIdent; delete [] rawhostmask; } - delete [] hostmask; return MOD_CONT; } + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_host_setter(u)) + return false; - tmp_time = time(NULL); + notice_lang(s_HostServ, u, HOST_HELP_SET); + return true; + } - if ((na = findnick(nick))) { - if (na->status & NS_VERBOTEN) { - notice_lang(s_HostServ, u, NICK_X_FORBIDDEN, nick); - if (vIdent) { - delete [] vIdent; - delete [] rawhostmask; - } - delete [] hostmask; - return MOD_CONT; - } - if (vIdent && ircd->vident) { - alog("vHost for user \002%s\002 set to \002%s@%s\002 by oper \002%s\002", nick, vIdent, hostmask, u->nick); - } else { - alog("vHost for user \002%s\002 set to \002%s\002 by oper \002%s\002", nick, hostmask, u->nick); - } - addHostCore(nick, vIdent, hostmask, u->nick, tmp_time); - if (vIdent) { - notice_lang(s_HostServ, u, HOST_IDENT_SET, nick, vIdent, - hostmask); - } else { - notice_lang(s_HostServ, u, HOST_SET, nick, hostmask); - } - } else { - notice_lang(s_HostServ, u, HOST_NOREG, nick); + void OnSyntaxError(User *u) + { + syntax_error(s_HostServ, u, "SET", HOST_SET_SYNTAX, s_HostServ); } - delete [] hostmask; - if (vIdent) { - delete [] vIdent; - delete [] rawhostmask; +}; + +class HSSet : public Module +{ + public: + HSSet(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + + this->AddCommand(HOSTSERV, new CommandHSSet(), MOD_UNIQUE); + + this->SetHostHelp(myHostServHelp); } - return MOD_CONT; +}; + +/** + * Add the help response to anopes /hs help output. + * @param u The user who is requesting help + **/ +void myHostServHelp(User *u) +{ + if (is_host_setter(u)) + notice_lang(s_HostServ, u, HOST_HELP_CMD_SET); } MODULE_INIT("hs_set", HSSet) diff --git a/src/core/hs_setall.c b/src/core/hs_setall.c index 39605fd24..2124deda2 100644 --- a/src/core/hs_setall.c +++ b/src/core/hs_setall.c @@ -15,104 +15,125 @@ #include "module.h" -int do_setall(User * u); -void myHostServHelp(User * u); -extern int do_hs_sync(NickCore * nc, char *vIdent, char *hostmask, - char *creator, time_t time); +void myHostServHelp(User *u); +extern int do_hs_sync(NickCore *nc, char *vIdent, char *hostmask, char *creator, time_t time); -class HSSetAll : public Module +class CommandHSSetAll : public Command { public: - HSSetAll(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandHSSetAll() : Command("SETALL", 2, 2) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("SETALL", do_setall, is_host_setter, HOST_HELP_SETALL, -1, -1, -1, -1); - this->AddCommand(HOSTSERV, c, MOD_UNIQUE); - this->SetHostHelp(myHostServHelp); } -}; - - - -/** - * Add the help response to anopes /hs help output. - * @param u The user who is requesting help - **/ -void myHostServHelp(User * u) -{ - if (is_host_setter(u)) { - notice_lang(s_HostServ, u, HOST_HELP_CMD_SETALL); - } -} - -/** - * The /hs setall command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_setall(User * u) -{ - char *nick = strtok(NULL, " "); - char *rawhostmask = strtok(NULL, " "); - char *hostmask = new char[HOSTMAX]; - - NickAlias *na; - int32 tmp_time; - char *s; - char *vIdent = NULL; - - if (!nick || !rawhostmask) { - notice_lang(s_HostServ, u, HOST_SETALL_SYNTAX, s_HostServ); - delete [] hostmask; - return MOD_CONT; - } + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[0].c_str(); + const char *rawhostmask = params[1].c_str(); + char *hostmask = new char[HOSTMAX]; + + NickAlias *na; + int32 tmp_time; + char *s; + + char *vIdent = NULL; + + vIdent = myStrGetOnlyToken(rawhostmask, '@', 0); /* Get the first substring, @ as delimiter */ + if (vIdent) + { + rawhostmask = myStrGetTokenRemainder(rawhostmask, '@', 1); /* get the remaining string */ + if (!rawhostmask) + { + notice_lang(s_HostServ, u, HOST_SETALL_SYNTAX, s_HostServ); + delete [] vIdent; + delete [] hostmask; + return MOD_CONT; + } + if (strlen(vIdent) > USERMAX - 1) + { + notice_lang(s_HostServ, u, HOST_SET_IDENTTOOLONG, USERMAX); + delete [] vIdent; + delete [] rawhostmask; + delete [] hostmask; + return MOD_CONT; + } + else + { + for (s = vIdent; *s; ++s) + { + if (!isvalidchar(*s)) + { + notice_lang(s_HostServ, u, HOST_SET_IDENT_ERROR); + delete [] vIdent; + delete [] rawhostmask; + delete [] hostmask; + return MOD_CONT; + } + } + } + if (!ircd->vident) + { + notice_lang(s_HostServ, u, HOST_NO_VIDENT); + delete [] vIdent; + delete [] rawhostmask; + delete [] hostmask; + return MOD_CONT; + } + } - vIdent = myStrGetOnlyToken(rawhostmask, '@', 0); /* Get the first substring, @ as delimiter */ - if (vIdent) { - rawhostmask = myStrGetTokenRemainder(rawhostmask, '@', 1); /* get the remaining string */ - if (!rawhostmask) { - notice_lang(s_HostServ, u, HOST_SETALL_SYNTAX, s_HostServ); - delete [] vIdent; + if (strlen(rawhostmask) < HOSTMAX - 1) + snprintf(hostmask, HOSTMAX - 1, "%s", rawhostmask); + else + { + notice_lang(s_HostServ, u, HOST_SET_TOOLONG, HOSTMAX); + if (vIdent) + { + delete [] vIdent; + delete [] rawhostmask; + } delete [] hostmask; return MOD_CONT; } - if (strlen(vIdent) > USERMAX - 1) { - notice_lang(s_HostServ, u, HOST_SET_IDENTTOOLONG, USERMAX); - delete [] vIdent; - delete [] rawhostmask; + + if (!isValidHost(hostmask, 3)) + { + notice_lang(s_HostServ, u, HOST_SET_ERROR); + if (vIdent) + { + delete [] vIdent; + delete [] rawhostmask; + } delete [] hostmask; return MOD_CONT; - } else { - for (s = vIdent; *s; s++) { - if (!isvalidchar(*s)) { - notice_lang(s_HostServ, u, HOST_SET_IDENT_ERROR); + } + + tmp_time = time(NULL); + + if ((na = findnick(nick))) + { + if (na->status & NS_VERBOTEN) + { + notice_lang(s_HostServ, u, NICK_X_FORBIDDEN, nick); + if (vIdent) { delete [] vIdent; delete [] rawhostmask; - delete [] hostmask; - return MOD_CONT; } + delete [] hostmask; + return MOD_CONT; } + if (vIdent && ircd->vident) + alog("vHost for all nicks in group \002%s\002 set to \002%s@%s\002 by oper \002%s\002", nick, vIdent, hostmask, u->nick); + else + alog("vHost for all nicks in group \002%s\002 set to \002%s\002 by oper \002%s\002", nick, hostmask, u->nick); + do_hs_sync(na->nc, vIdent, hostmask, u->nick, tmp_time); + if (vIdent) + notice_lang(s_HostServ, u, HOST_IDENT_SETALL, nick, vIdent, hostmask); + else + notice_lang(s_HostServ, u, HOST_SETALL, nick, hostmask); } - if (!ircd->vident) { - notice_lang(s_HostServ, u, HOST_NO_VIDENT); - delete [] vIdent; - delete [] rawhostmask; - delete [] hostmask; - return MOD_CONT; - } - } - - if (strlen(rawhostmask) < HOSTMAX - 1) - snprintf(hostmask, HOSTMAX - 1, "%s", rawhostmask); - else { - notice_lang(s_HostServ, u, HOST_SET_TOOLONG, HOSTMAX); - if (vIdent) { + else + notice_lang(s_HostServ, u, HOST_NOREG, nick); + if (vIdent) + { delete [] vIdent; delete [] rawhostmask; } @@ -120,49 +141,43 @@ int do_setall(User * u) return MOD_CONT; } - if (!isValidHost(hostmask, 3)) { - notice_lang(s_HostServ, u, HOST_SET_ERROR); - if (vIdent) { - delete [] vIdent; - delete [] rawhostmask; - } - delete [] hostmask; - return MOD_CONT; - } + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_host_setter(u)) + return false; - tmp_time = time(NULL); + notice_lang(s_HostServ, u, HOST_HELP_SETALL); + return true; + } - if ((na = findnick(nick))) { - if (na->status & NS_VERBOTEN) { - notice_lang(s_HostServ, u, NICK_X_FORBIDDEN, nick); - if (vIdent) { - delete [] vIdent; - delete [] rawhostmask; - } - delete [] hostmask; - return MOD_CONT; - } - if (vIdent && ircd->vident) { - alog("vHost for all nicks in group \002%s\002 set to \002%s@%s\002 by oper \002%s\002", nick, vIdent, hostmask, u->nick); - } else { - alog("vHost for all nicks in group \002%s\002 set to \002%s\002 by oper \002%s\002", nick, hostmask, u->nick); - } - do_hs_sync(na->nc, vIdent, hostmask, u->nick, tmp_time); - if (vIdent) { - notice_lang(s_HostServ, u, HOST_IDENT_SETALL, nick, vIdent, - hostmask); - } else { - notice_lang(s_HostServ, u, HOST_SETALL, nick, hostmask); - } - } else { - notice_lang(s_HostServ, u, HOST_NOREG, nick); + void OnSyntaxError(User *u) + { + syntax_error(s_HostServ, u, "SETALL", HOST_SETALL_SYNTAX, s_HostServ); } - if (vIdent) { - delete [] vIdent; - delete [] rawhostmask; +}; + +class HSSetAll : public Module +{ + public: + HSSetAll(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + + this->AddCommand(HOSTSERV, new CommandHSSetAll(), MOD_UNIQUE); + this->SetHostHelp(myHostServHelp); } - delete [] hostmask; - return MOD_CONT; +}; + +/** + * Add the help response to anopes /hs help output. + * @param u The user who is requesting help + **/ +void myHostServHelp(User *u) +{ + if (is_host_setter(u)) + notice_lang(s_HostServ, u, HOST_HELP_CMD_SETALL); } MODULE_INIT("hs_setall", HSSetAll) diff --git a/src/core/ms_cancel.c b/src/core/ms_cancel.c index 17fa3d87b..63c81ea22 100644 --- a/src/core/ms_cancel.c +++ b/src/core/ms_cancel.c @@ -15,80 +15,82 @@ #include "module.h" -int do_cancel(User * u); -void myMemoServHelp(User * u); +void myMemoServHelp(User *u); + +class CommandMSCancel : public Command +{ + public: + CommandMSCancel() : Command("CANCEL", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + int ischan; + int isforbid; + const char *name = params[0].c_str(); + MemoInfo *mi; + + if (!nick_recognized(u)) + notice_lang(s_MemoServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + else if (!(mi = getmemoinfo(name, &ischan, &isforbid))) + { + if (isforbid) + notice_lang(s_MemoServ, u, ischan ? CHAN_X_FORBIDDEN : NICK_X_FORBIDDEN, name); + else + notice_lang(s_MemoServ, u, ischan ? CHAN_X_NOT_REGISTERED : NICK_X_NOT_REGISTERED, name); + } + else + { + int i; + + for (i = mi->memos.size() - 1; i >= 0; --i) + { + if ((mi->memos[i]->flags & MF_UNREAD) && !stricmp(mi->memos[i]->sender, u->na->nc->display) && (!(mi->memos[i]->flags & MF_NOTIFYS))) + { + delmemo(mi, mi->memos[i]->number); + notice_lang(s_MemoServ, u, MEMO_CANCELLED, name); + return MOD_CONT; + } + } + + notice_lang(s_MemoServ, u, MEMO_CANCEL_NONE); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_MemoServ, u, MEMO_HELP_CANCEL); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_MemoServ, u, "CANCEL", MEMO_CANCEL_SYNTAX); + } +}; class MSCancel : public Module { public: MSCancel(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("CANCEL", do_cancel, NULL, MEMO_HELP_CANCEL, -1, -1, -1, -1); - this->AddCommand(MEMOSERV, c, MOD_UNIQUE); + this->AddCommand(MEMOSERV, new CommandMSCancel(), MOD_UNIQUE); this->SetMemoHelp(myMemoServHelp); } }; - - /** * Add the help response to anopes /ms help output. * @param u The user who is requesting help **/ -void myMemoServHelp(User * u) +void myMemoServHelp(User *u) { notice_lang(s_MemoServ, u, MEMO_HELP_CMD_CANCEL); } -/** - * The /ms cancel command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_cancel(User * u) -{ - int ischan; - int isforbid; - char *name = strtok(NULL, " "); - MemoInfo *mi; - - if (!name) { - syntax_error(s_MemoServ, u, "CANCEL", MEMO_CANCEL_SYNTAX); - - } else if (!nick_recognized(u)) { - notice_lang(s_MemoServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); - - } else if (!(mi = getmemoinfo(name, &ischan, &isforbid))) { - if (isforbid) { - notice_lang(s_MemoServ, u, - ischan ? CHAN_X_FORBIDDEN : - NICK_X_FORBIDDEN, name); - } else { - notice_lang(s_MemoServ, u, - ischan ? CHAN_X_NOT_REGISTERED : - NICK_X_NOT_REGISTERED, name); - } - } else { - int i; - - for (i = mi->memos.size() - 1; i >= 0; i--) { - if ((mi->memos[i]->flags & MF_UNREAD) - && !stricmp(mi->memos[i]->sender, u->na->nc->display) - && (!(mi->memos[i]->flags & MF_NOTIFYS))) { - delmemo(mi, mi->memos[i]->number); - notice_lang(s_MemoServ, u, MEMO_CANCELLED, name); - return MOD_CONT; - } - } - - notice_lang(s_MemoServ, u, MEMO_CANCEL_NONE); - } - return MOD_CONT; -} - MODULE_INIT("ms_cancel", MSCancel) diff --git a/src/core/ms_check.c b/src/core/ms_check.c index 12be375e1..7f13db617 100644 --- a/src/core/ms_check.c +++ b/src/core/ms_check.c @@ -15,93 +15,101 @@ #include "module.h" -int do_memocheck(User * u); -void myMemoServHelp(User * u); +void myMemoServHelp(User *u); + +class CommandMSCheck : public Command +{ + public: + CommandMSCheck() : Command("CHECK", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + NickAlias *na = NULL; + MemoInfo *mi = NULL; + int i, found = 0; + const char *recipient = params[0].c_str(); + struct tm *tm; + char timebuf[64]; + + if (!nick_recognized(u)) + { + notice_lang(s_MemoServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + return MOD_CONT; + } + else if (!(na = findnick(recipient))) + { + notice_lang(s_MemoServ, u, NICK_X_NOT_REGISTERED, recipient); + return MOD_CONT; + } + + if ((na->status & NS_VERBOTEN)) + { + notice_lang(s_MemoServ, u, NICK_X_FORBIDDEN, recipient); + return MOD_CONT; + } + + mi = &na->nc->memos; + + /* Okay, I know this looks strange but we wanna get the LAST memo, so we + have to loop backwards */ + + for (i = mi->memos.size() - 1; i >= 0; --i) + { + if (!stricmp(mi->memos[i]->sender, u->na->nc->display)) + { + found = 1; /* Yes, we've found the memo */ + + tm = localtime(&mi->memos[i]->time); + strftime_lang(timebuf, sizeof(timebuf), u, STRFTIME_DATE_TIME_FORMAT, tm); + + if (mi->memos[i]->flags & MF_UNREAD) + notice_lang(s_MemoServ, u, MEMO_CHECK_NOT_READ, na->nick, timebuf); + else + notice_lang(s_MemoServ, u, MEMO_CHECK_READ, na->nick, timebuf); + break; + } + } + + if (!found) + notice_lang(s_MemoServ, u, MEMO_CHECK_NO_MEMO, na->nick); + + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_MemoServ, u, MEMO_HELP_CHECK); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_MemoServ, u, "CHECK", MEMO_CHECK_SYNTAX); + } +}; class MSCheck : public Module { public: MSCheck(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("CHECK", do_memocheck, NULL, MEMO_HELP_CHECK, -1, -1, -1, -1); - this->AddCommand(MEMOSERV, c, MOD_UNIQUE); + this->AddCommand(MEMOSERV, new CommandMSCheck(), MOD_UNIQUE); this->SetMemoHelp(myMemoServHelp); } }; - - /** * Add the help response to anopes /ms help output. * @param u The user who is requesting help **/ -void myMemoServHelp(User * u) +void myMemoServHelp(User *u) { notice_lang(s_MemoServ, u, MEMO_HELP_CMD_CHECK); } -/** - * The /ms check command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_memocheck(User * u) -{ - NickAlias *na = NULL; - MemoInfo *mi = NULL; - int i, found = 0; - char *recipient = strtok(NULL, ""); - struct tm *tm; - char timebuf[64]; - - if (!recipient) { - syntax_error(s_MemoServ, u, "CHECK", MEMO_CHECK_SYNTAX); - return MOD_CONT; - } else if (!nick_recognized(u)) { - notice_lang(s_MemoServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); - return MOD_CONT; - } else if (!(na = findnick(recipient))) { - notice_lang(s_MemoServ, u, NICK_X_NOT_REGISTERED, recipient); - return MOD_CONT; - } - - if ((na->status & NS_VERBOTEN)) { - notice_lang(s_MemoServ, u, NICK_X_FORBIDDEN, recipient); - return MOD_CONT; - } - - mi = &na->nc->memos; - -/* Okay, I know this looks strange but we wanna get the LAST memo, so we - have to loop backwards */ - - for (i = (mi->memos.size() - 1); i >= 0; i--) { - if (!stricmp(mi->memos[i]->sender, u->na->nc->display)) { - found = 1; /* Yes, we've found the memo */ - - tm = localtime(&mi->memos[i]->time); - strftime_lang(timebuf, sizeof(timebuf), u, - STRFTIME_DATE_TIME_FORMAT, tm); - - if (mi->memos[i]->flags & MF_UNREAD) - notice_lang(s_MemoServ, u, MEMO_CHECK_NOT_READ, na->nick, - timebuf); - else - notice_lang(s_MemoServ, u, MEMO_CHECK_READ, na->nick, - timebuf); - break; - } - } - - if (!found) - notice_lang(s_MemoServ, u, MEMO_CHECK_NO_MEMO, na->nick); - - return MOD_CONT; -} - MODULE_INIT("ms_check", MSCheck) diff --git a/src/core/ms_del.c b/src/core/ms_del.c index b77f7b950..58c7bf2c1 100644 --- a/src/core/ms_del.c +++ b/src/core/ms_del.c @@ -15,141 +15,165 @@ #include "module.h" -int do_del(User * u); -int del_memo_callback(User * u, int num, va_list args); -void myMemoServHelp(User * u); +int del_memo_callback(User *u, int num, va_list args); +void myMemoServHelp(User *u); -class MSDel : public Module +class CommandMSDel : public Command { public: - MSDel(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandMSDel() : Command("DEL", 0, 2) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - c = createCommand("DEL", do_del, NULL, MEMO_HELP_DEL, -1, -1, -1, -1); - this->AddCommand(MEMOSERV, c, MOD_UNIQUE); - this->SetMemoHelp(myMemoServHelp); } -}; - - - -/** - * Add the help response to anopes /ms help output. - * @param u The user who is requesting help - **/ -void myMemoServHelp(User * u) -{ - notice_lang(s_MemoServ, u, MEMO_HELP_CMD_DEL); -} -/** - * The /ms del command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_del(User * u) -{ - MemoInfo *mi; - ChannelInfo *ci; - char *numstr = strtok(NULL, ""), *chan = NULL; - int last, last0, i; - char buf[BUFSIZE], *end; - int delcount, count, left; + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + MemoInfo *mi; + ChannelInfo *ci; + const char *numstr = params.size() ? params[0].c_str() : NULL, *chan = NULL; + int last, last0, i; + char buf[BUFSIZE], *end; + int delcount, count, left; - if (numstr && *numstr == '#') { - chan = strtok(numstr, " "); - numstr = strtok(NULL, ""); - if (!(ci = cs_findchan(chan))) { - notice_lang(s_MemoServ, u, CHAN_X_NOT_REGISTERED, chan); - return MOD_CONT; - } else if (readonly) { - notice_lang(s_MemoServ, u, READ_ONLY_MODE); - return MOD_CONT; - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_MemoServ, u, CHAN_X_FORBIDDEN, chan); - return MOD_CONT; - } else if (!check_access(u, ci, CA_MEMO)) { - notice_lang(s_MemoServ, u, ACCESS_DENIED); - return MOD_CONT; + if (numstr && *numstr == '#') + { + chan = numstr; + numstr = params.size() > 1 ? params[1].c_str() : NULL; + if (!(ci = cs_findchan(chan))) + { + notice_lang(s_MemoServ, u, CHAN_X_NOT_REGISTERED, chan); + return MOD_CONT; + } + else if (readonly) + { + notice_lang(s_MemoServ, u, READ_ONLY_MODE); + return MOD_CONT; + } + else if (ci->flags & CI_VERBOTEN) + { + notice_lang(s_MemoServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } + else if (!check_access(u, ci, CA_MEMO)) + { + notice_lang(s_MemoServ, u, ACCESS_DENIED); + return MOD_CONT; + } + mi = &ci->memos; } - mi = &ci->memos; - } else { - if (!nick_identified(u)) { - notice_lang(s_MemoServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); - return MOD_CONT; + else + { + if (!nick_identified(u)) + { + notice_lang(s_MemoServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + return MOD_CONT; + } + mi = &u->na->nc->memos; + } + if (!numstr || (!isdigit(*numstr) && stricmp(numstr, "ALL") && stricmp(numstr, "LAST"))) + this->OnSyntaxError(u); + else if (mi->memos.empty()) + { + if (chan) + notice_lang(s_MemoServ, u, MEMO_X_HAS_NO_MEMOS, chan); + else + notice_lang(s_MemoServ, u, MEMO_HAVE_NO_MEMOS); } - mi = &u->na->nc->memos; - } - if (!numstr - || (!isdigit(*numstr) && stricmp(numstr, "ALL") != 0 - && stricmp(numstr, "LAST") != 0)) { - syntax_error(s_MemoServ, u, "DEL", MEMO_DEL_SYNTAX); - } else if (mi->memos.size() == 0) { - if (chan) - notice_lang(s_MemoServ, u, MEMO_X_HAS_NO_MEMOS, chan); else - notice_lang(s_MemoServ, u, MEMO_HAVE_NO_MEMOS); - } else { - if (isdigit(*numstr)) { - /* Delete a specific memo or memos. */ - last = -1; /* Last memo deleted */ - last0 = -1; /* Beginning of range of last memos deleted */ - end = buf; - left = sizeof(buf); - delcount = - process_numlist(numstr, &count, del_memo_callback, u, mi, - &last, &last0, &end, &left); - if (last != -1) { - /* Some memos got deleted; tell them which ones. */ - if (delcount > 1) { - if (last0 != last) - end += snprintf(end, sizeof(buf) - (end - buf), - ",%d-%d", last0, last); + { + if (isdigit(*numstr)) + { + /* Delete a specific memo or memos. */ + last = -1; /* Last memo deleted */ + last0 = -1; /* Beginning of range of last memos deleted */ + end = buf; + left = sizeof(buf); + delcount = process_numlist(numstr, &count, del_memo_callback, u, mi, &last, &last0, &end, &left); + if (last != -1) + { + /* Some memos got deleted; tell them which ones. */ + if (delcount > 1) + { + if (last0 != last) + end += snprintf(end, sizeof(buf) - (end - buf), ",%d-%d", last0, last); + else + end += snprintf(end, sizeof(buf) - (end - buf), ",%d", last); + /* "buf+1" here because *buf == ',' */ + notice_lang(s_MemoServ, u, MEMO_DELETED_SEVERAL, buf + 1); + } else - end += snprintf(end, sizeof(buf) - (end - buf), - ",%d", last); - /* "buf+1" here because *buf == ',' */ - notice_lang(s_MemoServ, u, MEMO_DELETED_SEVERAL, - buf + 1); - } else { - notice_lang(s_MemoServ, u, MEMO_DELETED_ONE, last); + notice_lang(s_MemoServ, u, MEMO_DELETED_ONE, last); } - } else { - /* No memos were deleted. Tell them so. */ - if (count == 1) - notice_lang(s_MemoServ, u, MEMO_DOES_NOT_EXIST, - atoi(numstr)); else - notice_lang(s_MemoServ, u, MEMO_DELETED_NONE); + { + /* No memos were deleted. Tell them so. */ + if (count == 1) + notice_lang(s_MemoServ, u, MEMO_DOES_NOT_EXIST, atoi(numstr)); + else + notice_lang(s_MemoServ, u, MEMO_DELETED_NONE); + } } - } else if (stricmp(numstr, "LAST") == 0) { - /* Delete last memo. */ - for (i = 0; i < mi->memos.size(); i++) - last = mi->memos[i]->number; - delmemo(mi, last); - notice_lang(s_MemoServ, u, MEMO_DELETED_ONE, last); - } else { - /* Delete all memos. */ - for (i = 0; i < mi->memos.size(); i++) { - delete [] mi->memos[i]->text; - delete mi->memos[i]; + else if (!stricmp(numstr, "LAST")) + { + /* Delete last memo. */ + for (i = 0; i < mi->memos.size(); ++i) + last = mi->memos[i]->number; + delmemo(mi, last); + notice_lang(s_MemoServ, u, MEMO_DELETED_ONE, last); } - mi->memos.clear(); - if (chan) - notice_lang(s_MemoServ, u, MEMO_CHAN_DELETED_ALL, chan); else - notice_lang(s_MemoServ, u, MEMO_DELETED_ALL); + { + /* Delete all memos. */ + for (i = 0; i < mi->memos.size(); ++i) + { + delete [] mi->memos[i]->text; + delete mi->memos[i]; + } + mi->memos.clear(); + if (chan) + notice_lang(s_MemoServ, u, MEMO_CHAN_DELETED_ALL, chan); + else + notice_lang(s_MemoServ, u, MEMO_DELETED_ALL); + } + + /* Reset the order */ + for (i = 0; i < mi->memos.size(); ++i) + mi->memos[i]->number = i + 1; } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_MemoServ, u, MEMO_HELP_DEL); + return true; + } - /* Reset the order */ - for (i = 0; i < mi->memos.size(); i++) - mi->memos[i]->number = i + 1; + void OnSyntaxError(User *u) + { + syntax_error(s_MemoServ, u, "DEL", MEMO_DEL_SYNTAX); + } +}; + +class MSDel : public Module +{ + public: + MSDel(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(MEMOSERV, new CommandMSDel(), MOD_UNIQUE); + this->SetMemoHelp(myMemoServHelp); } - return MOD_CONT; +}; + +/** + * Add the help response to anopes /ms help output. + * @param u The user who is requesting help + **/ +void myMemoServHelp(User *u) +{ + notice_lang(s_MemoServ, u, MEMO_HELP_CMD_DEL); } /** @@ -159,7 +183,7 @@ int do_del(User * u) * @param va_list Variable Arguemtns * @return 1 if successful, 0 if it fails */ -int del_memo_callback(User * u, int num, va_list args) +int del_memo_callback(User *u, int num, va_list args) { MemoInfo *mi = va_arg(args, MemoInfo *); int *last = va_arg(args, int *); @@ -167,9 +191,12 @@ int del_memo_callback(User * u, int num, va_list args) char **end = va_arg(args, char **); int *left = va_arg(args, int *); - if (delmemo(mi, num)) { - if (num != (*last) + 1) { - if (*last != -1) { + if (delmemo(mi, num)) + { + if (num != (*last) + 1) + { + if (*last != -1) + { int len; if (*last0 != *last) len = snprintf(*end, *left, ",%d-%d", *last0, *last); @@ -182,9 +209,9 @@ int del_memo_callback(User * u, int num, va_list args) } *last = num; return 1; - } else { - return 0; } + else + return 0; } MODULE_INIT("ms_del", MSDel) diff --git a/src/core/ms_help.c b/src/core/ms_help.c index 0b5db69ce..4fa4ac783 100644 --- a/src/core/ms_help.c +++ b/src/core/ms_help.c @@ -6,8 +6,8 @@ * Please read COPYING and README for further details. * * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * + * Based on the original code of Services by Andy Church. + * * $Id$ * */ @@ -15,43 +15,37 @@ #include "module.h" -int do_help(User * u); +class CommandMSHelp : public Command +{ + public: + CommandMSHelp() : Command("HELP", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + mod_help_cmd(s_MemoServ, u, MEMOSERV, params[0].c_str()); + return MOD_CONT; + } + + void OnSyntaxError(User *u) + { + notice_help(s_MemoServ, u, MEMO_HELP_HEADER); + moduleDisplayHelp(3, u); + notice_help(s_MemoServ, u, MEMO_HELP_FOOTER, s_ChanServ); + } +}; class MSHelp : public Module { public: MSHelp(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("HELP", do_help, NULL, -1, -1, -1, -1, -1); - this->AddCommand(MEMOSERV, c, MOD_UNIQUE); + this->AddCommand(MEMOSERV, new CommandMSHelp(), MOD_UNIQUE); } }; - - - -/** - * The /ms help command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_help(User * u) -{ - char *cmd = strtok(NULL, ""); - - if (!cmd) { - notice_help(s_MemoServ, u, MEMO_HELP_HEADER); - moduleDisplayHelp(3, u); - notice_help(s_MemoServ, u, MEMO_HELP_FOOTER, s_ChanServ); - } else { - mod_help_cmd(s_MemoServ, u, MEMOSERV, cmd); - } - return MOD_CONT; -} - MODULE_INIT("ms_help", MSHelp) diff --git a/src/core/ms_info.c b/src/core/ms_info.c index 6fc7c4a04..a2ef38a4d 100644 --- a/src/core/ms_info.c +++ b/src/core/ms_info.c @@ -15,206 +15,226 @@ #include "module.h" -int do_info(User * u); -void myMemoServHelp(User * u); +void myMemoServHelp(User *u); -class MSInfo : public Module +class CommandMSInfo : public Command { public: - MSInfo(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandMSInfo() : Command("INFO", 0, 1) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - c = createCommand("INFO", do_info, NULL, -1, MEMO_HELP_INFO, -1, MEMO_SERVADMIN_HELP_INFO, MEMO_SERVADMIN_HELP_INFO); - this->AddCommand(MEMOSERV, c, MOD_UNIQUE); - this->SetMemoHelp(myMemoServHelp); } -}; - - -/** - * Add the help response to anopes /ms help output. - * @param u The user who is requesting help - **/ -void myMemoServHelp(User * u) -{ - notice_lang(s_MemoServ, u, MEMO_HELP_CMD_INFO); -} - -/** - * The /ms info command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_info(User * u) -{ - MemoInfo *mi; - NickAlias *na = NULL; - ChannelInfo *ci = NULL; - char *name = strtok(NULL, " "); - int is_servadmin = is_services_admin(u); - int hardmax = 0; - - if (is_servadmin && name && *name != '#') { - na = findnick(name); - if (!na) { - notice_lang(s_MemoServ, u, NICK_X_NOT_REGISTERED, name); - return MOD_CONT; - } else if (na->status & NS_VERBOTEN) { - notice_lang(s_MemoServ, u, NICK_X_FORBIDDEN, name); - return MOD_CONT; + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + MemoInfo *mi; + NickAlias *na = NULL; + ChannelInfo *ci = NULL; + const char *name = params.size() ? params[0].c_str() : NULL; + int is_servadmin = is_services_admin(u); + int hardmax = 0; + + if (is_servadmin && name && *name != '#') + { + na = findnick(name); + if (!na) + { + notice_lang(s_MemoServ, u, NICK_X_NOT_REGISTERED, name); + return MOD_CONT; + } + else if (na->status & NS_VERBOTEN) + { + notice_lang(s_MemoServ, u, NICK_X_FORBIDDEN, name); + return MOD_CONT; + } + mi = &na->nc->memos; + hardmax = na->nc->flags & NI_MEMO_HARDMAX ? 1 : 0; } - mi = &na->nc->memos; - hardmax = na->nc->flags & NI_MEMO_HARDMAX ? 1 : 0; - } else if (name && *name == '#') { - ci = cs_findchan(name); - if (!ci) { - notice_lang(s_MemoServ, u, CHAN_X_NOT_REGISTERED, name); - return MOD_CONT; - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_MemoServ, u, CHAN_X_FORBIDDEN, name); - return MOD_CONT; - } else if (!check_access(u, ci, CA_MEMO)) { + else if (name && *name == '#') + { + ci = cs_findchan(name); + if (!ci) + { + notice_lang(s_MemoServ, u, CHAN_X_NOT_REGISTERED, name); + return MOD_CONT; + } + else if (ci->flags & CI_VERBOTEN) + { + notice_lang(s_MemoServ, u, CHAN_X_FORBIDDEN, name); + return MOD_CONT; + } + else if (!check_access(u, ci, CA_MEMO)) + { + notice_lang(s_MemoServ, u, ACCESS_DENIED); + return MOD_CONT; + } + mi = &ci->memos; + hardmax = ci->flags & CI_MEMO_HARDMAX ? 1 : 0; + } + else if (name) /* It's not a chan and we aren't services admin */ + { notice_lang(s_MemoServ, u, ACCESS_DENIED); return MOD_CONT; } - mi = &ci->memos; - hardmax = ci->flags & CI_MEMO_HARDMAX ? 1 : 0; - } else if (name) { /* It's not a chan and we aren't services admin */ - notice_lang(s_MemoServ, u, ACCESS_DENIED); - return MOD_CONT; - } else { /* !name */ - if (!nick_identified(u)) { - notice_lang(s_MemoServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); - return MOD_CONT; + else /* !name */ + { + if (!nick_identified(u)) + { + notice_lang(s_MemoServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + return MOD_CONT; + } + mi = &u->na->nc->memos; + hardmax = u->na->nc->flags & NI_MEMO_HARDMAX ? 1 : 0; } - mi = &u->na->nc->memos; - hardmax = u->na->nc->flags & NI_MEMO_HARDMAX ? 1 : 0; - } - if (name && (ci || na->nc != u->na->nc)) { - - if (mi->memos.empty()) { - notice_lang(s_MemoServ, u, MEMO_INFO_X_NO_MEMOS, name); - } else if (mi->memos.size() == 1) { - if (mi->memos[0]->flags & MF_UNREAD) - notice_lang(s_MemoServ, u, MEMO_INFO_X_MEMO_UNREAD, name); - else - notice_lang(s_MemoServ, u, MEMO_INFO_X_MEMO, name); - } else { - int count = 0, i; - for (i = 0; i < mi->memos.size(); i++) { - if (mi->memos[i]->flags & MF_UNREAD) - count++; + if (name && (ci || na->nc != u->na->nc)) + { + if (mi->memos.empty()) + notice_lang(s_MemoServ, u, MEMO_INFO_X_NO_MEMOS, name); + else if (mi->memos.size() == 1) + { + if (mi->memos[0]->flags & MF_UNREAD) + notice_lang(s_MemoServ, u, MEMO_INFO_X_MEMO_UNREAD, name); + else + notice_lang(s_MemoServ, u, MEMO_INFO_X_MEMO, name); } - if (count == mi->memos.size()) - notice_lang(s_MemoServ, u, MEMO_INFO_X_MEMOS_ALL_UNREAD, - name, count); - else if (count == 0) - notice_lang(s_MemoServ, u, MEMO_INFO_X_MEMOS, name, - mi->memos.size()); - else if (count == 1) - notice_lang(s_MemoServ, u, MEMO_INFO_X_MEMOS_ONE_UNREAD, - name, mi->memos.size()); else - notice_lang(s_MemoServ, u, MEMO_INFO_X_MEMOS_SOME_UNREAD, - name, mi->memos.size(), count); - } - if (mi->memomax == 0) { - if (hardmax) - notice_lang(s_MemoServ, u, MEMO_INFO_X_HARD_LIMIT, name, - mi->memomax); - else - notice_lang(s_MemoServ, u, MEMO_INFO_X_LIMIT, name, - mi->memomax); - } else if (mi->memomax > 0) { - if (hardmax) - notice_lang(s_MemoServ, u, MEMO_INFO_X_HARD_LIMIT, name, - mi->memomax); + { + int count = 0, i; + for (i = 0; i < mi->memos.size(); ++i) + { + if (mi->memos[i]->flags & MF_UNREAD) + ++count; + } + if (count == mi->memos.size()) + notice_lang(s_MemoServ, u, MEMO_INFO_X_MEMOS_ALL_UNREAD, name, count); + else if (!count) + notice_lang(s_MemoServ, u, MEMO_INFO_X_MEMOS, name, mi->memos.size()); + else if (count == 1) + notice_lang(s_MemoServ, u, MEMO_INFO_X_MEMOS_ONE_UNREAD, name, mi->memos.size()); + else + notice_lang(s_MemoServ, u, MEMO_INFO_X_MEMOS_SOME_UNREAD, name, mi->memos.size(), count); + } + if (!mi->memomax) + { + if (hardmax) + notice_lang(s_MemoServ, u, MEMO_INFO_X_HARD_LIMIT, name, mi->memomax); + else + notice_lang(s_MemoServ, u, MEMO_INFO_X_LIMIT, name, mi->memomax); + } + else if (mi->memomax > 0) + { + if (hardmax) + notice_lang(s_MemoServ, u, MEMO_INFO_X_HARD_LIMIT, name, mi->memomax); + else + notice_lang(s_MemoServ, u, MEMO_INFO_X_LIMIT, name, mi->memomax); + } else - notice_lang(s_MemoServ, u, MEMO_INFO_X_LIMIT, name, - mi->memomax); - } else { - notice_lang(s_MemoServ, u, MEMO_INFO_X_NO_LIMIT, name); - } - - /* I ripped this code out of ircservices 4.4.5, since I didn't want - to rewrite the whole thing (it pisses me off). */ - if (na) { - if ((na->nc->flags & NI_MEMO_RECEIVE) - && (na->nc->flags & NI_MEMO_SIGNON)) { - notice_lang(s_MemoServ, u, MEMO_INFO_X_NOTIFY_ON, name); - } else if (na->nc->flags & NI_MEMO_RECEIVE) { - notice_lang(s_MemoServ, u, MEMO_INFO_X_NOTIFY_RECEIVE, - name); - } else if (na->nc->flags & NI_MEMO_SIGNON) { - notice_lang(s_MemoServ, u, MEMO_INFO_X_NOTIFY_SIGNON, - name); - } else { - notice_lang(s_MemoServ, u, MEMO_INFO_X_NOTIFY_OFF, name); + notice_lang(s_MemoServ, u, MEMO_INFO_X_NO_LIMIT, name); + + /* I ripped this code out of ircservices 4.4.5, since I didn't want + to rewrite the whole thing (it pisses me off). */ + if (na) + { + if ((na->nc->flags & NI_MEMO_RECEIVE) && (na->nc->flags & NI_MEMO_SIGNON)) + notice_lang(s_MemoServ, u, MEMO_INFO_X_NOTIFY_ON, name); + else if (na->nc->flags & NI_MEMO_RECEIVE) + notice_lang(s_MemoServ, u, MEMO_INFO_X_NOTIFY_RECEIVE, name); + else if (na->nc->flags & NI_MEMO_SIGNON) + notice_lang(s_MemoServ, u, MEMO_INFO_X_NOTIFY_SIGNON, name); + else + notice_lang(s_MemoServ, u, MEMO_INFO_X_NOTIFY_OFF, name); } } - - } else { /* !name || (!ci || na->nc == u->na->nc) */ - - if (mi->memos.empty()) { - notice_lang(s_MemoServ, u, MEMO_INFO_NO_MEMOS); - } else if (mi->memos.size() == 1) { - if (mi->memos[0]->flags & MF_UNREAD) - notice_lang(s_MemoServ, u, MEMO_INFO_MEMO_UNREAD); - else - notice_lang(s_MemoServ, u, MEMO_INFO_MEMO); - } else { - int count = 0, i; - for (i = 0; i < mi->memos.size(); i++) { - if (mi->memos[i]->flags & MF_UNREAD) - count++; + else /* !name || (!ci || na->nc == u->na->nc) */ + { + if (mi->memos.empty()) + notice_lang(s_MemoServ, u, MEMO_INFO_NO_MEMOS); + else if (mi->memos.size() == 1) + { + if (mi->memos[0]->flags & MF_UNREAD) + notice_lang(s_MemoServ, u, MEMO_INFO_MEMO_UNREAD); + else + notice_lang(s_MemoServ, u, MEMO_INFO_MEMO); } - if (count == mi->memos.size()) - notice_lang(s_MemoServ, u, MEMO_INFO_MEMOS_ALL_UNREAD, - count); - else if (count == 0) - notice_lang(s_MemoServ, u, MEMO_INFO_MEMOS, mi->memos.size()); - else if (count == 1) - notice_lang(s_MemoServ, u, MEMO_INFO_MEMOS_ONE_UNREAD, - mi->memos.size()); else - notice_lang(s_MemoServ, u, MEMO_INFO_MEMOS_SOME_UNREAD, - mi->memos.size(), count); - } + { + int count = 0, i; + for (i = 0; i < mi->memos.size(); ++i) + { + if (mi->memos[i]->flags & MF_UNREAD) + ++count; + } + if (count == mi->memos.size()) + notice_lang(s_MemoServ, u, MEMO_INFO_MEMOS_ALL_UNREAD, count); + else if (!count) + notice_lang(s_MemoServ, u, MEMO_INFO_MEMOS, mi->memos.size()); + else if (count == 1) + notice_lang(s_MemoServ, u, MEMO_INFO_MEMOS_ONE_UNREAD, mi->memos.size()); + else + notice_lang(s_MemoServ, u, MEMO_INFO_MEMOS_SOME_UNREAD, mi->memos.size(), count); + } - if (mi->memomax == 0) { - if (!is_servadmin && hardmax) - notice_lang(s_MemoServ, u, MEMO_INFO_HARD_LIMIT_ZERO); + if (!mi->memomax) + { + if (!is_servadmin && hardmax) + notice_lang(s_MemoServ, u, MEMO_INFO_HARD_LIMIT_ZERO); + else + notice_lang(s_MemoServ, u, MEMO_INFO_LIMIT_ZERO); + } + else if (mi->memomax > 0) + { + if (!is_servadmin && hardmax) + notice_lang(s_MemoServ, u, MEMO_INFO_HARD_LIMIT, mi->memomax); + else + notice_lang(s_MemoServ, u, MEMO_INFO_LIMIT, mi->memomax); + } else - notice_lang(s_MemoServ, u, MEMO_INFO_LIMIT_ZERO); - } else if (mi->memomax > 0) { - if (!is_servadmin && hardmax) - notice_lang(s_MemoServ, u, MEMO_INFO_HARD_LIMIT, - mi->memomax); + notice_lang(s_MemoServ, u, MEMO_INFO_NO_LIMIT); + + /* Ripped too. But differently because of a seg fault (loughs) */ + if ((u->na->nc->flags & NI_MEMO_RECEIVE) && (u->na->nc->flags & NI_MEMO_SIGNON)) + notice_lang(s_MemoServ, u, MEMO_INFO_NOTIFY_ON); + else if (u->na->nc->flags & NI_MEMO_RECEIVE) + notice_lang(s_MemoServ, u, MEMO_INFO_NOTIFY_RECEIVE); + else if (u->na->nc->flags & NI_MEMO_SIGNON) + notice_lang(s_MemoServ, u, MEMO_INFO_NOTIFY_SIGNON); else - notice_lang(s_MemoServ, u, MEMO_INFO_LIMIT, mi->memomax); - } else { - notice_lang(s_MemoServ, u, MEMO_INFO_NO_LIMIT); + notice_lang(s_MemoServ, u, MEMO_INFO_NOTIFY_OFF); } + return MOD_CONT; + } - /* Ripped too. But differently because of a seg fault (loughs) */ - if ((u->na->nc->flags & NI_MEMO_RECEIVE) - && (u->na->nc->flags & NI_MEMO_SIGNON)) { - notice_lang(s_MemoServ, u, MEMO_INFO_NOTIFY_ON); - } else if (u->na->nc->flags & NI_MEMO_RECEIVE) { - notice_lang(s_MemoServ, u, MEMO_INFO_NOTIFY_RECEIVE); - } else if (u->na->nc->flags & NI_MEMO_SIGNON) { - notice_lang(s_MemoServ, u, MEMO_INFO_NOTIFY_SIGNON); - } else { - notice_lang(s_MemoServ, u, MEMO_INFO_NOTIFY_OFF); - } + bool OnHelp(User *u, const std::string &subcommand) + { + if (is_services_admin(u)) + notice_lang(s_MemoServ, u, MEMO_SERVADMIN_HELP_INFO); + else + notice_lang(s_MemoServ, u, MEMO_HELP_INFO); + + return true; } - return MOD_CONT; /* if (name && (ci || na->nc != u->na->nc)) */ +}; + +class MSInfo : public Module +{ + public: + MSInfo(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(MEMOSERV, new CommandMSInfo(), MOD_UNIQUE); + this->SetMemoHelp(myMemoServHelp); + } +}; + +/** + * Add the help response to anopes /ms help output. + * @param u The user who is requesting help + **/ +void myMemoServHelp(User *u) +{ + notice_lang(s_MemoServ, u, MEMO_HELP_CMD_INFO); } MODULE_INIT("ms_info", MSInfo) diff --git a/src/core/ms_list.c b/src/core/ms_list.c index 881d9fe5c..1d02d4258 100644 --- a/src/core/ms_list.c +++ b/src/core/ms_list.c @@ -14,125 +14,150 @@ /*************************************************************************/ #include "module.h" -int do_list(User * u); -int list_memo_callback(User * u, int num, va_list args); -int list_memo(User * u, int index, MemoInfo * mi, int *sent_header, int newi, const char *chan); -void myMemoServHelp(User * u); + +int list_memo_callback(User *u, int num, va_list args); +int list_memo(User *u, int index, MemoInfo *mi, int *sent_header, int newi, const char *chan); +void myMemoServHelp(User *u); + +class CommandMSList : public Command +{ + public: + CommandMSList() : Command("LIST", 0, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *param = params.size() ? params[0].c_str() : NULL, *chan = NULL; + ChannelInfo *ci; + MemoInfo *mi; + Memo *m; + int i; + + if (param && *param == '#') + { + chan = param; + param = params.size() > 1 ? params[1].c)_str() : NULL; + if (!(ci = cs_findchan(chan))) + { + notice_lang(s_MemoServ, u, CHAN_X_NOT_REGISTERED, chan); + return MOD_CONT; + } + else if (ci->flags & CI_VERBOTEN) + { + notice_lang(s_MemoServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } + else if (!check_access(u, ci, CA_MEMO)) + { + notice_lang(s_MemoServ, u, ACCESS_DENIED); + return MOD_CONT; + } + mi = &ci->memos; + } + else + { + if (!nick_identified(u)) + { + notice_lang(s_MemoServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + return MOD_CONT; + } + mi = &u->na->nc->memos; + } + if (param && !isdigit(*param) && stricmp(param, "NEW")) + this->OnSyntaxError(u); + else if (!mi->memos.size()) + { + if (chan) + notice_lang(s_MemoServ, u, MEMO_X_HAS_NO_MEMOS, chan); + else + notice_lang(s_MemoServ, u, MEMO_HAVE_NO_MEMOS); + } + else + { + int sent_header = 0; + if (param && isdigit(*param)) + process_numlist(param, NULL, list_memo_callback, u, + mi, &sent_header, chan); + else + { + if (param) + { + for (i = 0; i < mi->memos.size(); ++i) + { + if (mi->memos[i]->flags & MF_UNREAD) + break; + } + if (i == mi->memos.size()) + { + if (chan) + notice_lang(s_MemoServ, u, MEMO_X_HAS_NO_NEW_MEMOS, chan); + else + notice_lang(s_MemoServ, u, MEMO_HAVE_NO_NEW_MEMOS); + return MOD_CONT; + } + } + for (i = 0; i < mi->memos.size(); ++i) + { + if (param && !(mi->memos[i]->flags & MF_UNREAD)) + continue; + list_memo(u, i, mi, &sent_header, param != NULL, chan); + } + } + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_MemoServ, u, MEMO_HELP_LIST); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_MemoServ, u, "LIST", MEMO_LIST_SYNTAX); + } +}; class MSList : public Module { public: MSList(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("LIST", do_list, NULL, MEMO_HELP_LIST, -1, -1, -1, -1); - this->AddCommand(MEMOSERV, c, MOD_UNIQUE); + this->AddCommand(MEMOSERV, new CommandMSList(), MOD_UNIQUE); this->SetMemoHelp(myMemoServHelp); } }; - - - /** * Add the help response to anopes /ms help output. * @param u The user who is requesting help **/ -void myMemoServHelp(User * u) +void myMemoServHelp(User *u) { notice_lang(s_MemoServ, u, MEMO_HELP_CMD_LIST); } /** - * List the memos (if any) for the source nick or given channel. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_list(User * u) -{ - char *param = strtok(NULL, " "), *chan = NULL; - ChannelInfo *ci; - MemoInfo *mi; - Memo *m; - int i; - - if (param && *param == '#') { - chan = param; - param = strtok(NULL, " "); - if (!(ci = cs_findchan(chan))) { - notice_lang(s_MemoServ, u, CHAN_X_NOT_REGISTERED, chan); - return MOD_CONT; - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_MemoServ, u, CHAN_X_FORBIDDEN, chan); - return MOD_CONT; - } else if (!check_access(u, ci, CA_MEMO)) { - notice_lang(s_MemoServ, u, ACCESS_DENIED); - return MOD_CONT; - } - mi = &ci->memos; - } else { - if (!nick_identified(u)) { - notice_lang(s_MemoServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); - return MOD_CONT; - } - mi = &u->na->nc->memos; - } - if (param && !isdigit(*param) && stricmp(param, "NEW") != 0) { - syntax_error(s_MemoServ, u, "LIST", MEMO_LIST_SYNTAX); - } else if (mi->memos.size() == 0) { - if (chan) - notice_lang(s_MemoServ, u, MEMO_X_HAS_NO_MEMOS, chan); - else - notice_lang(s_MemoServ, u, MEMO_HAVE_NO_MEMOS); - } else { - int sent_header = 0; - if (param && isdigit(*param)) { - process_numlist(param, NULL, list_memo_callback, u, - mi, &sent_header, chan); - } else { - if (param) { - for (i = 0; i < mi->memos.size(); i++) { - if (mi->memos[i]->flags & MF_UNREAD) - break; - } - if (i == mi->memos.size()) { - if (chan) - notice_lang(s_MemoServ, u, MEMO_X_HAS_NO_NEW_MEMOS, - chan); - else - notice_lang(s_MemoServ, u, MEMO_HAVE_NO_NEW_MEMOS); - return MOD_CONT; - } - } - for (i = 0; i < mi->memos.size(); i++) { - if (param && !(mi->memos[i]->flags & MF_UNREAD)) - continue; - list_memo(u, i, mi, &sent_header, param != NULL, chan); - } - } - } - return MOD_CONT; -} - -/** * list memno callback function * @param u User Struct * @param int Memo number * @param va_list List of arguements * @return result form list_memo() */ -int list_memo_callback(User * u, int num, va_list args) +int list_memo_callback(User *u, int num, va_list args) { MemoInfo *mi = va_arg(args, MemoInfo *); int *sent_header = va_arg(args, int *); const char *chan = va_arg(args, const char *); int i; - for (i = 0; i < mi->memos.size(); i++) { + for (i = 0; i < mi->memos.size(); ++i) + { if (mi->memos[i]->number == num) break; } @@ -150,7 +175,7 @@ int list_memo_callback(User * u, int num, va_list args) * @param chan Channel name * @return MOD_CONT */ -int list_memo(User * u, int index, MemoInfo * mi, int *sent_header, int newi, const char *chan) +int list_memo(User *u, int index, MemoInfo *mi, int *sent_header, int newi, const char *chan) { Memo *m; char timebuf[64]; @@ -158,27 +183,20 @@ int list_memo(User * u, int index, MemoInfo * mi, int *sent_header, int newi, co if (index < 0 || index >= mi->memos.size()) return 0; - if (!*sent_header) { - if (chan) { - notice_lang(s_MemoServ, u, - newi ? MEMO_LIST_CHAN_NEW_MEMOS : - MEMO_LIST_CHAN_MEMOS, chan, s_MemoServ, chan); - } else { - notice_lang(s_MemoServ, u, - newi ? MEMO_LIST_NEW_MEMOS : MEMO_LIST_MEMOS, - u->nick, s_MemoServ); - } + if (!*sent_header) + { + if (chan) + notice_lang(s_MemoServ, u, newi ? MEMO_LIST_CHAN_NEW_MEMOS : MEMO_LIST_CHAN_MEMOS, chan, s_MemoServ, chan); + else + notice_lang(s_MemoServ, u, newi ? MEMO_LIST_NEW_MEMOS : MEMO_LIST_MEMOS, u->nick, s_MemoServ); notice_lang(s_MemoServ, u, MEMO_LIST_HEADER); *sent_header = 1; } m = mi->memos[index]; tm = *localtime(&m->time); - strftime_lang(timebuf, sizeof(timebuf), - u, STRFTIME_DATE_TIME_FORMAT, &tm); + strftime_lang(timebuf, sizeof(timebuf), u, STRFTIME_DATE_TIME_FORMAT, &tm); timebuf[sizeof(timebuf) - 1] = 0; /* just in case */ - notice_lang(s_MemoServ, u, MEMO_LIST_FORMAT, - (m->flags & MF_UNREAD) ? '*' : ' ', - m->number, m->sender, timebuf); + notice_lang(s_MemoServ, u, MEMO_LIST_FORMAT, (m->flags & MF_UNREAD) ? '*' : ' ', m->number, m->sender, timebuf); return 1; } diff --git a/src/core/ms_read.c b/src/core/ms_read.c index 71d911f2f..27ed0931b 100644 --- a/src/core/ms_read.c +++ b/src/core/ms_read.c @@ -15,135 +15,155 @@ #include "module.h" -int do_read(User * u); -int read_memo_callback(User * u, int num, va_list args); -int read_memo(User * u, int index, MemoInfo * mi, const char *chan); -void myMemoServHelp(User * u); -extern void rsend_notify(User * u, Memo * m, const char *chan); +int read_memo_callback(User *u, int num, va_list args); +int read_memo(User *u, int index, MemoInfo *mi, const char *chan); +void myMemoServHelp(User *u); +extern void rsend_notify(User *u, Memo *m, const char *chan); +class CommandMSRead : public Command +{ + public: + CommandMSRead() : Command("READ", 0, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + MemoInfo *mi; + ChannelInfo *ci; + const char *numstr = params.size() ? params[0].c_str() : NULL, *chan = NULL; + int num, count; + + if (numstr && *numstr == '#') + { + chan = numstr; + numstr = params.size() > 1 ? params[1].c_str() : NULL; + if (!(ci = cs_findchan(chan))) + { + notice_lang(s_MemoServ, u, CHAN_X_NOT_REGISTERED, chan); + return MOD_CONT; + } + else if (ci->flags & CI_VERBOTEN) + { + notice_lang(s_MemoServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } + else if (!check_access(u, ci, CA_MEMO)) + { + notice_lang(s_MemoServ, u, ACCESS_DENIED); + return MOD_CONT; + } + mi = &ci->memos; + } + else + { + if (!nick_identified(u)) + { + notice_lang(s_MemoServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + return MOD_CONT; + } + mi = &u->na->nc->memos; + } + num = numstr ? atoi(numstr) : -1; + if (!numstr || (stricmp(numstr, "LAST") && stricmp(numstr, "NEW") && num <= 0)) + this->OnSyntaxError(u); + else if (mi->memos.empty()) + { + if (chan) + notice_lang(s_MemoServ, u, MEMO_X_HAS_NO_MEMOS, chan); + else + notice_lang(s_MemoServ, u, MEMO_HAVE_NO_MEMOS); + } + else { + int i; + + if (!stricmp(numstr, "NEW")) + { + int readcount = 0; + for (i = 0; i < mi->memos.size(); ++i) + { + if (mi->memos[i]->flags & MF_UNREAD) + { + read_memo(u, i, mi, chan); + ++readcount; + } + } + if (!readcount) + { + if (chan) + notice_lang(s_MemoServ, u, MEMO_X_HAS_NO_NEW_MEMOS, chan); + else + notice_lang(s_MemoServ, u, MEMO_HAVE_NO_NEW_MEMOS); + } + } + else if (!stricmp(numstr, "LAST")) + { + for (i = 0; i < mi->memos.size() - 1; ++i); + read_memo(u, i, mi, chan); + } + else /* number[s] */ + { + if (!process_numlist(numstr, &count, read_memo_callback, u, mi, chan)) + { + if (count == 1) + notice_lang(s_MemoServ, u, MEMO_DOES_NOT_EXIST, num); + else + notice_lang(s_MemoServ, u, MEMO_LIST_NOT_FOUND, numstr); + } + } + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_MemoServ, u, MEMO_HELP_READ); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_MemoServ, u, "READ", MEMO_READ_SYNTAX); + } +}; class MSRead : public Module { public: MSRead(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("READ", do_read, NULL, MEMO_HELP_READ, -1, -1, -1, -1); - this->AddCommand(MEMOSERV, c, MOD_UNIQUE); + this->AddCommand(MEMOSERV, new CommandMSRead(), MOD_UNIQUE); this->SetMemoHelp(myMemoServHelp); } }; - - /** * Add the help response to anopes /ms help output. * @param u The user who is requesting help **/ -void myMemoServHelp(User * u) +void myMemoServHelp(User *u) { notice_lang(s_MemoServ, u, MEMO_HELP_CMD_READ); } /** - * The /ms read command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_read(User * u) -{ - MemoInfo *mi; - ChannelInfo *ci; - char *numstr = strtok(NULL, " "), *chan = NULL; - int num, count; - - if (numstr && *numstr == '#') { - chan = numstr; - numstr = strtok(NULL, " "); - if (!(ci = cs_findchan(chan))) { - notice_lang(s_MemoServ, u, CHAN_X_NOT_REGISTERED, chan); - return MOD_CONT; - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_MemoServ, u, CHAN_X_FORBIDDEN, chan); - return MOD_CONT; - } else if (!check_access(u, ci, CA_MEMO)) { - notice_lang(s_MemoServ, u, ACCESS_DENIED); - return MOD_CONT; - } - mi = &ci->memos; - } else { - if (!nick_identified(u)) { - notice_lang(s_MemoServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); - return MOD_CONT; - } - mi = &u->na->nc->memos; - } - num = numstr ? atoi(numstr) : -1; - if (!numstr - || (stricmp(numstr, "LAST") != 0 && stricmp(numstr, "NEW") != 0 - && num <= 0)) { - syntax_error(s_MemoServ, u, "READ", MEMO_READ_SYNTAX); - - } else if (mi->memos.empty()) { - if (chan) - notice_lang(s_MemoServ, u, MEMO_X_HAS_NO_MEMOS, chan); - else - notice_lang(s_MemoServ, u, MEMO_HAVE_NO_MEMOS); - - } else { - int i; - - if (stricmp(numstr, "NEW") == 0) { - int readcount = 0; - for (i = 0; i < mi->memos.size(); i++) { - if (mi->memos[i]->flags & MF_UNREAD) { - read_memo(u, i, mi, chan); - readcount++; - } - } - if (!readcount) { - if (chan) - notice_lang(s_MemoServ, u, MEMO_X_HAS_NO_NEW_MEMOS, - chan); - else - notice_lang(s_MemoServ, u, MEMO_HAVE_NO_NEW_MEMOS); - } - } else if (stricmp(numstr, "LAST") == 0) { - for (i = 0; i < mi->memos.size() - 1; i++); - read_memo(u, i, mi, chan); - } else { /* number[s] */ - if (!process_numlist(numstr, &count, read_memo_callback, u, - mi, chan)) { - if (count == 1) - notice_lang(s_MemoServ, u, MEMO_DOES_NOT_EXIST, num); - else - notice_lang(s_MemoServ, u, MEMO_LIST_NOT_FOUND, - numstr); - } - } - - } - return MOD_CONT; -} - -/** * Read a memo callback function * @param u User Struct * @param int Index number * @param va_list variable arguements * @return result of read_memo() */ -int read_memo_callback(User * u, int num, va_list args) +int read_memo_callback(User *u, int num, va_list args) { MemoInfo *mi = va_arg(args, MemoInfo *); const char *chan = va_arg(args, const char *); int i; - for (i = 0; i < mi->memos.size(); i++) { + for (i = 0; i < mi->memos.size(); ++i) + { if (mi->memos[i]->number == num) break; } @@ -159,7 +179,7 @@ int read_memo_callback(User * u, int num, va_list args) * @param chan Channel Name * @return 1 on success, 0 if failed */ -int read_memo(User * u, int index, MemoInfo * mi, const char *chan) +int read_memo(User *u, int index, MemoInfo *mi, const char *chan) { Memo *m; char timebuf[64]; @@ -169,22 +189,18 @@ int read_memo(User * u, int index, MemoInfo * mi, const char *chan) return 0; m = mi->memos[index]; tm = *localtime(&m->time); - strftime_lang(timebuf, sizeof(timebuf), - u, STRFTIME_DATE_TIME_FORMAT, &tm); + strftime_lang(timebuf, sizeof(timebuf), u, STRFTIME_DATE_TIME_FORMAT, &tm); timebuf[sizeof(timebuf) - 1] = 0; if (chan) - notice_lang(s_MemoServ, u, MEMO_CHAN_HEADER, m->number, - m->sender, timebuf, s_MemoServ, chan, m->number); + notice_lang(s_MemoServ, u, MEMO_CHAN_HEADER, m->number, m->sender, timebuf, s_MemoServ, chan, m->number); else - notice_lang(s_MemoServ, u, MEMO_HEADER, m->number, - m->sender, timebuf, s_MemoServ, m->number); + notice_lang(s_MemoServ, u, MEMO_HEADER, m->number, m->sender, timebuf, s_MemoServ, m->number); notice_lang(s_MemoServ, u, MEMO_TEXT, m->text); m->flags &= ~MF_UNREAD; /* Check if a receipt notification was requested */ - if (m->flags & MF_RECEIPT) { + if (m->flags & MF_RECEIPT) rsend_notify(u, m, chan); - } return 1; } diff --git a/src/core/ms_rsend.c b/src/core/ms_rsend.c index 90f581f3e..120a9e0de 100644 --- a/src/core/ms_rsend.c +++ b/src/core/ms_rsend.c @@ -15,21 +15,83 @@ #include "module.h" -int do_rsend(User * u); -void myMemoServHelp(User * u); +void myMemoServHelp(User *u); + +class CommandMSRSend : public Command +{ + public: + CommandMSRSend() : Command("RSEND", 2, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *name = params[0].c_str(); + const char *text = params[1].c_str(); + NickAlias *na = NULL; + int z = 3; + + /* prevent user from rsend to themselves */ + if ((na = findnick(name))) + { + if (u->na) + { + if (!stricmp(na->nc->display, u->na->nc->display)) + { + notice_lang(s_MemoServ, u, MEMO_NO_RSEND_SELF); + return MOD_CONT; + } + } + else + { + notice_lang(s_MemoServ, u, NICK_X_NOT_REGISTERED, name); + return MOD_CONT; + } + } + + if (MSMemoReceipt == 1) + { + /* Services opers and above can use rsend */ + if (is_services_oper(u)) + memo_send(u, name, text, z); + else + notice_lang(s_MemoServ, u, ACCESS_DENIED); + } + else if (MSMemoReceipt == 2) + /* Everybody can use rsend */ + memo_send(u, name, text, z); + else + { + /* rsend has been disabled */ + if (debug) + alog("debug: MSMemoReceipt is set misconfigured to %d", MSMemoReceipt); + notice_lang(s_MemoServ, u, MEMO_RSEND_DISABLED); + } + + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_MemoServ, u, MEMO_HELP_RSEND); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_MemoServ, u, "RSEND", MEMO_RSEND_SYNTAX); + } +}; class MSRSend : public Module { public: MSRSend(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("RSEND", do_rsend, NULL, MEMO_HELP_RSEND, -1, -1, -1, -1); - this->AddCommand(MEMOSERV, c, MOD_UNIQUE); + this->AddCommand(MEMOSERV, new CommandMSRSend(), MOD_UNIQUE); this->SetMemoHelp(myMemoServHelp); if (!MSMemoReceipt) @@ -41,67 +103,10 @@ class MSRSend : public Module * Add the help response to anopes /ms help output. * @param u The user who is requesting help **/ -void myMemoServHelp(User * u) +void myMemoServHelp(User *u) { - if (((MSMemoReceipt == 1) && (is_services_oper(u))) - || (MSMemoReceipt == 2)) { + if ((MSMemoReceipt == 1 && is_services_oper(u)) || MSMemoReceipt == 2) notice_lang(s_MemoServ, u, MEMO_HELP_CMD_RSEND); - } -} - -/** - * The /ms rsend command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_rsend(User * u) -{ - char *name = strtok(NULL, " "); - char *text = strtok(NULL, ""); - NickAlias *na = NULL; - int z = 3; - - - - /* check if the variables are here */ - if (!name || !text) { - notice_lang(s_MemoServ, u, MEMO_RSEND_SYNTAX); - return MOD_CONT; - } - - /* prevent user from rsend to themselves */ - if ((na = findnick(name))) { - if (u->na) { - if (stricmp(na->nc->display, u->na->nc->display) == 0) { - notice_lang(s_MemoServ, u, MEMO_NO_RSEND_SELF); - return MOD_CONT; - } - } else { - notice_lang(s_MemoServ, u, NICK_X_NOT_REGISTERED, name); - return MOD_CONT; - } - } - - if (MSMemoReceipt == 1) { - /* Services opers and above can use rsend */ - if (is_services_oper(u)) { - memo_send(u, name, text, z); - } else { - notice_lang(s_MemoServ, u, ACCESS_DENIED); - } - } else if (MSMemoReceipt == 2) { - /* Everybody can use rsend */ - memo_send(u, name, text, z); - } else { - /* rsend has been disabled */ - if (debug) { - alog("debug: MSMemoReceipt is set misconfigured to %d", - MSMemoReceipt); - } - notice_lang(s_MemoServ, u, MEMO_RSEND_DISABLED); - } - - return MOD_CONT; } MODULE_INIT("ms_rsend", MSRSend) diff --git a/src/core/ms_send.c b/src/core/ms_send.c index 76e018943..ea91883ba 100644 --- a/src/core/ms_send.c +++ b/src/core/ms_send.c @@ -15,48 +15,56 @@ #include "module.h" -int do_send(User * u); -void myMemoServHelp(User * u); +void myMemoServHelp(User *u); + +class CommandMSSend : public Command +{ + public: + CommandMSSend() : Command("SEND", 2, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *name = params[0].c_str(); + const char *text = params[1].c_str(); + int z = 0; + memo_send(u, name, text, z); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_MemoServ, u, MEMO_HELP_SEND); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_MemoServ, u, "SEND", MEMO_SEND_SYNTAX); + } +}; class MSSend : public Module { public: MSSend(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("SEND", do_send, NULL, MEMO_HELP_SEND, -1, -1, -1, -1); - this->AddCommand(MEMOSERV, c, MOD_UNIQUE); + this->AddCommand(MEMOSERV, new CommandMSSend(), MOD_UNIQUE); this->SetMemoHelp(myMemoServHelp); } }; - - /** * Add the help response to anopes /ms help output. * @param u The user who is requesting help **/ -void myMemoServHelp(User * u) +void myMemoServHelp(User *u) { notice_lang(s_MemoServ, u, MEMO_HELP_CMD_SEND); } -/** - * The /ms send command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_send(User * u) -{ - char *name = strtok(NULL, " "); - char *text = strtok(NULL, ""); - int z = 0; - memo_send(u, name, text, z); - return MOD_CONT; -} - MODULE_INIT("ms_send", MSSend) diff --git a/src/core/ms_sendall.c b/src/core/ms_sendall.c index e19883b94..cee26e418 100644 --- a/src/core/ms_sendall.c +++ b/src/core/ms_sendall.c @@ -15,70 +15,81 @@ #include "module.h" -int do_sendall(User * u); -void myMemoServHelp(User * u); +void myMemoServHelp(User *u); + +class CommandMSSendAll : public Command +{ + public: + CommandMSSendAll() : Command("SENDALL", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + int i, z = 1; + NickCore *nc; + const char *text = params[0].c_str(); + + if (readonly) + { + notice_lang(s_MemoServ, u, MEMO_SEND_DISABLED); + return MOD_CONT; + } + else if (checkDefCon(DEFCON_NO_NEW_MEMOS)) + { + notice_lang(s_MemoServ, u, OPER_DEFCON_DENIED); + return MOD_CONT; + } + + for (i = 0; i < 1024; ++i) + { + for (nc = nclists[i]; nc; nc = nc->next) + { + if (stricmp(u->nick, nc->display)) + memo_send(u, nc->display, text, z); + } /* /nc */ + } /* /i */ + + notice_lang(s_MemoServ, u, MEMO_MASS_SENT); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_admin(u)) + return false; + + notice_lang(s_MemoServ, u, MEMO_HELP_SENDALL); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_MemoServ, u, "SENDALL", MEMO_SEND_SYNTAX); + } +}; class MSSendAll : public Module { public: MSSendAll(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("SENDALL", do_sendall, is_services_admin, -1, -1, -1, MEMO_HELP_SENDALL, MEMO_HELP_SENDALL); - this->AddCommand(MEMOSERV, c, MOD_UNIQUE); + this->AddCommand(MEMOSERV, new CommandMSSendAll(), MOD_UNIQUE); this->SetMemoHelp(myMemoServHelp); } }; - - /** * Add the help response to anopes /ms help output. * @param u The user who is requesting help **/ -void myMemoServHelp(User * u) +void myMemoServHelp(User *u) { - if (is_services_admin(u)) { + if (is_services_admin(u)) notice_lang(s_MemoServ, u, MEMO_HELP_CMD_SENDALL); - } -} - -/** - * The /ms sendall command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_sendall(User * u) -{ - int i, z = 1; - NickCore *nc; - char *text = strtok(NULL, ""); - - if (readonly) { - notice_lang(s_MemoServ, u, MEMO_SEND_DISABLED); - return MOD_CONT; - } else if (checkDefCon(DEFCON_NO_NEW_MEMOS)) { - notice_lang(s_MemoServ, u, OPER_DEFCON_DENIED); - return MOD_CONT; - } else if (!text) { - syntax_error(s_MemoServ, u, "SENDALL", MEMO_SEND_SYNTAX); - return MOD_CONT; - } - - - for (i = 0; i < 1024; i++) { - for (nc = nclists[i]; nc; nc = nc->next) { - if (stricmp(u->nick, nc->display) != 0) - memo_send(u, nc->display, text, z); - } /* /nc */ - } /* /i */ - - notice_lang(s_MemoServ, u, MEMO_MASS_SENT); - return MOD_CONT; } MODULE_INIT("ms_sendall", MSSendAll) diff --git a/src/core/ms_set.c b/src/core/ms_set.c index e48918127..ca12163de 100644 --- a/src/core/ms_set.c +++ b/src/core/ms_set.c @@ -15,238 +15,266 @@ #include "module.h" -int do_set(User * u); -int do_set_notify(User * u, MemoInfo * mi, char *param); -int do_set_limit(User * u, MemoInfo * mi, char *param); -void myMemoServHelp(User * u); +void myMemoServHelp(User *u); -class MSSet : public Module +class CommandMSSet : public Command { - public: - MSSet(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + CommandResult DoNotify(User *u, std::vector<std::string> ¶ms, MemoInfo &mi) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("SET", do_set, NULL, MEMO_HELP_SET, -1, -1, -1, -1); - this->AddCommand(MEMOSERV, c, MOD_UNIQUE); - - c = createCommand("SET NOTIFY", NULL, NULL, MEMO_HELP_SET_NOTIFY, -1, -1, -1, -1); - this->AddCommand(MEMOSERV, c, MOD_UNIQUE); - - c = createCommand("SET LIMIT", NULL, NULL, -1, MEMO_HELP_SET_LIMIT, MEMO_SERVADMIN_HELP_SET_LIMIT, MEMO_SERVADMIN_HELP_SET_LIMIT, MEMO_SERVADMIN_HELP_SET_LIMIT); - c->help_param1 = reinterpret_cast<char *>(static_cast<long>(MSMaxMemos)); - this->AddCommand(MEMOSERV, c, MOD_UNIQUE); - - this->SetMemoHelp(myMemoServHelp); - } -}; - - - -/** - * Add the help response to anopes /hs help output. - * @param u The user who is requesting help - **/ -void myMemoServHelp(User * u) -{ - notice_lang(s_MemoServ, u, MEMO_HELP_CMD_SET); -} + const char *params = params[1].c_str(); -/** - * The /ms set command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_set(User * u) -{ - char *cmd = strtok(NULL, " "); - char *param = strtok(NULL, ""); - MemoInfo *mi = &u->na->nc->memos; - - if (readonly) { - notice_lang(s_MemoServ, u, MEMO_SET_DISABLED); - return MOD_CONT; - } - if (!param) { - syntax_error(s_MemoServ, u, "SET", MEMO_SET_SYNTAX); - } else if (!nick_identified(u)) { - notice_lang(s_MemoServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + if (!stricmp(param, "ON")) + { + u->na->nc->flags |= NI_MEMO_SIGNON | NI_MEMO_RECEIVE; + notice_lang(s_MemoServ, u, MEMO_SET_NOTIFY_ON, s_MemoServ); + } + else if (!stricmp(param, "LOGON")) + { + u->na->nc->flags |= NI_MEMO_SIGNON; + u->na->nc->flags &= ~NI_MEMO_RECEIVE; + notice_lang(s_MemoServ, u, MEMO_SET_NOTIFY_LOGON, s_MemoServ); + } + else if (!stricmp(param, "NEW")) + { + u->na->nc->flags &= ~NI_MEMO_SIGNON; + u->na->nc->flags |= NI_MEMO_RECEIVE; + notice_lang(s_MemoServ, u, MEMO_SET_NOTIFY_NEW, s_MemoServ); + } + else if (!stricmp(param, "MAIL")) + { + if (u->na->nc->email) + { + u->na->nc->flags |= NI_MEMO_MAIL; + notice_lang(s_MemoServ, u, MEMO_SET_NOTIFY_MAIL); + } + else + notice_lang(s_MemoServ, u, MEMO_SET_NOTIFY_INVALIDMAIL); + } + else if (!stricmp(param, "NOMAIL")) + { + u->na->nc->flags &= ~NI_MEMO_MAIL; + notice_lang(s_MemoServ, u, MEMO_SET_NOTIFY_NOMAIL); + } + else if (!stricmp(param, "OFF")) + { + u->na->nc->flags &= ~(NI_MEMO_SIGNON | NI_MEMO_RECEIVE); + notice_lang(s_MemoServ, u, MEMO_SET_NOTIFY_OFF, s_MemoServ); + } + else + syntax_error(s_MemoServ, u, "SET NOTIFY", MEMO_SET_NOTIFY_SYNTAX); return MOD_CONT; - } else if (stricmp(cmd, "NOTIFY") == 0) { - do_set_notify(u, mi, param); - } else if (stricmp(cmd, "LIMIT") == 0) { - do_set_limit(u, mi, param); - } else { - notice_lang(s_MemoServ, u, MEMO_SET_UNKNOWN_OPTION, cmd); - notice_lang(s_MemoServ, u, MORE_INFO, s_MemoServ, "SET"); } - return MOD_CONT; -} -/** - * The /ms set notify command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_set_notify(User * u, MemoInfo * mi, char *param) -{ - if (stricmp(param, "ON") == 0) { - u->na->nc->flags |= NI_MEMO_SIGNON | NI_MEMO_RECEIVE; - notice_lang(s_MemoServ, u, MEMO_SET_NOTIFY_ON, s_MemoServ); - } else if (stricmp(param, "LOGON") == 0) { - u->na->nc->flags |= NI_MEMO_SIGNON; - u->na->nc->flags &= ~NI_MEMO_RECEIVE; - notice_lang(s_MemoServ, u, MEMO_SET_NOTIFY_LOGON, s_MemoServ); - } else if (stricmp(param, "NEW") == 0) { - u->na->nc->flags &= ~NI_MEMO_SIGNON; - u->na->nc->flags |= NI_MEMO_RECEIVE; - notice_lang(s_MemoServ, u, MEMO_SET_NOTIFY_NEW, s_MemoServ); - } else if (stricmp(param, "MAIL") == 0) { - if (u->na->nc->email) { - u->na->nc->flags |= NI_MEMO_MAIL; - notice_lang(s_MemoServ, u, MEMO_SET_NOTIFY_MAIL); - } else { - notice_lang(s_MemoServ, u, MEMO_SET_NOTIFY_INVALIDMAIL); - } - } else if (stricmp(param, "NOMAIL") == 0) { - u->na->nc->flags &= ~NI_MEMO_MAIL; - notice_lang(s_MemoServ, u, MEMO_SET_NOTIFY_NOMAIL); - } else if (stricmp(param, "OFF") == 0) { - u->na->nc->flags &= ~(NI_MEMO_SIGNON | NI_MEMO_RECEIVE); - notice_lang(s_MemoServ, u, MEMO_SET_NOTIFY_OFF, s_MemoServ); - } else { - syntax_error(s_MemoServ, u, "SET NOTIFY", MEMO_SET_NOTIFY_SYNTAX); - } - return MOD_CONT; -} + CommandResult DoLimit(User *u, std::vector<std::string> ¶ms) + { + const char *p1 = params[1].c_str(); + const char *p2 = params.size() > 2 ? params[2].c_str() : NULL; + const char *p3 = params.size() > 3 ? params[3].c_str() : NULL; + const char *user = NULL, *chan = NULL; + int32 limit; + NickAlias *na = u->na; + ChannelInfo *ci = NULL; + int is_servadmin = is_services_admin(u); -/** - * The /ms set limit command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_set_limit(User * u, MemoInfo * mi, char *param) -{ - char *p1 = strtok(param, " "); - char *p2 = strtok(NULL, " "); - char *p3 = strtok(NULL, " "); - char *user = NULL, *chan = NULL; - int32 limit; - NickAlias *na = u->na; - ChannelInfo *ci = NULL; - int is_servadmin = is_services_admin(u); - - if (p1 && *p1 == '#') { - chan = p1; - p1 = p2; - p2 = p3; - p3 = strtok(NULL, " "); - if (!(ci = cs_findchan(chan))) { - notice_lang(s_MemoServ, u, CHAN_X_NOT_REGISTERED, chan); - return MOD_CONT; - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_MemoServ, u, CHAN_X_FORBIDDEN, chan); - return MOD_CONT; - } else if (!is_servadmin && !check_access(u, ci, CA_MEMO)) { - notice_lang(s_MemoServ, u, ACCESS_DENIED); - return MOD_CONT; + if (*p1 == '#') + { + chan = p1; + p1 = p2; + p2 = p3; + p3 = params.size() > 4 ? params[4].c_str() : NULL; + if (!(ci = cs_findchan(chan))) + { + notice_lang(s_MemoServ, u, CHAN_X_NOT_REGISTERED, chan); + return MOD_CONT; + } + else if (ci->flags & CI_VERBOTEN) + { + notice_lang(s_MemoServ, u, CHAN_X_FORBIDDEN, chan); + return MOD_CONT; + } + else if (!is_servadmin && !check_access(u, ci, CA_MEMO)) + { + notice_lang(s_MemoServ, u, ACCESS_DENIED); + return MOD_CONT; + } + mi = &ci->memos; } - mi = &ci->memos; - } - if (is_servadmin) { - if (p2 && stricmp(p2, "HARD") != 0 && !chan) { - if (!(na = findnick(p1))) { - notice_lang(s_MemoServ, u, NICK_X_NOT_REGISTERED, p1); + if (is_servadmin) + { + if (p2 && stricmp(p2, "HARD") && !chan) + { + if (!(na = findnick(p1))) + { + notice_lang(s_MemoServ, u, NICK_X_NOT_REGISTERED, p1); + return MOD_CONT; + } + user = p1; + mi = &na->nc->memos; + p1 = p2; + p2 = p3; + } + else if (!p1) + { + syntax_error(s_MemoServ, u, "SET LIMIT", MEMO_SET_LIMIT_SERVADMIN_SYNTAX); return MOD_CONT; } - user = p1; - mi = &na->nc->memos; - p1 = p2; - p2 = p3; - } else if (!p1) { - syntax_error(s_MemoServ, u, "SET LIMIT", - MEMO_SET_LIMIT_SERVADMIN_SYNTAX); - return MOD_CONT; + if ((!isdigit(*p1) && stricmp(p1, "NONE")) || (p2 && stricmp(p2, "HARD"))) + { + syntax_error(s_MemoServ, u, "SET LIMIT", MEMO_SET_LIMIT_SERVADMIN_SYNTAX); + return MOD_CONT; + } + if (chan) + { + if (p2) + ci->flags |= CI_MEMO_HARDMAX; + else + ci->flags &= ~CI_MEMO_HARDMAX; + } + else + { + if (p2) + na->nc->flags |= NI_MEMO_HARDMAX; + else + na->nc->flags &= ~NI_MEMO_HARDMAX; + } + limit = atoi(p1); + if (limit < 0 || limit > 32767) + { + notice_lang(s_MemoServ, u, MEMO_SET_LIMIT_OVERFLOW, 32767); + limit = 32767; + } + if (stricmp(p1, "NONE") == 0) + limit = -1; } - if ((!isdigit(*p1) && stricmp(p1, "NONE") != 0) || - (p2 && stricmp(p2, "HARD") != 0)) { - syntax_error(s_MemoServ, u, "SET LIMIT", - MEMO_SET_LIMIT_SERVADMIN_SYNTAX); - return MOD_CONT; + else + { + if (!p1 || p2 || !isdigit(*p1)) { + syntax_error(s_MemoServ, u, "SET LIMIT", MEMO_SET_LIMIT_SYNTAX); + return MOD_CONT; + } + if (chan && (ci->flags & CI_MEMO_HARDMAX)) + { + notice_lang(s_MemoServ, u, MEMO_SET_LIMIT_FORBIDDEN, chan); + return MOD_CONT; + } + else if (!chan && (na->nc->flags & NI_MEMO_HARDMAX)) { + notice_lang(s_MemoServ, u, MEMO_SET_YOUR_LIMIT_FORBIDDEN); + return MOD_CONT; + } + limit = atoi(p1); + /* The first character is a digit, but we could still go negative + * from overflow... watch out! */ + if (limit < 0 || (MSMaxMemos > 0 && limit > MSMaxMemos)) + { + if (chan) + notice_lang(s_MemoServ, u, MEMO_SET_LIMIT_TOO_HIGH, chan, MSMaxMemos); + else + notice_lang(s_MemoServ, u, MEMO_SET_YOUR_LIMIT_TOO_HIGH, MSMaxMemos); + return MOD_CONT; + } + else if (limit > 32767) + { + notice_lang(s_MemoServ, u, MEMO_SET_LIMIT_OVERFLOW, 32767); + limit = 32767; + } } - if (chan) { - if (p2) - ci->flags |= CI_MEMO_HARDMAX; + mi->memomax = limit; + if (limit > 0) + { + if (!chan && na->nc == u->na->nc) + notice_lang(s_MemoServ, u, MEMO_SET_YOUR_LIMIT, limit); else - ci->flags &= ~CI_MEMO_HARDMAX; - } else { - if (p2) - na->nc->flags |= NI_MEMO_HARDMAX; + notice_lang(s_MemoServ, u, MEMO_SET_LIMIT, chan ? chan : user, limit); + } + else if (!limit) + { + if (!chan && na->nc == u->na->nc) + notice_lang(s_MemoServ, u, MEMO_SET_YOUR_LIMIT_ZERO); else - na->nc->flags &= ~NI_MEMO_HARDMAX; + notice_lang(s_MemoServ, u, MEMO_SET_LIMIT_ZERO, chan ? chan : user); } - limit = atoi(p1); - if (limit < 0 || limit > 32767) { - notice_lang(s_MemoServ, u, MEMO_SET_LIMIT_OVERFLOW, 32767); - limit = 32767; + else + { + if (!chan && na->nc == u->na->nc) + notice_lang(s_MemoServ, u, MEMO_UNSET_YOUR_LIMIT); + else + notice_lang(s_MemoServ, u, MEMO_UNSET_LIMIT, + chan ? chan : user); } - if (stricmp(p1, "NONE") == 0) - limit = -1; - } else { - if (!p1 || p2 || !isdigit(*p1)) { - syntax_error(s_MemoServ, u, "SET LIMIT", - MEMO_SET_LIMIT_SYNTAX); + return MOD_CONT; + } + public: + CommandMSSet() : Command("SET", 2, 5) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + MemoInfo *mi = &u->na->nc->memos; + + if (readonly) + { + notice_lang(s_MemoServ, u, MEMO_SET_DISABLED); return MOD_CONT; } - if (chan && (ci->flags & CI_MEMO_HARDMAX)) { - notice_lang(s_MemoServ, u, MEMO_SET_LIMIT_FORBIDDEN, chan); - return MOD_CONT; - } else if (!chan && (na->nc->flags & NI_MEMO_HARDMAX)) { - notice_lang(s_MemoServ, u, MEMO_SET_YOUR_LIMIT_FORBIDDEN); - return MOD_CONT; + if (!nick_identified(u)) + notice_lang(s_MemoServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + else if (!stricmp(cmd, "NOTIFY")) + return this->DoNotify(u, params, mi); + else if (!stricmp(cmd, "LIMIT")) { + return this->DoLimit(u, params, mi); } - limit = atoi(p1); - /* The first character is a digit, but we could still go negative - * from overflow... watch out! */ - if (limit < 0 || (MSMaxMemos > 0 && limit > MSMaxMemos)) { - if (chan) { - notice_lang(s_MemoServ, u, MEMO_SET_LIMIT_TOO_HIGH, - chan, MSMaxMemos); - } else { - notice_lang(s_MemoServ, u, MEMO_SET_YOUR_LIMIT_TOO_HIGH, - MSMaxMemos); - } - return MOD_CONT; - } else if (limit > 32767) { - notice_lang(s_MemoServ, u, MEMO_SET_LIMIT_OVERFLOW, 32767); - limit = 32767; + else + { + notice_lang(s_MemoServ, u, MEMO_SET_UNKNOWN_OPTION, cmd); + notice_lang(s_MemoServ, u, MORE_INFO, s_MemoServ, "SET"); } + return MOD_CONT; } - mi->memomax = limit; - if (limit > 0) { - if (!chan && na->nc == u->na->nc) - notice_lang(s_MemoServ, u, MEMO_SET_YOUR_LIMIT, limit); - else - notice_lang(s_MemoServ, u, MEMO_SET_LIMIT, - chan ? chan : user, limit); - } else if (limit == 0) { - if (!chan && na->nc == u->na->nc) - notice_lang(s_MemoServ, u, MEMO_SET_YOUR_LIMIT_ZERO); - else - notice_lang(s_MemoServ, u, MEMO_SET_LIMIT_ZERO, - chan ? chan : user); - } else { - if (!chan && na->nc == u->na->nc) - notice_lang(s_MemoServ, u, MEMO_UNSET_YOUR_LIMIT); - else - notice_lang(s_MemoServ, u, MEMO_UNSET_LIMIT, - chan ? chan : user); + + bool OnHelp(User *u, const std::string &subcommand) + { + // This needs to change XXX + notice_lang(s_MemoServ, u, MEMO_HELP_SET); + notice_lang(s_MemoServ, u, MEMO_HELP_SET_NOTIFY); + notice_lang(s_MemoServ, u, MEMO_HELP_SET_LIMIT, MSMaxMemos); + + if (is_services_oper(u)) + notice_lang(s_MemoServ, u, MEMO_SERVADMIN_HELP_SET_LIMIT, MSMaxMemos); + + return true; } - return MOD_CONT; + + void OnSyntaxError(User *u) + { + syntax_error(s_MemoServ, u, "SET", MEMO_SET_SYNTAX); + } +}; + +class MSSet : public Module +{ + public: + MSSet(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + + this->AddCommand(MEMOSERV, new CommandMSSet(), MOD_UNIQUE); + + this->SetMemoHelp(myMemoServHelp); + } +}; + +/** + * Add the help response to anopes /hs help output. + * @param u The user who is requesting help + **/ +void myMemoServHelp(User *u) +{ + notice_lang(s_MemoServ, u, MEMO_HELP_CMD_SET); } MODULE_INIT("ms_set", MSSet) diff --git a/src/core/ms_staff.c b/src/core/ms_staff.c index fbf7c03f5..2f6bf2d1f 100644 --- a/src/core/ms_staff.c +++ b/src/core/ms_staff.c @@ -15,67 +15,79 @@ #include "module.h" -int do_staff(User * u); -void myMemoServHelp(User * u); +void myMemoServHelp(User *u); + +class CommandMSStaff : public Command +{ + public: + CommandMSStaff() : Command("STAFF", 1, 1) + { + } + + CommandResult Execute(User *u, std::vecyor<std::string> ¶ms) + { + NickCore *nc; + int i, z = 0; + const char *text = params[0].c_str(); + + if (readonly) + { + notice_lang(s_MemoServ, u, MEMO_SEND_DISABLED); + return MOD_CONT; + } + else if (checkDefCon(DEFCON_NO_NEW_MEMOS)) + { + notice_lang(s_MemoServ, u, OPER_DEFCON_DENIED); + return MOD_CONT; + } + + for (i = 0; i < 1024; ++i) + { + for (nc = nclists[i]; nc; nc = nc->next) + { + if (nick_is_services_oper(nc)) + memo_send(u, nc->display, text, z); + } + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_oper(u)) + return false; + + notice_lang(s_MemoServ, u, MEMO_HELP_STAFF); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_MemoServ, u, "SEND", MEMO_SEND_SYNTAX); + } +}; class MSStaff : public Module { public: MSStaff(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("STAFF", do_staff, is_services_oper, -1, -1, MEMO_HELP_STAFF, MEMO_HELP_STAFF, MEMO_HELP_STAFF); - this->AddCommand(MEMOSERV, c, MOD_UNIQUE); + this->AddCommand(MEMOSERV, new CommandMSStaff(), MOD_UNIQUE); this->SetMemoHelp(myMemoServHelp); } }; - - /** * Add the help response to anopes /ms help output. * @param u The user who is requesting help **/ -void myMemoServHelp(User * u) +void myMemoServHelp(User *u) { - if (is_services_oper(u)) { + if (is_services_oper(u)) notice_lang(s_MemoServ, u, MEMO_HELP_CMD_STAFF); - } -} - -/** - * The /ms staff command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_staff(User * u) -{ - NickCore *nc; - int i, z = 0; - char *text = strtok(NULL, ""); - - if (readonly) { - notice_lang(s_MemoServ, u, MEMO_SEND_DISABLED); - return MOD_CONT; - } else if (checkDefCon(DEFCON_NO_NEW_MEMOS)) { - notice_lang(s_MemoServ, u, OPER_DEFCON_DENIED); - return MOD_CONT; - } else if (text == NULL) { - syntax_error(s_MemoServ, u, "SEND", MEMO_SEND_SYNTAX); - return MOD_CONT; - } - - for (i = 0; i < 1024; i++) { - for (nc = nclists[i]; nc; nc = nc->next) { - if (nick_is_services_oper(nc)) - memo_send(u, nc->display, text, z); - } - } - return MOD_CONT; } MODULE_INIT("ms_staff", MSStaff) diff --git a/src/core/ns_access.c b/src/core/ns_access.c index df888bd27..cbca3a989 100644 --- a/src/core/ns_access.c +++ b/src/core/ns_access.c @@ -15,164 +15,206 @@ #include "module.h" -int do_access(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); -class NSAccess : public Module +class CommandNSAccess : public Command { - public: - NSAccess(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + CommandResult DoServAdminList(User *u, std::vector<std::string> ¶ms) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("ACCESS", do_access, NULL, NICK_HELP_ACCESS, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - - this->SetNickHelp(myNickServHelp); - } -}; - - - -/** - * Add the help response to anopes /ns help output. - * @param u The user who is requesting help - **/ -void myNickServHelp(User * u) -{ - notice_lang(s_NickServ, u, NICK_HELP_CMD_ACCESS); -} - -/** - * The /ns access command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_access(User * u) -{ - char *cmd = strtok(NULL, " "); - char *mask = strtok(NULL, " "); - NickAlias *na; - int i; - char **access; - - if (cmd && stricmp(cmd, "LIST") == 0 && mask && is_services_admin(u) - && (na = findnick(mask))) { + const char *mask = params.size() > 2 ? params[2].c_str() : NULL; + char **access; + int i; - if (na->nc->accesscount == 0) { + if (!na->nc->accesscount) + { notice_lang(s_NickServ, u, NICK_ACCESS_LIST_X_EMPTY, na->nick); return MOD_CONT; } - if (na->status & NS_VERBOTEN) { + if (na->status & NS_VERBOTEN) + { notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); return MOD_CONT; } - if (na->nc->flags & NI_SUSPENDED) { + if (na->nc->flags & NI_SUSPENDED) + { notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); return MOD_CONT; } - - notice_lang(s_NickServ, u, NICK_ACCESS_LIST_X, mask); - mask = strtok(NULL, " "); - for (access = na->nc->access, i = 0; i < na->nc->accesscount; - access++, i++) { + notice_lang(s_NickServ, u, NICK_ACCESS_LIST_X, params[1].c_str()); + for (access = na->nc->access, i = 0; i < na->nc->accesscount; ++access, ++i) + { if (mask && !match_wild(mask, *access)) continue; - notice_user(s_NickServ, u, " %s", *access); + notice_user(s_NickServ, u, " %s", *access); } - } else if (!cmd || ((stricmp(cmd, "LIST") == 0) ? !!mask : !mask)) { - syntax_error(s_NickServ, u, "ACCESS", NICK_ACCESS_SYNTAX); - - } else if (mask && !strchr(mask, '@')) { - notice_lang(s_NickServ, u, BAD_USERHOST_MASK); - notice_lang(s_NickServ, u, MORE_INFO, s_NickServ, "ACCESS"); - - } else if (!(na = u->na)) { - notice_lang(s_NickServ, u, NICK_NOT_REGISTERED); - - } else if (na->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); + return MOD_CONT; + } - } else if (na->nc->flags & NI_SUSPENDED) { - notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); + CommandResult DoAdd(User *u, std::vector<std::string> ¶ms, const char *mask) + { + char **access; + int i; - } else if (!nick_identified(u)) { - notice_lang(s_NickServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + if (!mask) + { + this->OnSyntaxError(u); + return MOD_CONT; + } - } else if (stricmp(cmd, "ADD") == 0) { - if (na->nc->accesscount >= NSAccessMax) { - notice_lang(s_NickServ, u, NICK_ACCESS_REACHED_LIMIT, - NSAccessMax); + if (na->nc->accesscount >= NSAccessMax) + { + notice_lang(s_NickServ, u, NICK_ACCESS_REACHED_LIMIT, NSAccessMax); return MOD_CONT; } - for (access = na->nc->access, i = 0; i < na->nc->accesscount; - access++, i++) { - if (strcmp(*access, mask) == 0) { - notice_lang(s_NickServ, u, NICK_ACCESS_ALREADY_PRESENT, - *access); + for (access = na->nc->access, i = 0; i < na->nc->accesscount; ++access, ++i) + { + if (!strcmp(*access, mask)) + { + notice_lang(s_NickServ, u, NICK_ACCESS_ALREADY_PRESENT, *access); return MOD_CONT; } } - na->nc->accesscount++; - na->nc->access = - static_cast<char **>(srealloc(na->nc->access, sizeof(char *) * na->nc->accesscount)); + ++na->nc->accesscount; + na->nc->access = static_cast<char **>(srealloc(na->nc->access, sizeof(char *) * na->nc->accesscount)); na->nc->access[na->nc->accesscount - 1] = sstrdup(mask); notice_lang(s_NickServ, u, NICK_ACCESS_ADDED, mask); - } else if (stricmp(cmd, "DEL") == 0) { + return MOD_CONT; + } + + CommandResult DoDel(User *u, std::vector<std::string> ¶ms, const char *mask) + { + char **access; + int i; + + if (!mask) + { + this->OnSyntaxError(u); + return MOD_CONT; + } - for (access = na->nc->access, i = 0; i < na->nc->accesscount; - access++, i++) { - if (stricmp(*access, mask) == 0) + for (access = na->nc->access, i = 0; i < na->nc->accesscount; ++access, ++i) + { + if (!stricmp(*access, mask)) break; } - if (i == na->nc->accesscount) { + if (i == na->nc->accesscount) + { notice_lang(s_NickServ, u, NICK_ACCESS_NOT_FOUND, mask); return MOD_CONT; } notice_lang(s_NickServ, u, NICK_ACCESS_DELETED, *access); delete [] *access; - na->nc->accesscount--; - if (i < na->nc->accesscount) /* if it wasn't the last entry... */ - memmove(access, access + 1, - (na->nc->accesscount - i) * sizeof(char *)); - if (na->nc->accesscount) /* if there are any entries left... */ - na->nc->access = - static_cast<char **>(srealloc(na->nc->access, - na->nc->accesscount * sizeof(char *))); - else { + --na->nc->accesscount; + if (i < na->nc->accesscount) /* if it wasn't the last entry... */ + memmove(access, access + 1, (na->nc->accesscount - i) * sizeof(char *)); + if (na->nc->accesscount) /* if there are any entries left... */ + na->nc->access = static_cast<char **>(srealloc(na->nc->access, na->nc->accesscount * sizeof(char *))); + else + { free(na->nc->access); na->nc->access = NULL; } - } else if (stricmp(cmd, "LIST") == 0) { - if (na->nc->accesscount == 0) { + + return MOD_CONT; + } + + CommandResult DoList(User *u, std::vector<std::string> *params, const char *mask) + { + char **access; + int i; + + if (!na->nc->accesscount) + { notice_lang(s_NickServ, u, NICK_ACCESS_LIST_EMPTY, u->nick); return MOD_CONT; } notice_lang(s_NickServ, u, NICK_ACCESS_LIST); - for (access = na->nc->access, i = 0; i < na->nc->accesscount; - access++, i++) { + for (access = na->nc->access, i = 0; i < na->nc->accesscount; ++access, ++i) + { if (mask && !match_wild(mask, *access)) continue; - notice_user(s_NickServ, u, " %s", *access); + notice_user(s_NickServ, u, " %s", *access); } - } else { + + return MOD_CONT; + } + public: + CommandNSAccess() : Command("ACCESS", 1, 3) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + const char *mask = params.size() > 1 ? params[1].c_str() : NULL; + NickAlias *na; + + if (!stricmp(cmd, "LIST") && is_services_admin(u) && mask && (na = findnick(params[1].c_str()))) + return this->DoServAdminList(u, params, na); + + if (mask && !strchr(mask, '@')) + { + notice_lang(s_NickServ, u, BAD_USERHOST_MASK); + notice_lang(s_NickServ, u, MORE_INFO, s_NickServ, "ACCESS"); + + } + else if (!(na = u->na)) + notice_lang(s_NickServ, u, NICK_NOT_REGISTERED); + else if (na->status & NS_VERBOTEN) + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); + else if (na->nc->flags & NI_SUSPENDED) + notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); + else if (!nick_identified(u)) + notice_lang(s_NickServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + else if (!stricmp(cmd, "ADD")) + return this->DoAdd(u, params, mask); + else if (!stricmp(cmd, "DEL")) + return this->DoDel(u, params, mask); + else if (!stricmp(cmd, "LIST")) + return thus->DoList(u, params, mask); + else + this->OnSyntaxError(u); + return MOD_CONT; + } + + void OnSyntaxError(User *u) + { syntax_error(s_NickServ, u, "ACCESS", NICK_ACCESS_SYNTAX); + } +}; + +class NSAccess : public Module +{ + public: + NSAccess(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(NICKSERV, new CommandNSAccess(), MOD_UNIQUE); + + this->SetNickHelp(myNickServHelp); } - return MOD_CONT; +}; + +/** + * Add the help response to anopes /ns help output. + * @param u The user who is requesting help + **/ +void myNickServHelp(User *u) +{ + notice_lang(s_NickServ, u, NICK_HELP_CMD_ACCESS); } MODULE_INIT("ns_access", NSAccess) diff --git a/src/core/ns_alist.c b/src/core/ns_alist.c index c84cd373d..c2e59a978 100644 --- a/src/core/ns_alist.c +++ b/src/core/ns_alist.c @@ -15,160 +15,154 @@ #include "module.h" -int do_alist(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); -class NSAList : public Module +class CommandNSAList : public Command { public: - NSAList(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandNSAList() : Command("ALIST", 0, 2) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("ALIST", do_alist, NULL, -1, NICK_HELP_ALIST, -1, NICK_SERVADMIN_HELP_ALIST, NICK_SERVADMIN_HELP_ALIST); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - - this->SetNickHelp(myNickServHelp); } -}; - - -/** - * Add the help response to anopes /ns help output. - * @param u The user who is requesting help - **/ -void myNickServHelp(User * u) -{ - notice_lang(s_NickServ, u, NICK_HELP_CMD_ALIST); -} - -/** - * The /ns alist command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_alist(User * u) -{ - -/* - * List the channels that the given nickname has access on - * - * /ns ALIST [level] - * /ns ALIST [nickname] [level] - * - * -jester - */ - - char *nick = NULL; - char *lev = NULL; + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + /* + * List the channels that the given nickname has access on + * + * /ns ALIST [level] + * /ns ALIST [nickname] [level] + * + * -jester + */ - NickAlias *na; + const char *nick = NULL; + const char *lev = NULL; - int min_level = 0; - int is_servadmin = is_services_admin(u); + NickAlias *na; - if (!is_servadmin) { - /* Non service admins can only see their own levels */ - na = u->na; - } else { - /* Services admins can request ALIST on nicks. - * The first argument for service admins must - * always be a nickname. - */ - nick = strtok(NULL, " "); + int min_level = 0; + int is_servadmin = is_services_admin(u); + int lev_param = 0; - /* If an argument was passed, use it as the nick to see levels - * for, else check levels for the user calling the command */ - if (nick) { - na = findnick(nick); - } else { + if (!is_servadmin) + /* Non service admins can only see their own levels */ na = u->na; + else + { + /* Services admins can request ALIST on nicks. + * The first argument for service admins must + * always be a nickname. + */ + nick = params.size() ? params[0].c_str() : NULL; + lev_param = 1; + + /* If an argument was passed, use it as the nick to see levels + * for, else check levels for the user calling the command */ + if (nick) + na = findnick(nick); + else + na = u->na; } - } - /* If available, get level from arguments */ - lev = strtok(NULL, " "); - - /* if a level was given, make sure it's an int for later */ - if (lev) { - if (stricmp(lev, "FOUNDER") == 0) { - min_level = ACCESS_FOUNDER; - } else if (stricmp(lev, "SOP") == 0) { - min_level = ACCESS_SOP; - } else if (stricmp(lev, "AOP") == 0) { - min_level = ACCESS_AOP; - } else if (stricmp(lev, "HOP") == 0) { - min_level = ACCESS_HOP; - } else if (stricmp(lev, "VOP") == 0) { - min_level = ACCESS_VOP; - } else { - min_level = atoi(lev); + /* If available, get level from arguments */ + lev = params.size() > lev_param ? params[lev_param].c_str() : NULL; + + /* if a level was given, make sure it's an int for later */ + if (lev) { + if (!stricmp(lev, "FOUNDER")) + min_level = ACCESS_FOUNDER; + else if (!stricmp(lev, "SOP")) + min_level = ACCESS_SOP; + else if (!stricmp(lev, "AOP")) + min_level = ACCESS_AOP; + else if (!stricmp(lev, "HOP")) + min_level = ACCESS_HOP; + else if (!stricmp(lev, "VOP")) + min_level = ACCESS_VOP; + else + min_level = atoi(lev); } - } - if (!nick_identified(u)) { - notice_lang(s_NickServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); - } else if (is_servadmin && nick && !na) { - notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); - } else if (na->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); - } else if (min_level <= ACCESS_INVALID || min_level > ACCESS_FOUNDER) { - notice_lang(s_NickServ, u, CHAN_ACCESS_LEVEL_RANGE, - ACCESS_INVALID + 1, ACCESS_FOUNDER - 1); - } else { - int i, level; - int chan_count = 0; - int match_count = 0; - ChannelInfo *ci; - - notice_lang(s_NickServ, u, (is_servadmin ? NICK_ALIST_HEADER_X : - NICK_ALIST_HEADER), na->nick); - - for (i = 0; i < 256; i++) { - for ((ci = chanlists[i]); ci; (ci = ci->next)) { - - if ((level = get_access_level(ci, na))) { - chan_count++; - - if (min_level > level) { - continue; + if (!nick_identified(u)) + notice_lang(s_NickServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + else if (is_servadmin && nick && !na) + notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + else if (na->status & NS_VERBOTEN) + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); + else if (min_level <= ACCESS_INVALID || min_level > ACCESS_FOUNDER) + notice_lang(s_NickServ, u, CHAN_ACCESS_LEVEL_RANGE, ACCESS_INVALID + 1, ACCESS_FOUNDER - 1); + else + { + int i, level; + int chan_count = 0; + int match_count = 0; + ChannelInfo *ci; + + notice_lang(s_NickServ, u, is_servadmin ? NICK_ALIST_HEADER_X : NICK_ALIST_HEADER, na->nick); + + for (i = 0; i < 256; ++i) + { + for (ci = chanlists[i]; ci; ci = ci->next) + { + if ((level = get_access_level(ci, na))) + { + ++chan_count; + + if (min_level > level) + continue; + + ++match_count; + + if ((ci->flags & CI_XOP) || level == ACCESS_FOUNDER) + { + const char *xop; + + xop = get_xop_level(level); + + notice_lang(s_NickServ, u, NICK_ALIST_XOP_FORMAT, match_count, ci->flags & CI_NO_EXPIRE ? '!' : ' ', ci->name, xop, ci->desc ? ci->desc : ""); + } + else + notice_lang(s_NickServ, u, NICK_ALIST_ACCESS_FORMAT, match_count, ci->flags & CI_NO_EXPIRE ? '!' : ' ', ci->name, level, ci->desc ? ci->desc : ""); } + } + } - match_count++; - - if ((ci->flags & CI_XOP) || (level == ACCESS_FOUNDER)) { - const char *xop; + notice_lang(s_NickServ, u, NICK_ALIST_FOOTER, match_count, chan_count); + } + return MOD_CONT; + } - xop = get_xop_level(level); + bool OnHelp(User *u, const std::string &subcommand) + { + if (is_services_admin(u)) + notice_lang(s_NickServ, u, NICK_SERVADMIN_HELP_ALIST); + else + notice_lang(s_NickServ, u, NICK_HELP_ALIST); + } +}; - notice_lang(s_NickServ, u, NICK_ALIST_XOP_FORMAT, - match_count, - ((ci-> - flags & CI_NO_EXPIRE) ? '!' : ' '), - ci->name, xop, - (ci->desc ? ci->desc : "")); - } else { - notice_lang(s_NickServ, u, - NICK_ALIST_ACCESS_FORMAT, match_count, - ((ci-> - flags & CI_NO_EXPIRE) ? '!' : ' '), - ci->name, level, - (ci->desc ? ci->desc : "")); +class NSAList : public Module +{ + public: + NSAList(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); - } - } - } - } + this->AddCommand(NICKSERV, new CommandNSAList(), MOD_UNIQUE); - notice_lang(s_NickServ, u, NICK_ALIST_FOOTER, match_count, - chan_count); + this->SetNickHelp(myNickServHelp); } - return MOD_CONT; +}; + +/** + * Add the help response to anopes /ns help output. + * @param u The user who is requesting help + **/ +void myNickServHelp(User *u) +{ + notice_lang(s_NickServ, u, NICK_HELP_CMD_ALIST); } MODULE_INIT("ns_alist", NSAList) diff --git a/src/core/ns_drop.c b/src/core/ns_drop.c index 1f4ba3e2d..460a9fb93 100644 --- a/src/core/ns_drop.c +++ b/src/core/ns_drop.c @@ -15,130 +15,126 @@ #include "module.h" -int do_drop(User * u); -int do_unlink(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); + +class CommandNSDrop : public Command +{ + public: + CommandNSDrop() : Command("DROP", 0, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params.size() ? params[0].c_str() : NULL; + NickAlias *na; + NickRequest *nr = NULL; + int is_servadmin = is_services_admin(u); + int is_mine; /* Does the nick being dropped belong to the user that is dropping? */ + char *my_nick = NULL; + + if (readonly && !is_servadmin) + { + notice_lang(s_NickServ, u, NICK_DROP_DISABLED); + return MOD_CONT; + } + + if (!(na = (nick ? findnick(nick) : u->na))) + { + if (nick) + { + if ((nr = findrequestnick(nick)) && is_servadmin) + { + if (readonly) + notice_lang(s_NickServ, u, READ_ONLY_MODE); + if (WallDrop) + ircdproto->SendGlobops(s_NickServ, "\2%s\2 used DROP on \2%s\2", u->nick, nick); + alog("%s: %s!%s@%s dropped nickname %s (e-mail: %s)", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, nr->nick, nr->email); + delnickrequest(nr); + notice_lang(s_NickServ, u, NICK_X_DROPPED, nick); + } + else + notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + } + else + notice_lang(s_NickServ, u, NICK_NOT_REGISTERED); + return MOD_CONT; + } + + is_mine = u->na && u->na->nc == na->nc; + if (is_mine && !nick) + my_nick = sstrdup(na->nick); + + if (is_mine && !nick_identified(u)) + notice_lang(s_NickServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + else if (!is_mine && !is_servadmin) + notice_lang(s_NickServ, u, ACCESS_DENIED); + else if (NSSecureAdmins && !is_mine && nick_is_services_admin(na->nc) && !is_services_root(u)) + notice_lang(s_NickServ, u, PERMISSION_DENIED); + else + { + if (readonly) + notice_lang(s_NickServ, u, READ_ONLY_MODE); + + if (ircd->sqline && (na->status & NS_VERBOTEN)) + ircdproto->SendSQLineDel(na->nick); + + alog("%s: %s!%s@%s dropped nickname %s (group %s) (e-mail: %s)", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, na->nick, na->nc->display, na->nc->email ? na->nc->email : "none"); + delnick(na); + send_event(EVENT_NICK_DROPPED, 1, my_nick ? my_nick : nick); + + if (!is_mine) + { + if (WallDrop) + ircdproto->SendGlobops(s_NickServ, "\2%s\2 used DROP on \2%s\2", u->nick, nick); + notice_lang(s_NickServ, u, NICK_X_DROPPED, nick); + } + else + { + if (nick) + notice_lang(s_NickServ, u, NICK_X_DROPPED, nick); + else + notice_lang(s_NickServ, u, NICK_DROPPED); + if (my_nick) + delete [] my_nick; + } + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (is_services_admin(u)) + notice_lang(s_NickServ, u, NICK_SERVADMIN_HELP_DROP); + else + notice_lang(s_NickServ, u, NICK_HELP_DROP); + + return true; + } +}; class NSDrop : public Module { public: NSDrop(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("DROP", do_drop, NULL, -1, NICK_HELP_DROP, -1, NICK_SERVADMIN_HELP_DROP, NICK_SERVADMIN_HELP_DROP); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("UNLINK", do_unlink, NULL, -1, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + this->AddCommand(NICKSERV, new CommandNSDrop(), MOD_UNIQUE); this->SetNickHelp(myNickServHelp); } }; - /** * Add the help response to anopes /ns help output. * @param u The user who is requesting help **/ -void myNickServHelp(User * u) +void myNickServHelp(User *u) { notice_lang(s_NickServ, u, NICK_HELP_CMD_DROP); } -/** - * The /ns drop command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_drop(User * u) -{ - char *nick = strtok(NULL, " "); - NickAlias *na; - NickRequest *nr = NULL; - int is_servadmin = is_services_admin(u); - int is_mine; /* Does the nick being dropped belong to the user that is dropping? */ - char *my_nick = NULL; - - if (readonly && !is_servadmin) { - notice_lang(s_NickServ, u, NICK_DROP_DISABLED); - return MOD_CONT; - } - - if (!(na = (nick ? findnick(nick) : u->na))) { - if (nick) { - if ((nr = findrequestnick(nick)) && is_servadmin) { - if (readonly) - notice_lang(s_NickServ, u, READ_ONLY_MODE); - if (WallDrop) - ircdproto->SendGlobops(s_NickServ, - "\2%s\2 used DROP on \2%s\2", u->nick, - nick); - alog("%s: %s!%s@%s dropped nickname %s (e-mail: %s)", - s_NickServ, u->nick, u->username, u->host, - nr->nick, nr->email); - delnickrequest(nr); - notice_lang(s_NickServ, u, NICK_X_DROPPED, nick); - } else { - notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); - } - } else - notice_lang(s_NickServ, u, NICK_NOT_REGISTERED); - return MOD_CONT; - } - - is_mine = (u->na && (u->na->nc == na->nc)); - if (is_mine && !nick) - my_nick = sstrdup(na->nick); - - if (is_mine && !nick_identified(u)) { - notice_lang(s_NickServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); - } else if (!is_mine && !is_servadmin) { - notice_lang(s_NickServ, u, ACCESS_DENIED); - } else if (NSSecureAdmins && !is_mine && nick_is_services_admin(na->nc) - && !is_services_root(u)) { - notice_lang(s_NickServ, u, PERMISSION_DENIED); - } else { - if (readonly) - notice_lang(s_NickServ, u, READ_ONLY_MODE); - - if (ircd->sqline && (na->status & NS_VERBOTEN)) { - ircdproto->SendSQLineDel(na->nick); - } - - alog("%s: %s!%s@%s dropped nickname %s (group %s) (e-mail: %s)", - s_NickServ, u->nick, u->username, u->host, - na->nick, na->nc->display, - (na->nc->email ? na->nc->email : "none")); - delnick(na); - send_event(EVENT_NICK_DROPPED, 1, (my_nick ? my_nick : nick)); - - if (!is_mine) { - if (WallDrop) - ircdproto->SendGlobops(s_NickServ, "\2%s\2 used DROP on \2%s\2", - u->nick, nick); - notice_lang(s_NickServ, u, NICK_X_DROPPED, nick); - } else { - if (nick) - notice_lang(s_NickServ, u, NICK_X_DROPPED, nick); - else - notice_lang(s_NickServ, u, NICK_DROPPED); - if (my_nick) { - delete [] my_nick; - } - } - } - return MOD_CONT; -} - - -int do_unlink(User * u) -{ - notice_lang(s_NickServ, u, OBSOLETE_COMMAND, "DROP"); - return MOD_CONT; -} - MODULE_INIT("ns_drop", NSDrop) diff --git a/src/core/ns_forbid.c b/src/core/ns_forbid.c index 0a39dd1d0..9abe8fe81 100644 --- a/src/core/ns_forbid.c +++ b/src/core/ns_forbid.c @@ -15,108 +15,119 @@ #include "module.h" -int do_forbid(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); NickAlias *makenick(const char *nick); +class CommandNSForbid : public Command +{ + public: + CommandNSForbid() : Command("FORBID", 1, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + NickAlias *na; + const char *nick = params[0].c_str(); + const char *reason = params.size() > 1 ? params[1].c_str(); + + /* Assumes that permission checking has already been done. */ + if (ForceForbidReason && !reason) { + this->OnSyntaxError(u); + return MOD_CONT; + } + + if (readonly) + notice_lang(s_NickServ, u, READ_ONLY_MODE); + if (!ircdproto->IsNickValid(nick)) + { + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, nick); + return MOD_CONT; + } + if ((na = findnick(nick))) + { + if (NSSecureAdmins && nick_is_services_admin(na->nc) && !is_services_root(u)) + { + notice_lang(s_NickServ, u, PERMISSION_DENIED); + return MOD_CONT; + } + delnick(na); + } + na = makenick(nick); + if (na) + { + na->status |= NS_VERBOTEN; + na->last_usermask = sstrdup(u->nick); + if (reason) + na->last_realname = sstrdup(reason); + + na->u = finduser(na->nick); + if (na->u) + na->u->na = na; + + if (na->u) + { + notice_lang(s_NickServ, na->u, FORCENICKCHANGE_NOW); + collide(na, 0); + } + + + if (ircd->sqline) + ircdproto->SendSQLine(na->nick, reason ? reason : "Forbidden"); + + if (WallForbid) + ircdproto->SendGlobops(s_NickServ, "\2%s\2 used FORBID on \2%s\2", u->nick, nick); + + alog("%s: %s set FORBID for nick %s", s_NickServ, u->nick, nick); + notice_lang(s_NickServ, u, NICK_FORBID_SUCCEEDED, nick); + send_event(EVENT_NICK_FORBIDDEN, 1, nick); + } + else + { + alog("%s: Valid FORBID for %s by %s failed", s_NickServ, nick, u->nick); + notice_lang(s_NickServ, u, NICK_FORBID_FAILED, nick); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_admin(u)) + return false; + + notice_lang(s_NickServ, u, NICK_SERVADMIN_HELP_FORBID); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "FORBID", ForceForbidReason ? NICK_FORBID_SYNTAX_REASON : NICK_FORBID_SYNTAX); + } +}; + class NSForbid : public Module { public: NSForbid(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("FORBID", do_forbid, is_services_admin, -1, -1, -1, NICK_SERVADMIN_HELP_FORBID, NICK_SERVADMIN_HELP_FORBID); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + this->AddCommand(NICKSERV, new CommandNSForbid(), MOD_UNIQUE); this->SetNickHelp(myNickServHelp); } }; - - /** * Add the help response to anopes /ns help output. * @param u The user who is requesting help **/ -void myNickServHelp(User * u) +void myNickServHelp(User *u) { - if (is_services_admin(u)) { + if (is_services_admin(u)) notice_lang(s_NickServ, u, NICK_HELP_CMD_FORBID); - } -} - -/** - * The /ns forbid command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_forbid(User * u) -{ - NickAlias *na; - char *nick = strtok(NULL, " "); - char *reason = strtok(NULL, ""); - - /* Assumes that permission checking has already been done. */ - if (!nick || (ForceForbidReason && !reason)) { - syntax_error(s_NickServ, u, "FORBID", - (ForceForbidReason ? NICK_FORBID_SYNTAX_REASON : - NICK_FORBID_SYNTAX)); - return MOD_CONT; - } - - if (readonly) - notice_lang(s_NickServ, u, READ_ONLY_MODE); - if (!ircdproto->IsNickValid(nick)) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, nick); - return MOD_CONT; - } - if ((na = findnick(nick)) != NULL) { - if (NSSecureAdmins && nick_is_services_admin(na->nc) - && !is_services_root(u)) { - notice_lang(s_NickServ, u, PERMISSION_DENIED); - return MOD_CONT; - } - delnick(na); - } - na = makenick(nick); - if (na) { - na->status |= NS_VERBOTEN; - na->last_usermask = sstrdup(u->nick); - if (reason) - na->last_realname = sstrdup(reason); - - na->u = finduser(na->nick); - if (na->u) - na->u->na = na; - - if (na->u) { - notice_lang(s_NickServ, na->u, FORCENICKCHANGE_NOW); - collide(na, 0); - } - - - if (ircd->sqline) { - ircdproto->SendSQLine(na->nick, ((reason) ? reason : "Forbidden")); - } - - if (WallForbid) - ircdproto->SendGlobops(s_NickServ, "\2%s\2 used FORBID on \2%s\2", - u->nick, nick); - - alog("%s: %s set FORBID for nick %s", s_NickServ, u->nick, nick); - notice_lang(s_NickServ, u, NICK_FORBID_SUCCEEDED, nick); - send_event(EVENT_NICK_FORBIDDEN, 1, nick); - } else { - alog("%s: Valid FORBID for %s by %s failed", s_NickServ, nick, - u->nick); - notice_lang(s_NickServ, u, NICK_FORBID_FAILED, nick); - } - return MOD_CONT; } NickAlias *makenick(const char *nick) diff --git a/src/core/ns_getemail.c b/src/core/ns_getemail.c index 54eebd38b..ee2e9e16f 100644 --- a/src/core/ns_getemail.c +++ b/src/core/ns_getemail.c @@ -20,22 +20,69 @@ #include "module.h" -int do_getemail(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); + +class CommandNSGetEMail : public Command +{ + public: + CommandNSGetEMail() : Command("GETEMAIL", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *email = params[0].c_str(); + int i, j = 0; + NickCore *nc; + + alog("%s: %s!%s@%s used GETEMAIL on %s", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, email); + for (i = 0; i < 1024; ++i) + { + for (nc = nclists[i]; nc; nc = nc->next) + { + if (nc->email) + { + if (!stricmp(nc->email, email)) + { + ++j; + notice_lang(s_NickServ, u, NICK_GETEMAIL_EMAILS_ARE, nc->display, email); + } + } + } + } + if (j <= 0) + { + notice_lang(s_NickServ, u, NICK_GETEMAIL_NOT_USED, email); + return MOD_CONT; + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_admin(u)) + return false; + + notice_lang(s_NickServ, u, NICK_SERVADMIN_HELP_GETEMAIL); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "GETMAIL", NICK_GETEMAIL_SYNTAX); + } +}; class NSGetEMail : public Module { public: NSGetEMail(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("GETEMAIL", do_getemail, is_services_admin, -1, -1, -1, NICK_SERVADMIN_HELP_GETEMAIL, NICK_SERVADMIN_HELP_GETEMAIL); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + this->AddCommand(NICKSERV, new CommandNSGetEMail(), MOD_UNIQUE); this->SetNickHelp(myNickServHelp); } @@ -45,46 +92,10 @@ class NSGetEMail : public Module * Add the help response to anopes /ns help output. * @param u The user who is requesting help **/ -void myNickServHelp(User * u) +void myNickServHelp(User *u) { - if (is_services_admin(u)) { + if (is_services_admin(u)) notice_lang(s_NickServ, u, NICK_HELP_CMD_GETEMAIL); - } -} - -/** - * The /ns getemail command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_getemail(User * u) -{ - char *email = strtok(NULL, " "); - int i, j = 0; - NickCore *nc; - - if (!email) { - syntax_error(s_NickServ, u, "GETMAIL", NICK_GETEMAIL_SYNTAX); - return MOD_CONT; - } - alog("%s: %s!%s@%s used GETEMAIL on %s", s_NickServ, u->nick, - u->username, u->host, email); - for (i = 0; i < 1024; i++) { - for (nc = nclists[i]; nc; nc = nc->next) { - if (nc->email) { - if (stricmp(nc->email, email) == 0) { - j++; - notice_lang(s_NickServ, u, NICK_GETEMAIL_EMAILS_ARE, - nc->display, email); - } - } - } - } - if (j <= 0) { - notice_lang(s_NickServ, u, NICK_GETEMAIL_NOT_USED, email); - return MOD_CONT; - } - return MOD_CONT; } MODULE_INIT("ns_getemail", NSGetEMail) diff --git a/src/core/ns_getpass.c b/src/core/ns_getpass.c index dde17ca17..381d8b36f 100644 --- a/src/core/ns_getpass.c +++ b/src/core/ns_getpass.c @@ -15,22 +15,80 @@ #include "module.h" -int do_getpass(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); + +class CommandNSGetPass : public Command +{ + public: + CommandNSGetPass() : Command("GETPASS", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[0].c_str(); + char tmp_pass[PASSMAX]; + NickAlias *na; + NickRequest *nr = NULL; + + if (!(na = findnick(nick))) + { + if ((nr = findrequestnick(nick))) + { + alog("%s: %s!%s@%s used GETPASS on %s", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, nick); + if (WallGetpass) + ircdproto->SendGlobops(s_NickServ, "\2%s\2 used GETPASS on \2%s\2", u->nick, nick); + notice_lang(s_NickServ, u, NICK_GETPASS_PASSCODE_IS, nick, nr->passcode); + } + else + notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + } + else if (na->status & NS_VERBOTEN) + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); + else if (NSSecureAdmins && nick_is_services_admin(na->nc) && !is_services_root(u)) + notice_lang(s_NickServ, u, PERMISSION_DENIED); + else if (NSRestrictGetPass && !is_services_root(u)) + notice_lang(s_NickServ, u, PERMISSION_DENIED); + else + { + if (enc_decrypt(na->nc->pass, tmp_pass, PASSMAX - 1) == 1) + { + alog("%s: %s!%s@%s used GETPASS on %s", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, nick); + if (WallGetpass) + ircdproto->SendGlobops(s_NickServ, "\2%s\2 used GETPASS on \2%s\2", u->nick, nick); + notice_lang(s_NickServ, u, NICK_GETPASS_PASSWORD_IS, nick, tmp_pass); + } + else + notice_lang(s_NickServ, u, NICK_GETPASS_UNAVAILABLE); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_admin(u)) + return false; + + notice_lang(s_NickServ, u, NICK_SERVADMIN_HELP_GETPASS); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "GETPASS", NICK_GETPASS_SYNTAX); + } +}; class NSGetPass : public Module { public: NSGetPass(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("GETPASS", do_getpass, is_services_admin, -1, -1, -1, NICK_SERVADMIN_HELP_GETPASS, NICK_SERVADMIN_HELP_GETPASS); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + this->AddCommand(NICKSERV, new CommandNSGetPass(), MOD_UNIQUE); this->SetNickHelp(myNickServHelp); } @@ -40,61 +98,10 @@ class NSGetPass : public Module * Add the help response to anopes /ns help output. * @param u The user who is requesting help **/ -void myNickServHelp(User * u) +void myNickServHelp(User *u) { - if (is_services_admin(u)) { + if (is_services_admin(u)) notice_lang(s_NickServ, u, NICK_HELP_CMD_GETPASS); - } -} - -/** - * The /ns getpass command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_getpass(User * u) -{ - char *nick = strtok(NULL, " "); - char tmp_pass[PASSMAX]; - NickAlias *na; - NickRequest *nr = NULL; - - if (!nick) { - syntax_error(s_NickServ, u, "GETPASS", NICK_GETPASS_SYNTAX); - } else if (!(na = findnick(nick))) { - if ((nr = findrequestnick(nick))) { - alog("%s: %s!%s@%s used GETPASS on %s", s_NickServ, u->nick, - u->username, u->host, nick); - if (WallGetpass) - ircdproto->SendGlobops(s_NickServ, - "\2%s\2 used GETPASS on \2%s\2", u->nick, - nick); - notice_lang(s_NickServ, u, NICK_GETPASS_PASSCODE_IS, nick, - nr->passcode); - } else { - notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); - } - } else if (na->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); - } else if (NSSecureAdmins && nick_is_services_admin(na->nc) - && !is_services_root(u)) { - notice_lang(s_NickServ, u, PERMISSION_DENIED); - } else if (NSRestrictGetPass && !is_services_root(u)) { - notice_lang(s_NickServ, u, PERMISSION_DENIED); - } else { - if(enc_decrypt(na->nc->pass,tmp_pass,PASSMAX - 1)==1) { - alog("%s: %s!%s@%s used GETPASS on %s", s_NickServ, u->nick, - u->username, u->host, nick); - if (WallGetpass) - ircdproto->SendGlobops(s_NickServ, "\2%s\2 used GETPASS on \2%s\2", - u->nick, nick); - notice_lang(s_NickServ, u, NICK_GETPASS_PASSWORD_IS, nick, - tmp_pass); - } else { - notice_lang(s_NickServ, u, NICK_GETPASS_UNAVAILABLE); - } - } - return MOD_CONT; } MODULE_INIT("ns_getpass", NSGetPass) diff --git a/src/core/ns_ghost.c b/src/core/ns_ghost.c index be4a72752..840615da8 100644 --- a/src/core/ns_ghost.c +++ b/src/core/ns_ghost.c @@ -15,89 +15,101 @@ #include "module.h" -int do_ghost(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); + +class CommandNSGhost : public Command +{ + public: + CommandNSGhost() : Command("GHOST", 1, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[0].c_str(); + const char *pass = params.size() > 1 ? params[1].c_str() : NULL; + NickAlias *na; + User *u2; + + if (!(u2 = finduser(nick))) + notice_lang(s_NickServ, u, NICK_X_NOT_IN_USE, nick); + else if (!(na = u2->na)) + notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + else if (na->status & NS_VERBOTEN) + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); + else if (na->nc->flags & NI_SUSPENDED) + notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); + else if (!stricmp(nick, u->nick)) + notice_lang(s_NickServ, u, NICK_NO_GHOST_SELF); + else if (pass) + { + int res = enc_check_password(pass, na->nc->pass); + if (res == 1) + { + char buf[NICKMAX + 32]; + snprintf(buf, sizeof(buf), "GHOST command used by %s", u->nick); + kill_user(s_NickServ, nick, buf); + notice_lang(s_NickServ, u, NICK_GHOST_KILLED, nick); + } + else + { + notice_lang(s_NickServ, u, ACCESS_DENIED); + if (!res) + { + alog("%s: GHOST: invalid password for %s by %s!%s@%s", s_NickServ, nick, u->nick, u->GetIdent().c_str(), u->host); + bad_password(u); + } + } + } + else + { + if (group_identified(u, na->nc) || (!(na->nc->flags & NI_SECURE) && is_on_access(u, na->nc))) + { + char buf[NICKMAX + 32]; + snprintf(buf, sizeof(buf), "GHOST command used by %s", u->nick); + kill_user(s_NickServ, nick, buf); + notice_lang(s_NickServ, u, NICK_GHOST_KILLED, nick); + } + else + notice_lang(s_NickServ, u, ACCESS_DENIED); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_NickServ, u, NICK_HELP_GHOST); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "GHOST", NICK_GHOST_SYNTAX); + } +}; class NSGhost : public Module { public: NSGhost(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("GHOST", do_ghost, NULL, NICK_HELP_GHOST, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + this->AddCommand(NICKSERV, new CommandNSGhost(), MOD_UNIQUE); this->SetNickHelp(myNickServHelp); } }; - - /** * Add the help response to anopes /ns help output. * @param u The user who is requesting help **/ -void myNickServHelp(User * u) +void myNickServHelp(User *u) { notice_lang(s_NickServ, u, NICK_HELP_CMD_GHOST); } -/** - * The /ns ghost command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_ghost(User * u) -{ - char *nick = strtok(NULL, " "); - char *pass = strtok(NULL, " "); - NickAlias *na; - User *u2; - - if (!nick) { - syntax_error(s_NickServ, u, "GHOST", NICK_GHOST_SYNTAX); - } else if (!(u2 = finduser(nick))) { - notice_lang(s_NickServ, u, NICK_X_NOT_IN_USE, nick); - } else if (!(na = u2->na)) { - notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); - } else if (na->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); - } else if (na->nc->flags & NI_SUSPENDED) { - notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); - } else if (stricmp(nick, u->nick) == 0) { - notice_lang(s_NickServ, u, NICK_NO_GHOST_SELF); - } else if (pass) { - int res = enc_check_password(pass, na->nc->pass); - if (res == 1) { - char buf[NICKMAX + 32]; - snprintf(buf, sizeof(buf), "GHOST command used by %s", u->nick); - kill_user(s_NickServ, nick, buf); - notice_lang(s_NickServ, u, NICK_GHOST_KILLED, nick); - } else { - notice_lang(s_NickServ, u, ACCESS_DENIED); - if (res == 0) { - alog("%s: GHOST: invalid password for %s by %s!%s@%s", - s_NickServ, nick, u->nick, u->username, u->host); - bad_password(u); - } - } - } else { - if (group_identified(u, na->nc) - || (!(na->nc->flags & NI_SECURE) && is_on_access(u, na->nc))) { - char buf[NICKMAX + 32]; - snprintf(buf, sizeof(buf), "GHOST command used by %s", u->nick); - kill_user(s_NickServ, nick, buf); - notice_lang(s_NickServ, u, NICK_GHOST_KILLED, nick); - } else { - notice_lang(s_NickServ, u, ACCESS_DENIED); - } - } - return MOD_CONT; -} - MODULE_INIT("ns_ghost", NSGhost) diff --git a/src/core/ns_group.c b/src/core/ns_group.c index 888dc513f..724329327 100644 --- a/src/core/ns_group.c +++ b/src/core/ns_group.c @@ -15,229 +15,291 @@ #include "module.h" -int do_group(User * u); -void myNickServHelp(User * u); -int do_glist(User * u); -int do_listlinks(User * u); +void myNickServHelp(User *u); -NickAlias *makealias(const char *nick, NickCore * nc); +NickAlias *makealias(const char *nick, NickCore *nc); -/* Obsolete commands */ -int do_link(User * u); - -class NSGroup : public Module +class CommandNSGroup : public Command { public: - NSGroup(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandNSGroup() : Command("GROUP", 2, 2) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("GROUP", do_group, NULL, NICK_HELP_GROUP, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - - c = createCommand("LINK", do_link, NULL, -1, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - - c = createCommand("GLIST", do_glist, NULL, -1, NICK_HELP_GLIST, -1, NICK_SERVADMIN_HELP_GLIST, NICK_SERVADMIN_HELP_GLIST); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + } - c = createCommand("LISTLINKS", do_listlinks, NULL, -1, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + NickAlias *na, *target; + NickCore *nc; + const char *nick = params[0].c_str(); + const char *pass = params[1].c_str(); + int i; + char tsbuf[16]; + char modes[512]; + int len; + + if (NSEmailReg && findrequestnick(u->nick)) + { + notice_lang(s_NickServ, u, NICK_REQUESTED); + return MOD_CONT; + } - this->SetNickHelp(myNickServHelp); - } -}; + if (readonly) + { + notice_lang(s_NickServ, u, NICK_GROUP_DISABLED); + return MOD_CONT; + } + if (checkDefCon(DEFCON_NO_NEW_NICKS)) + { + notice_lang(s_NickServ, u, OPER_DEFCON_DENIED); + return MOD_CONT; + } + if (!ircdproto->IsNickValid(u->nick)) + { + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, u->nick); + return MOD_CONT; + } + if (RestrictOperNicks) + { + for (i = 0; i < RootNumber; ++i) + { + if (stristr(u->nick, ServicesRoots[i]) && !is_oper(u)) + { + notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, u->nick); + return MOD_CONT; + } + } + for (i = 0; i < servadmins.count && (nc = static_cast<NickCore *>(servadmins.list[i])); ++i) + { + if (stristr(u->nick, nc->display) && !is_oper(u)) + { + notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, u->nick); + return MOD_CONT; + } + } + for (i = 0; i < servopers.count && (nc = static_cast<NickCore *>(servopers.list[i])); ++i) + { + if (stristr(u->nick, nc->display) && !is_oper(u)) + { + notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, u->nick); + return MOD_CONT; + } + } + } -/** - * Add the help response to anopes /ns help output. - * @param u The user who is requesting help - **/ -void myNickServHelp(User * u) -{ - notice_lang(s_NickServ, u, NICK_HELP_CMD_GROUP); - notice_lang(s_NickServ, u, NICK_HELP_CMD_GLIST); -} + if (!(target = findnick(nick))) + notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + else if (time(NULL) < u->lastnickreg + NSRegDelay) + notice_lang(s_NickServ, u, NICK_GROUP_PLEASE_WAIT, NSRegDelay); + else if (u->na && (u->na->status & NS_VERBOTEN)) + { + alog("%s: %s@%s tried to use GROUP from FORBIDden nick %s", s_NickServ, u->GetIdent().c_str(), u->host, u->nick); + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, u->nick); + } + else if (u->na && (u->na->nc->flags & NI_SUSPENDED)) + { + alog("%s: %s!%s@%s tried to use GROUP from SUSPENDED nick %s", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, target->nick); + notice_lang(s_NickServ, u, NICK_X_SUSPENDED, u->nick); + } + else if (u->na && NSNoGroupChange) + notice_lang(s_NickServ, u, NICK_GROUP_CHANGE_DISABLED, s_NickServ); + else if (u->na && !nick_identified(u)) + notice_lang(s_NickServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + else if (target && (target->nc->flags & NI_SUSPENDED)) + { + alog("%s: %s!%s@%s tried to use GROUP from SUSPENDED nick %s", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, target->nick); + notice_lang(s_NickServ, u, NICK_X_SUSPENDED, target->nick); + } + else if (target->status & NS_VERBOTEN) + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, nick); + else if (u->na && target->nc == u->na->nc) + notice_lang(s_NickServ, u, NICK_GROUP_SAME, target->nick); + else if (NSMaxAliases && (target->nc->aliases.count >= NSMaxAliases) && !nick_is_services_admin(target->nc)) + notice_lang(s_NickServ, u, NICK_GROUP_TOO_MANY, target->nick, s_NickServ, s_NickServ); + else if (enc_check_password(pass, target->nc->pass) != 1) + { + alog("%s: Failed GROUP for %s!%s@%s (invalid password)", s_NickServ, u->nick, u->GetIdent().c_str(), u->host); + notice_lang(s_NickServ, u, PASSWORD_INCORRECT); + bad_password(u); + } + else + { + /* If the nick is already registered, drop it. + * If not, check that it is valid. + */ + if (u->na) + delnick(u->na); + else + { + int prefixlen = strlen(NSGuestNickPrefix); + int nicklen = strlen(u->nick); + + if (nicklen <= prefixlen + 7 && nicklen >= prefixlen + 1 && stristr(u->nick, NSGuestNickPrefix) == u->nick && strspn(u->nick + prefixlen, "1234567890") == nicklen - prefixlen) + { + notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, u->nick); + return MOD_CONT; + } + } + na = makealias(u->nick, target->nc); + + if (na) + { + na->last_usermask = new char[u->GetIdent().length() + u->GetDisplayedHost().length() + 2]; + sprintf(na->last_usermask, "%s@%s", u->GetIdent().c_str(), u->GetDisplayedHost().c_str()); + na->last_realname = sstrdup(u->realname); + na->time_registered = na->last_seen = time(NULL); + na->status = static_cast<int16>(NS_IDENTIFIED | NS_RECOGNIZED); + + if (!(na->nc->flags & NI_SERVICES_ROOT)) + { + for (i = 0; i < RootNumber; ++i) + { + if (!stricmp(ServicesRoots[i], u->nick)) + { + na->nc->flags |= NI_SERVICES_ROOT; + break; + } + } + } -/** - * The /ns group command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -/* Register a nick in a specified group. */ + u->na = na; + na->u = u; + + send_event(EVENT_GROUP, 1, u->nick); + alog("%s: %s!%s@%s makes %s join group of %s (%s) (e-mail: %s)", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, u->nick, target->nick, target->nc->display, (target->nc->email ? target->nc->email : "none")); + notice_lang(s_NickServ, u, NICK_GROUP_JOINED, target->nick); + + u->lastnickreg = time(NULL); + snprintf(tsbuf, sizeof(tsbuf), "%lu", static_cast<unsigned long>(u->timestamp)); + if (ircd->modeonreg) + { + len = strlen(ircd->modeonreg); + strncpy(modes, ircd->modeonreg, 512); + if (ircd->rootmodeonid && is_services_root(u)) + strncat(modes, ircd->rootmodeonid, 512 - len); + else if (ircd->adminmodeonid && is_services_admin(u)) + strncat(modes, ircd->adminmodeonid, 512 - len); + else if (ircd->opermodeonid && is_services_oper(u)) + strncat(modes, ircd->opermodeonid, 512 - len); + if (ircd->tsonmode) + common_svsmode(u, modes, tsbuf); + else + common_svsmode(u, modes, NULL); + } -int do_group(User * u) -{ - NickAlias *na, *target; - NickCore *nc; - char *nick = strtok(NULL, " "); - char *pass = strtok(NULL, " "); - int i; - char tsbuf[16]; - char modes[512]; - int len; - - if (NSEmailReg && (findrequestnick(u->nick))) { - notice_lang(s_NickServ, u, NICK_REQUESTED); + check_memos(u); + } + else + { + alog("%s: makealias(%s) failed", s_NickServ, u->nick); + notice_lang(s_NickServ, u, NICK_GROUP_FAILED); + } + } return MOD_CONT; } - if (readonly) { - notice_lang(s_NickServ, u, NICK_GROUP_DISABLED); - return MOD_CONT; - } - if (checkDefCon(DEFCON_NO_NEW_NICKS)) { - notice_lang(s_NickServ, u, OPER_DEFCON_DENIED); - return MOD_CONT; + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_NickServ, u, NICK_HELP_GROUP); + return true; } - if (!ircdproto->IsNickValid(u->nick)) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, u->nick); - return MOD_CONT; + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "GROUP", NICK_GROUP_SYNTAX); } +}; - if (RestrictOperNicks) { - for (i = 0; i < RootNumber; i++) { - if (stristr(u->nick, ServicesRoots[i]) && !is_oper(u)) { - notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, - u->nick); - return MOD_CONT; - } - } - for (i = 0; i < servadmins.count && (nc = static_cast<NickCore *>(servadmins.list[i])); i++) { - if (stristr(u->nick, nc->display) && !is_oper(u)) { - notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, - u->nick); - return MOD_CONT; - } - } - for (i = 0; i < servopers.count && (nc = static_cast<NickCore *>(servopers.list[i])); i++) { - if (stristr(u->nick, nc->display) && !is_oper(u)) { - notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, - u->nick); - return MOD_CONT; - } - } +class CommandNSGList : public Command +{ + public: + CommandNSGList() : Command("GLIST", 0, 1) + { } - if (!nick || !pass) { - syntax_error(s_NickServ, u, "GROUP", NICK_GROUP_SYNTAX); - } else if (!(target = findnick(nick))) { - notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); - } else if (time(NULL) < u->lastnickreg + NSRegDelay) { - notice_lang(s_NickServ, u, NICK_GROUP_PLEASE_WAIT, NSRegDelay); - } else if (u->na && (u->na->status & NS_VERBOTEN)) { - alog("%s: %s@%s tried to use GROUP from FORBIDden nick %s", - s_NickServ, u->username, u->host, u->nick); - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, u->nick); - } else if (u->na && (u->na->nc->flags & NI_SUSPENDED)) { - alog("%s: %s!%s@%s tried to use GROUP from SUSPENDED nick %s", - s_NickServ, u->nick, u->username, u->host, target->nick); - notice_lang(s_NickServ, u, NICK_X_SUSPENDED, u->nick); - } else if (u->na && NSNoGroupChange) { - notice_lang(s_NickServ, u, NICK_GROUP_CHANGE_DISABLED, s_NickServ); - } else if (u->na && !nick_identified(u)) { - notice_lang(s_NickServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); - } else if (target && (target->nc->flags & NI_SUSPENDED)) { - alog("%s: %s!%s@%s tried to use GROUP from SUSPENDED nick %s", - s_NickServ, u->nick, u->username, u->host, target->nick); - notice_lang(s_NickServ, u, NICK_X_SUSPENDED, target->nick); - } else if (target->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, nick); - } else if (u->na && target->nc == u->na->nc) { - notice_lang(s_NickServ, u, NICK_GROUP_SAME, target->nick); - } else if (NSMaxAliases && (target->nc->aliases.count >= NSMaxAliases) - && !nick_is_services_admin(target->nc)) { - notice_lang(s_NickServ, u, NICK_GROUP_TOO_MANY, target->nick, - s_NickServ, s_NickServ); - } else if (enc_check_password(pass, target->nc->pass) != 1) { - alog("%s: Failed GROUP for %s!%s@%s (invalid password)", - s_NickServ, u->nick, u->username, u->host); - notice_lang(s_NickServ, u, PASSWORD_INCORRECT); - bad_password(u); - } else { - /* If the nick is already registered, drop it. - * If not, check that it is valid. - */ - if (u->na) { - delnick(u->na); - } else { - int prefixlen = strlen(NSGuestNickPrefix); - int nicklen = strlen(u->nick); - - if (nicklen <= prefixlen + 7 && nicklen >= prefixlen + 1 - && stristr(u->nick, NSGuestNickPrefix) == u->nick - && strspn(u->nick + prefixlen, - "1234567890") == nicklen - prefixlen) { - notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, - u->nick); - return MOD_CONT; - } - } - na = makealias(u->nick, target->nc); - - if (na) { - na->last_usermask = new char[strlen(common_get_vident(u)) + strlen(common_get_vhost(u)) + 2]; - sprintf(na->last_usermask, "%s@%s", common_get_vident(u), - common_get_vhost(u)); - na->last_realname = sstrdup(u->realname); - na->time_registered = na->last_seen = time(NULL); - na->status = static_cast<int16>(NS_IDENTIFIED | NS_RECOGNIZED); - - if (!(na->nc->flags & NI_SERVICES_ROOT)) { - for (i = 0; i < RootNumber; i++) { - if (!stricmp(ServicesRoots[i], u->nick)) { - na->nc->flags |= NI_SERVICES_ROOT; - break; + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params.size() ? params[0].c_str() : NULL; + + NickAlias *na, *na2; + int is_servadmin = is_services_admin(u); + int nick_ided = nick_identified(u); + int i; + + if (nick ? (stricmp(nick, u->nick) ? !is_servadmin : !nick_ided) : !nick_ided) + notice_lang(s_NickServ, u, nick_ided ? ACCESS_DENIED : NICK_IDENTIFY_REQUIRED, s_NickServ); + else if (!nick ? !(na = u->na) : !(na = findnick(nick))) + notice_lang(s_NickServ, u, !nick ? NICK_NOT_REGISTERED : NICK_X_NOT_REGISTERED, nick); + else if (na->status & NS_VERBOTEN) + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); + else + { + time_t expt; + struct tm *tm; + char buf[BUFSIZE]; + int wont_expire; + + notice_lang(s_NickServ, u, nick ? NICK_GLIST_HEADER_X : NICK_GLIST_HEADER, na->nc->display); + for (i = 0; i < na->nc->aliases.count; ++i) + { + na2 = static_cast<NickAlias *>(na->nc->aliases.list[i]); + if (na2->nc == na->nc) + { + if (!(wont_expire = na2->status & NS_NO_EXPIRE)) + { + expt = na2->last_seen + NSExpire; + tm = localtime(&expt); + strftime_lang(buf, sizeof(buf), na2->u, STRFTIME_DATE_TIME_FORMAT, tm); } + notice_lang(s_NickServ, u, is_services_admin(u) && !wont_expire ? NICK_GLIST_REPLY_ADMIN : NICK_GLIST_REPLY, wont_expire ? '!' : ' ', na2->nick, buf); } } + notice_lang(s_NickServ, u, NICK_GLIST_FOOTER, na->nc->aliases.count); + } + return MOD_CONT; + } - u->na = na; - na->u = u; - - send_event(EVENT_GROUP, 1, u->nick); - alog("%s: %s!%s@%s makes %s join group of %s (%s) (e-mail: %s)", s_NickServ, u->nick, u->username, u->host, u->nick, target->nick, target->nc->display, (target->nc->email ? target->nc->email : "none")); - notice_lang(s_NickServ, u, NICK_GROUP_JOINED, target->nick); - - u->lastnickreg = time(NULL); - snprintf(tsbuf, sizeof(tsbuf), "%lu", - static_cast<unsigned long>(u->timestamp)); - if (ircd->modeonreg) { - len = strlen(ircd->modeonreg); - strncpy(modes,ircd->modeonreg,512); - if(ircd->rootmodeonid && is_services_root(u)) { - strncat(modes,ircd->rootmodeonid,512-len); - } else if(ircd->adminmodeonid && is_services_admin(u)) { - strncat(modes,ircd->adminmodeonid,512-len); - } else if(ircd->opermodeonid && is_services_oper(u)) { - strncat(modes,ircd->opermodeonid,512-len); - } - if (ircd->tsonmode) { - common_svsmode(u, modes, tsbuf); - } else { - common_svsmode(u, modes, NULL); - } - } - check_memos(u); - } else { - alog("%s: makealias(%s) failed", s_NickServ, u->nick); - notice_lang(s_NickServ, u, NICK_GROUP_FAILED); - } + bool OnHelp(User *u, const std::string &subcommand) + { + if (is_services_admin(u)) + notice_lang(s_NickServ, u, NICK_SERVADMIN_HELP_GLIST); + else + notice_lang(s_NickServ, u, NICK_HELP_GLIST); + + return true; } - return MOD_CONT; -} +}; +class NSGroup : public Module +{ + public: + NSGroup(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); -/* Creates a new alias in NickServ database. */ + this->AddCommand(NICKSERV, new CommandNSGroup(), MOD_UNIQUE); + this->AddCommand(NICKSERV, new CommandNSGList(), MOD_UNIQUE); -NickAlias *makealias(const char *nick, NickCore * nc) + this->SetNickHelp(myNickServHelp); + } +}; + +/** + * Add the help response to anopes /ns help output. + * @param u The user who is requesting help + **/ +void myNickServHelp(User *u) +{ + notice_lang(s_NickServ, u, NICK_HELP_CMD_GROUP); + notice_lang(s_NickServ, u, NICK_HELP_CMD_GLIST); +} + +/* Creates a new alias in NickServ database. */ +NickAlias *makealias(const char *nick, NickCore *nc) { NickAlias *na; @@ -250,68 +312,4 @@ NickAlias *makealias(const char *nick, NickCore * nc) return na; } - -int do_link(User * u) -{ - notice_lang(s_NickServ, u, OBSOLETE_COMMAND, "GROUP"); - return MOD_CONT; -} - -int do_glist(User * u) -{ - char *nick = strtok(NULL, " "); - - NickAlias *na, *na2; - int is_servadmin = is_services_admin(u); - int nick_ided = nick_identified(u); - int i; - - if ((nick ? (stricmp(nick, u->nick) ? !is_servadmin : !nick_ided) - : !nick_ided)) { - notice_lang(s_NickServ, u, - (nick_ided ? ACCESS_DENIED : - NICK_IDENTIFY_REQUIRED), s_NickServ); - } else if ((!nick ? !(na = u->na) : !(na = findnick(nick)))) { - notice_lang(s_NickServ, u, - (!nick ? NICK_NOT_REGISTERED : NICK_X_NOT_REGISTERED), - nick); - } else if (na->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); - } else { - time_t expt; - struct tm *tm; - char buf[BUFSIZE]; - int wont_expire; - - notice_lang(s_NickServ, u, - nick ? NICK_GLIST_HEADER_X : NICK_GLIST_HEADER, - na->nc->display); - for (i = 0; i < na->nc->aliases.count; i++) { - na2 = static_cast<NickAlias *>(na->nc->aliases.list[i]); - if (na2->nc == na->nc) { - if (!(wont_expire = na2->status & NS_NO_EXPIRE)) { - expt = na2->last_seen + NSExpire; - tm = localtime(&expt); - strftime_lang(buf, sizeof(buf), na2->u, - STRFTIME_DATE_TIME_FORMAT, tm); - } - notice_lang(s_NickServ, u, - ((is_services_admin(u) && !wont_expire) - ? NICK_GLIST_REPLY_ADMIN : NICK_GLIST_REPLY), - (wont_expire ? '!' : ' '), na2->nick, buf); - } - } - notice_lang(s_NickServ, u, NICK_GLIST_FOOTER, - na->nc->aliases.count); - } - return MOD_CONT; -} - - -int do_listlinks(User * u) -{ - notice_lang(s_NickServ, u, OBSOLETE_COMMAND, "GLIST"); - return MOD_CONT; -} - MODULE_INIT("ns_group", NSGroup) diff --git a/src/core/ns_help.c b/src/core/ns_help.c index 55683fa28..4d9129236 100644 --- a/src/core/ns_help.c +++ b/src/core/ns_help.c @@ -6,8 +6,8 @@ * Please read COPYING and README for further details. * * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * + * Based on the original code of Services by Andy Church. + * * $Id$ * */ @@ -15,56 +15,50 @@ #include "module.h" -int do_help(User * u); - -class NSHelp : public Module +class CommandNSHelp : public Command { public: - NSHelp(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandNSHelp() : Command("HELP", 1, 1) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("HELP", do_help, NULL, -1, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); } -}; + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str() + if (!stricmp(cmd, "SET LANGUAGE")) + { + int i; + notice_help(s_NickServ, u, NICK_HELP_SET_LANGUAGE); + for (i = 0; i < NUM_LANGS && langlist[i] >= 0; ++i) + notice_user(s_NickServ, u, " %2d) %s", i + 1, langnames[langlist[i]]); + } + else + mod_help_cmd(s_NickServ, u, NICKSERV, cmd); + } -/** - * The /ns help command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_help(User * u) -{ - char *cmd = strtok(NULL, ""); - - if (!cmd) { + void OnSyntaxError(User *u) + { notice_help(s_NickServ, u, NICK_HELP); moduleDisplayHelp(1, u); - if (is_services_admin(u)) { + if (is_services_admin(u)) notice_help(s_NickServ, u, NICK_SERVADMIN_HELP); - } if (NSExpire >= 86400) - notice_help(s_NickServ, u, NICK_HELP_EXPIRES, - NSExpire / 86400); + notice_help(s_NickServ, u, NICK_HELP_EXPIRES, NSExpire / 86400); notice_help(s_NickServ, u, NICK_HELP_FOOTER); - } else if (stricmp(cmd, "SET LANGUAGE") == 0) { - int i; - notice_help(s_NickServ, u, NICK_HELP_SET_LANGUAGE); - for (i = 0; i < NUM_LANGS && langlist[i] >= 0; i++) - notice_user(s_NickServ, u, " %2d) %s", i + 1, - langnames[langlist[i]]); - } else { - mod_help_cmd(s_NickServ, u, NICKSERV, cmd); } - return MOD_CONT; -} +}; + +class NSHelp : public Module +{ + public: + NSHelp(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); -/* EOF */ + this->AddCommand(NICKSERV, new CommandNSHelp(), MOD_UNIQUE); + } +}; MODULE_INIT("ns_help", NSHelp) diff --git a/src/core/ns_identify.c b/src/core/ns_identify.c index df2bece6e..76940f475 100644 --- a/src/core/ns_identify.c +++ b/src/core/ns_identify.c @@ -15,31 +15,132 @@ #include "module.h" -#define TO_COLLIDE 0 /* Collide the user with this nick */ -#define TO_RELEASE 1 /* Release a collided nick */ +#define TO_COLLIDE 0 /* Collide the user with this nick */ +#define TO_RELEASE 1 /* Release a collided nick */ -int do_identify(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); +class CommandNSIdentify : public Command +{ + public: + CommandNSIdentify(const std::string &cname) : Command(cname, 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + char *pass = params[0].c_str(); + NickAlias *na; + NickRequest *nr; + int res; + char tsbuf[16]; + char modes[512]; + int len; + + if (!(na = u->na)) + { + if ((nr = findrequestnick(u->nick))) + notice_lang(s_NickServ, u, NICK_IS_PREREG); + else + notice_lang(s_NickServ, u, NICK_NOT_REGISTERED); + } + else if (na->status & NS_VERBOTEN) + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); + else if (na->nc->flags & NI_SUSPENDED) + notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); + else if (nick_identified(u)) + notice_lang(s_NickServ, u, NICK_ALREADY_IDENTIFIED); + else if (!(res = enc_check_password(pass, na->nc->pass))) + { + alog("%s: Failed IDENTIFY for %s!%s@%s", s_NickServ, u->nick, u->GetIdent().c_str(), u->host); + notice_lang(s_NickServ, u, PASSWORD_INCORRECT); + bad_password(u); + } + else if (res == -1) + notice_lang(s_NickServ, u, NICK_IDENTIFY_FAILED); + else + { + if (!(na->status & NS_IDENTIFIED) && !(na->status & NS_RECOGNIZED)) + { + if (na->last_usermask) + delete [] na->last_usermask; + na->last_usermask = new char[u->GetIdent().length() + u->GetDisplayedHost().length() + 2]; + sprintf(na->last_usermask, "%s@%s", u->GetIdent().c_str(), u->GetDisplayedHost().c_str()); + if (na->last_realname) + delete [] na->last_realname; + na->last_realname = sstrdup(u->realname); + } + + na->status |= NS_IDENTIFIED; + na->last_seen = time(NULL); + snprintf(tsbuf, sizeof(tsbuf), "%lu", static_cast<unsigned long>(u->timestamp)); + + if (ircd->modeonreg) + { + len = strlen(ircd->modeonreg); + strncpy(modes, ircd->modeonreg, 512); + if (ircd->rootmodeonid && is_services_root(u)) + strncat(modes, ircd->rootmodeonid, 512 - len); + else if (ircd->adminmodeonid && is_services_admin(u)) + strncat(modes, ircd->adminmodeonid, 512 - len); + else if (ircd->opermodeonid && is_services_oper(u)) + strncat(modes, ircd->opermodeonid, 512 - len); + if (ircd->tsonmode) + common_svsmode(u, modes, tsbuf); + else + common_svsmode(u, modes, ""); + } + send_event(EVENT_NICK_IDENTIFY, 1, u->nick); + alog("%s: %s!%s@%s identified for nick %s", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, u->nick); + notice_lang(s_NickServ, u, NICK_IDENTIFY_SUCCEEDED); + if (ircd->vhost) + do_on_id(u); + if (NSModeOnID) + do_setmodes(u); + + if (NSForceEmail && u->na && !u->na->nc->email) + { + notice_lang(s_NickServ, u, NICK_IDENTIFY_EMAIL_REQUIRED); + notice_help(s_NickServ, u, NICK_IDENTIFY_EMAIL_HOWTO); + } + + if (!(na->status & NS_RECOGNIZED)) + check_memos(u); + + /* Enable nick tracking if enabled */ + if (NSNickTracking) + nsStartNickTracking(u); + + /* Clear any timers */ + if (na->nc->flags & NI_KILLPROTECT) + del_ns_timeout(na, TO_COLLIDE); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_NickServ, u, NICK_HELP_IDENTIFY); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "IDENTIFY", NICK_IDENTIFY_SYNTAX); + } +}; class NSIdentify : public Module { public: NSIdentify(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("ID", do_identify, NULL, NICK_HELP_IDENTIFY, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("IDENTIFY", do_identify, NULL, NICK_HELP_IDENTIFY, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SIDENTIFY", do_identify, NULL, -1, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - + this->AddCommand(NICKSERV, new CommandNSIdentify("IDENTIFY"), MOD_UNIQUE); + this->AddCommand(NICKSERV, new CommandNSIdentify("ID"), MOD_UNIQUE); this->SetNickHelp(myNickServHelp); } @@ -49,111 +150,9 @@ class NSIdentify : public Module * Add the help response to anopes /ns help output. * @param u The user who is requesting help **/ -void myNickServHelp(User * u) +void myNickServHelp(User *u) { notice_lang(s_NickServ, u, NICK_HELP_CMD_IDENTIFY); } -/** - * The /ns identify command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_identify(User * u) -{ - char *pass = strtok(NULL, " "); - NickAlias *na; - NickRequest *nr; - int res; - char tsbuf[16]; - char modes[512]; - int len; - - if (!pass) { - syntax_error(s_NickServ, u, "IDENTIFY", NICK_IDENTIFY_SYNTAX); - } else if (!(na = u->na)) { - if ((nr = findrequestnick(u->nick))) { - notice_lang(s_NickServ, u, NICK_IS_PREREG); - } else { - notice_lang(s_NickServ, u, NICK_NOT_REGISTERED); - } - } else if (na->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); - } else if (na->nc->flags & NI_SUSPENDED) { - notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); - } else if (nick_identified(u)) { - notice_lang(s_NickServ, u, NICK_ALREADY_IDENTIFIED); - } else if (!(res = enc_check_password(pass, na->nc->pass))) { - alog("%s: Failed IDENTIFY for %s!%s@%s", s_NickServ, u->nick, - u->username, u->host); - notice_lang(s_NickServ, u, PASSWORD_INCORRECT); - bad_password(u); - } else if (res == -1) { - notice_lang(s_NickServ, u, NICK_IDENTIFY_FAILED); - } else { - if (!(na->status & NS_IDENTIFIED) && !(na->status & NS_RECOGNIZED)) { - if (na->last_usermask) - delete [] na->last_usermask; - na->last_usermask = new char[strlen(common_get_vident(u)) + strlen(common_get_vhost(u)) + 2]; - sprintf(na->last_usermask, "%s@%s", common_get_vident(u), - common_get_vhost(u)); - if (na->last_realname) - delete [] na->last_realname; - na->last_realname = sstrdup(u->realname); - } - - na->status |= NS_IDENTIFIED; - na->last_seen = time(NULL); - snprintf(tsbuf, sizeof(tsbuf), "%lu", - static_cast<unsigned long>(u->timestamp)); - - if (ircd->modeonreg) { - len = strlen(ircd->modeonreg); - strncpy(modes,ircd->modeonreg,512); - if(ircd->rootmodeonid && is_services_root(u)) { - strncat(modes,ircd->rootmodeonid,512-len); - } else if(ircd->adminmodeonid && is_services_admin(u)) { - strncat(modes,ircd->adminmodeonid,512-len); - } else if(ircd->opermodeonid && is_services_oper(u)) { - strncat(modes,ircd->opermodeonid,512-len); - } - if (ircd->tsonmode) { - common_svsmode(u, modes, tsbuf); - } else { - common_svsmode(u, modes, ""); - } - } - ircdproto->SendAccountLogin(u, na->nc); - send_event(EVENT_NICK_IDENTIFY, 1, u->nick); - alog("%s: %s!%s@%s identified for nick %s", s_NickServ, u->nick, - u->username, u->host, u->nick); - notice_lang(s_NickServ, u, NICK_IDENTIFY_SUCCEEDED); - if (ircd->vhost) { - do_on_id(u); - } - if (NSModeOnID) { - do_setmodes(u); - } - - if (NSForceEmail && u->na && !u->na->nc->email) { - notice_lang(s_NickServ, u, NICK_IDENTIFY_EMAIL_REQUIRED); - notice_help(s_NickServ, u, NICK_IDENTIFY_EMAIL_HOWTO); - } - - if (!(na->status & NS_RECOGNIZED)) - check_memos(u); - - /* Enable nick tracking if enabled */ - if (NSNickTracking) - nsStartNickTracking(u); - - /* Clear any timers */ - if (na->nc->flags & NI_KILLPROTECT) { - del_ns_timeout(na, TO_COLLIDE); - } - - } - return MOD_CONT; -} - MODULE_INIT("ns_identify", NSIdentify) diff --git a/src/core/ns_info.c b/src/core/ns_info.c index bdf6325cb..ea903a0e7 100644 --- a/src/core/ns_info.c +++ b/src/core/ns_info.c @@ -15,259 +15,234 @@ #include "module.h" -static int do_info(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); -class NSInfo : public Module +class CommandNSInfo : public Command { - public: - NSInfo(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + // cannot be const, as it is modified + void CheckOptStr(std::string &buf, int opt, const std::string &str, NickCore *nc, NickAlias *na, bool reverse_logic = false) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion - ("$Id$"); - this->SetType(CORE); + if (reverse_logic ? !(nc->flags & opt) : (nc->flags & opt)) + { + const char *commastr = getstring(na, COMMA_SPACE); + if (!buf.empty()) + buf += commastr; - c = createCommand("INFO", do_info, NULL, NICK_HELP_INFO, -1, NICK_HELP_INFO, NICK_SERVADMIN_HELP_INFO, NICK_SERVADMIN_HELP_INFO); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - - this->SetNickHelp(myNickServHelp); + buf += str; + } + } + public: + CommandNSInfo() : Command("INFO", 1, 2) + { } -}; - - - - -/** - * Add the help response to anopes /ns help output. - * @param u The user who is requesting help - **/ -void myNickServHelp(User * u) -{ - notice_lang(s_NickServ, u, NICK_HELP_CMD_INFO); -} - -/** - * The /ns info command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_info(User * u) -{ - -/* Show hidden info to nick owners and sadmins when the "ALL" parameter is - * supplied. If a nick is online, the "Last seen address" changes to "Is - * online from". - * Syntax: INFO <nick> {ALL} - * -TheShadow (13 Mar 1999) - */ - - char *nick = strtok(NULL, " "); - char *param = strtok(NULL, " "); - - NickAlias *na; - NickRequest *nr = NULL; - /* Being an oper is enough from now on -GD */ - int is_servadmin = is_services_oper(u); - if (!nick) { - syntax_error(s_NickServ, u, "INFO", NICK_INFO_SYNTAX); - } else if (!(na = findnick(nick))) { - if ((nr = findrequestnick(nick))) { - notice_lang(s_NickServ, u, NICK_IS_PREREG); - if (param && stricmp(param, "ALL") == 0 && is_servadmin) { - notice_lang(s_NickServ, u, NICK_INFO_EMAIL, nr->email); - } else { - if (is_servadmin) { - notice_lang(s_NickServ, u, NICK_INFO_FOR_MORE, - s_NickServ, nr->nick); + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + /* Show hidden info to nick owners and sadmins when the "ALL" parameter is + * supplied. If a nick is online, the "Last seen address" changes to "Is + * online from". + * Syntax: INFO <nick> {ALL} + * -TheShadow (13 Mar 1999) + */ + char *nick = params[0].c_str(); + char *param = params.size() > 1 ? params[1].c_str() : NULL; + + NickAlias *na; + NickRequest *nr = NULL; + /* Being an oper is enough from now on -GD */ + int is_servadmin = is_services_oper(u); + + if (!(na = findnick(nick))) + { + if ((nr = findrequestnick(nick))) + { + notice_lang(s_NickServ, u, NICK_IS_PREREG); + if (param && !stricmp(param, "ALL") && is_servadmin) + notice_lang(s_NickServ, u, NICK_INFO_EMAIL, nr->email); + else + { + if (is_servadmin) + notice_lang(s_NickServ, u, NICK_INFO_FOR_MORE, s_NickServ, nr->nick); } } - } else if (nickIsServices(nick, 1)) { - notice_lang(s_NickServ, u, NICK_X_IS_SERVICES, nick); - } else { - notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + else if (nickIsServices(nick, 1)) + notice_lang(s_NickServ, u, NICK_X_IS_SERVICES, nick); + else + notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + } + else if (na->status & NS_VERBOTEN) + { + if (is_oper(u) && na->last_usermask) + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN_OPER, nick, na->last_usermask, na->last_realname ? na->last_realname : getstring(u->na, NO_REASON)); + else + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, nick); } - } else if (na->status & NS_VERBOTEN) { - if (is_oper(u) && na->last_usermask) - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN_OPER, nick, - na->last_usermask, - (na->last_realname ? na-> - last_realname : getstring(u->na, NO_REASON))); else - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, nick); - } else { - struct tm *tm; - char buf[BUFSIZE], *end; - const char *commastr = getstring(u->na, COMMA_SPACE); - int need_comma = 0; - int nick_online = 0; - int show_hidden = 0; - time_t expt; - - /* Is the real owner of the nick we're looking up online? -TheShadow */ - if (na->status & (NS_RECOGNIZED | NS_IDENTIFIED)) - nick_online = 1; - - /* Only show hidden fields to owner and sadmins and only when the ALL - * parameter is used. -TheShadow */ - if (param && stricmp(param, "ALL") == 0 && u->na - && ((nick_identified(u) && (na->nc == u->na->nc)) - || is_servadmin)) - show_hidden = 1; - - notice_lang(s_NickServ, u, NICK_INFO_REALNAME, na->nick, - na->last_realname); - - if ((nick_identified(u) && (na->nc == u->na->nc)) || is_servadmin) { - - if (nick_is_services_root(na->nc)) - notice_lang(s_NickServ, u, NICK_INFO_SERVICES_ROOT, - na->nick); - else if (nick_is_services_admin(na->nc)) - notice_lang(s_NickServ, u, NICK_INFO_SERVICES_ADMIN, - na->nick); - else if (nick_is_services_oper(na->nc)) - notice_lang(s_NickServ, u, NICK_INFO_SERVICES_OPER, - na->nick); + { + struct tm *tm; + char buf[BUFSIZE], *end; + const char *commastr = getstring(u->na, COMMA_SPACE); + int need_comma = 0; + int nick_online = 0; + int show_hidden = 0; + time_t expt; + + /* Is the real owner of the nick we're looking up online? -TheShadow */ + if (na->status & (NS_RECOGNIZED | NS_IDENTIFIED)) + nick_online = 1; + + /* Only show hidden fields to owner and sadmins and only when the ALL + * parameter is used. -TheShadow */ + if (param && !stricmp(param, "ALL") && u->na && ((nick_identified(u) && na->nc == u->na->nc) || is_servadmin)) + show_hidden = 1; + + notice_lang(s_NickServ, u, NICK_INFO_REALNAME, na->nick, na->last_realname); + + if ((nick_identified(u) && na->nc == u->na->nc) || is_servadmin) + { + if (nick_is_services_root(na->nc)) + notice_lang(s_NickServ, u, NICK_INFO_SERVICES_ROOT, na->nick); + else if (nick_is_services_admin(na->nc)) + notice_lang(s_NickServ, u, NICK_INFO_SERVICES_ADMIN, na->nick); + else if (nick_is_services_oper(na->nc)) + notice_lang(s_NickServ, u, NICK_INFO_SERVICES_OPER, na->nick); + } + else + { + if (nick_is_services_root(na->nc) && !(na->nc->flags & NI_HIDE_STATUS)) + notice_lang(s_NickServ, u, NICK_INFO_SERVICES_ROOT, na->nick); + else if (nick_is_services_admin(na->nc) && !(na->nc->flags & NI_HIDE_STATUS)) + notice_lang(s_NickServ, u, NICK_INFO_SERVICES_ADMIN, na->nick); + else if (nick_is_services_oper(na->nc) && !(na->nc->flags & NI_HIDE_STATUS)) + notice_lang(s_NickServ, u, NICK_INFO_SERVICES_OPER, na->nick); + } - } else { + if (nick_online) + { + if (show_hidden || !(na->nc->flags & NI_HIDE_MASK)) + notice_lang(s_NickServ, u, NICK_INFO_ADDRESS_ONLINE, na->last_usermask); + else + notice_lang(s_NickServ, u, NICK_INFO_ADDRESS_ONLINE_NOHOST, na->nick); + } + else { + if (show_hidden || !(na->nc->flags & NI_HIDE_MASK)) + notice_lang(s_NickServ, u, NICK_INFO_ADDRESS, na->last_usermask); + } - if (nick_is_services_root(na->nc) - && !(na->nc->flags & NI_HIDE_STATUS)) - notice_lang(s_NickServ, u, NICK_INFO_SERVICES_ROOT, - na->nick); - else if (nick_is_services_admin(na->nc) - && !(na->nc->flags & NI_HIDE_STATUS)) - notice_lang(s_NickServ, u, NICK_INFO_SERVICES_ADMIN, - na->nick); - else if (nick_is_services_oper(na->nc) - && !(na->nc->flags & NI_HIDE_STATUS)) - notice_lang(s_NickServ, u, NICK_INFO_SERVICES_OPER, - na->nick); + tm = localtime(&na->time_registered); + strftime_lang(buf, sizeof(buf), u, STRFTIME_DATE_TIME_FORMAT, tm); + notice_lang(s_NickServ, u, NICK_INFO_TIME_REGGED, buf); - } + if (!nick_online) + { + tm = localtime(&na->last_seen); + strftime_lang(buf, sizeof(buf), u, STRFTIME_DATE_TIME_FORMAT, tm); + notice_lang(s_NickServ, u, NICK_INFO_LAST_SEEN, buf); + } - if (nick_online) { - if (show_hidden || !(na->nc->flags & NI_HIDE_MASK)) - notice_lang(s_NickServ, u, NICK_INFO_ADDRESS_ONLINE, - na->last_usermask); - else - notice_lang(s_NickServ, u, NICK_INFO_ADDRESS_ONLINE_NOHOST, - na->nick); - } else { - if (show_hidden || !(na->nc->flags & NI_HIDE_MASK)) - notice_lang(s_NickServ, u, NICK_INFO_ADDRESS, - na->last_usermask); - } + if (na->last_quit && (show_hidden || !(na->nc->flags & NI_HIDE_QUIT))) + notice_lang(s_NickServ, u, NICK_INFO_LAST_QUIT, na->last_quit); + + if (na->nc->url) + notice_lang(s_NickServ, u, NICK_INFO_URL, na->nc->url); + if (na->nc->email && (show_hidden || !(na->nc->flags & NI_HIDE_EMAIL))) + notice_lang(s_NickServ, u, NICK_INFO_EMAIL, na->nc->email); + if (na->nc->icq) + notice_lang(s_NickServ, u, NICK_INFO_ICQ, na->nc->icq); + + if (show_hidden) + { + if (s_HostServ && ircd->vhost) { + if (getvHost(na->nick) != NULL) { + if (ircd->vident && getvIdent(na->nick) != NULL) { + notice_lang(s_NickServ, u, NICK_INFO_VHOST2, + getvIdent(na->nick), + getvHost(na->nick)); + } else { + notice_lang(s_NickServ, u, NICK_INFO_VHOST, + getvHost(na->nick)); + } + } + } + if (na->nc->greet) + notice_lang(s_NickServ, u, NICK_INFO_GREET, na->nc->greet); - tm = localtime(&na->time_registered); - strftime_lang(buf, sizeof(buf), u, STRFTIME_DATE_TIME_FORMAT, tm); - notice_lang(s_NickServ, u, NICK_INFO_TIME_REGGED, buf); + std::string optbuf; - if (!nick_online) { - tm = localtime(&na->last_seen); - strftime_lang(buf, sizeof(buf), u, STRFTIME_DATE_TIME_FORMAT, - tm); - notice_lang(s_NickServ, u, NICK_INFO_LAST_SEEN, buf); - } + CheckOptStr(optbuf, NI_KILLPROTECT, getstring(u->na, NICK_INFO_OPT_KILL), na->nc, u->na); + CheckOptStr(optbuf, NI_SECURE, getstring(u->na, NICK_INFO_OPT_SECURE), na->nc, u->na); + CheckOptStr(optbuf, NI_PRIVATE, getstring(u->na, NICK_INFO_OPT_PRIVATE), na->nc, u->na); + CheckOptStr(optbuf, NI_MSG, getstring(u->na, NICK_INFO_OPT_MSG), na->nc, u->na); + CheckOptStr(optbuf, NI_AUTOOP, getstring(u->na, NICK_INFO_OPT_AUTOOP), na->nc, u->na, true); - if (na->last_quit - && (show_hidden || !(na->nc->flags & NI_HIDE_QUIT))) - notice_lang(s_NickServ, u, NICK_INFO_LAST_QUIT, na->last_quit); + notice_lang(s_NickServ, u, NICK_INFO_OPTIONS, optbuf.empty() ? getstring(u->na, NICK_INFO_OPT_NONE) : optbuf.c_str()); - if (na->nc->url) - notice_lang(s_NickServ, u, NICK_INFO_URL, na->nc->url); - if (na->nc->email - && (show_hidden || !(na->nc->flags & NI_HIDE_EMAIL))) - notice_lang(s_NickServ, u, NICK_INFO_EMAIL, na->nc->email); - if (na->nc->icq) - notice_lang(s_NickServ, u, NICK_INFO_ICQ, na->nc->icq); + if (na->nc->flags & NI_SUSPENDED) + { + if (na->last_quit) + notice_lang(s_NickServ, u, NICK_INFO_SUSPENDED, na->last_quit); + else + notice_lang(s_NickServ, u, NICK_INFO_SUSPENDED_NO_REASON); + } - if (show_hidden) { - if (s_HostServ && ircd->vhost) { - if (getvHost(na->nick) != NULL) { - if (ircd->vident && getvIdent(na->nick) != NULL) { - notice_lang(s_NickServ, u, NICK_INFO_VHOST2, - getvIdent(na->nick), - getvHost(na->nick)); - } else { - notice_lang(s_NickServ, u, NICK_INFO_VHOST, - getvHost(na->nick)); + if (na->status & NS_NO_EXPIRE) + notice_lang(s_NickServ, u, NICK_INFO_NO_EXPIRE); + else + { + if (is_services_admin(u)) + { + expt = na->last_seen + NSExpire; + tm = localtime(&expt); + strftime_lang(buf, sizeof(buf), na->u, STRFTIME_DATE_TIME_FORMAT, tm); + notice_lang(s_NickServ, u, NICK_INFO_EXPIRE, buf); } } } - if (na->nc->greet) - notice_lang(s_NickServ, u, NICK_INFO_GREET, na->nc->greet); - *buf = 0; - end = buf; + if (!show_hidden && ((u->na && (na->nc == u->na->nc) && nick_identified(u)) || is_servadmin)) + notice_lang(s_NickServ, u, NICK_INFO_FOR_MORE, s_NickServ, na->nick); + } + return MOD_CONT; + } - if (na->nc->flags & NI_KILLPROTECT) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s", - getstring(u->na, NICK_INFO_OPT_KILL)); - need_comma = 1; - } - if (na->nc->flags & NI_SECURE) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, NICK_INFO_OPT_SECURE)); - need_comma = 1; - } - if (na->nc->flags & NI_PRIVATE) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, NICK_INFO_OPT_PRIVATE)); - need_comma = 1; - } - if (na->nc->flags & NI_MSG) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, NICK_INFO_OPT_MSG)); - need_comma = 1; - } - if (!(na->nc->flags & NI_AUTOOP)) { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", - need_comma ? commastr : "", - getstring(u->na, NICK_INFO_OPT_AUTOOP)); - need_comma = 1; - } + bool OnHelp(User *u, const std::string &subcommand) + { + if (is_services_admin(u)) + notice_lang(s_NickServ, u, NICK_SERVADMIN_HELP_INFO); + else + notice_lang(s_NickServ, u, NICK_HELP_INFO); + return true; + } - notice_lang(s_NickServ, u, NICK_INFO_OPTIONS, - *buf ? buf : getstring(u->na, NICK_INFO_OPT_NONE)); + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "INFO", NICK_INFO_SYNTAX); + } +}; - if (na->nc->flags & NI_SUSPENDED) { - if (na->last_quit) { - notice_lang(s_NickServ, u, NICK_INFO_SUSPENDED, - na->last_quit); - } else { - notice_lang(s_NickServ, u, - NICK_INFO_SUSPENDED_NO_REASON); - } - } +class NSInfo : public Module +{ + public: + NSInfo(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); - if (na->status & NS_NO_EXPIRE) { - notice_lang(s_NickServ, u, NICK_INFO_NO_EXPIRE); - } else { - if (is_services_admin(u)) { - expt = na->last_seen + NSExpire; - tm = localtime(&expt); - strftime_lang(buf, sizeof(buf), na->u, - STRFTIME_DATE_TIME_FORMAT, tm); - notice_lang(s_NickServ, u, NICK_INFO_EXPIRE, buf); - } - } - } + this->AddCommand(NICKSERV, new CommandNSInfo(), MOD_UNIQUE); - if (!show_hidden - && ((u->na && (na->nc == u->na->nc) && nick_identified(u)) - || is_servadmin)) - notice_lang(s_NickServ, u, NICK_INFO_FOR_MORE, s_NickServ, - na->nick); + this->SetNickHelp(myNickServHelp); } - return MOD_CONT; +}; + +/** + * Add the help response to anopes /ns help output. + * @param u The user who is requesting help + **/ +void myNickServHelp(User *u) +{ + notice_lang(s_NickServ, u, NICK_HELP_CMD_INFO); } MODULE_INIT("ns_info", NSInfo) diff --git a/src/core/ns_list.c b/src/core/ns_list.c index 1fd26c709..239b596e9 100644 --- a/src/core/ns_list.c +++ b/src/core/ns_list.c @@ -15,222 +15,222 @@ #include "module.h" -int do_list(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); -class NSList : public Module +class CommandNSList : public Command { public: - NSList(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandNSList() : Command("LIST", 1, 2) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("LIST", do_list, NULL, -1, NICK_HELP_LIST, -1, NICK_SERVADMIN_HELP_LIST, NICK_SERVADMIN_HELP_LIST); - - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - - this->SetNickHelp(myNickServHelp); } -}; - + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + /* SADMINS can search for nicks based on their NS_VERBOTEN and NS_NO_EXPIRE + * status. The keywords FORBIDDEN and NOEXPIRE represent these two states + * respectively. These keywords should be included after the search pattern. + * Multiple keywords are accepted and should be separated by spaces. Only one + * of the keywords needs to match a nick's state for the nick to be displayed. + * Forbidden nicks can be identified by "[Forbidden]" appearing in the last + * seen address field. Nicks with NOEXPIRE set are preceeded by a "!". Only + * SADMINS will be shown forbidden nicks and the "!" indicator. + * Syntax for sadmins: LIST pattern [FORBIDDEN] [NOEXPIRE] + * -TheShadow + * + * UPDATE: SUSPENDED keyword is now accepted as well. + */ + char *pattern = params[0].c_str(); + NickAlias *na; + NickCore *mync; + unsigned nnicks, i; + char buf[BUFSIZE]; + int is_servadmin = is_services_admin(u); + int16 matchflags = 0; + NickRequest *nr = NULL; + int nronly = 0; + int susp_keyword = 0; + char noexpire_char = ' '; + int count = 0, from = 0, to = 0, tofree = 0; + char *tmp = NULL; + char *s = NULL; + + if (NSListOpersOnly && !is_oper(u)) /* reverse the help logic */ + { + notice_lang(s_NickServ, u, ACCESS_DENIED); + return MOD_STOP; + } -/** - * Add the help response to anopes /ns help output. - * @param u The user who is requesting help - **/ -void myNickServHelp(User * u) -{ - if (!NSListOpersOnly || (is_oper(u))) { - notice_lang(s_NickServ, u, NICK_HELP_CMD_LIST); - } -} - -/** - * The /ns list command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_list(User * u) -{ - -/* SADMINS can search for nicks based on their NS_VERBOTEN and NS_NO_EXPIRE - * status. The keywords FORBIDDEN and NOEXPIRE represent these two states - * respectively. These keywords should be included after the search pattern. - * Multiple keywords are accepted and should be separated by spaces. Only one - * of the keywords needs to match a nick's state for the nick to be displayed. - * Forbidden nicks can be identified by "[Forbidden]" appearing in the last - * seen address field. Nicks with NOEXPIRE set are preceeded by a "!". Only - * SADMINS will be shown forbidden nicks and the "!" indicator. - * Syntax for sadmins: LIST pattern [FORBIDDEN] [NOEXPIRE] - * -TheShadow - * - * UPDATE: SUSPENDED keyword is now accepted as well. - */ - - - char *pattern = strtok(NULL, " "); - char *keyword; - NickAlias *na; - NickCore *mync; - unsigned nnicks, i; - char buf[BUFSIZE]; - int is_servadmin = is_services_admin(u); - int16 matchflags = 0; - NickRequest *nr = NULL; - int nronly = 0; - int susp_keyword = 0; - char noexpire_char = ' '; - int count = 0, from = 0, to = 0, tofree = 0; - char *tmp = NULL; - char *s = NULL; - - if (!(!NSListOpersOnly || (is_oper(u)))) { /* reverse the help logic */ - notice_lang(s_NickServ, u, ACCESS_DENIED); - return MOD_STOP; - } - - if (!pattern) { - syntax_error(s_NickServ, u, "LIST", - is_servadmin ? NICK_LIST_SERVADMIN_SYNTAX : - NICK_LIST_SYNTAX); - } else { - - if (pattern) { - if (pattern[0] == '#') { - tmp = myStrGetOnlyToken((pattern + 1), '-', 0); /* Read FROM out */ - if (!tmp) { + if (pattern[0] == '#') + { + tmp = myStrGetOnlyToken((pattern + 1), '-', 0); /* Read FROM out */ + if (!tmp) + { + notice_lang(s_ChanServ, u, LIST_INCORRECT_RANGE); + return MOD_CONT; + } + for (s = tmp; *s; ++s) + { + if (!isdigit(*s)) + { + delete [] tmp; notice_lang(s_ChanServ, u, LIST_INCORRECT_RANGE); return MOD_CONT; } - for (s = tmp; *s; s++) { - if (!isdigit(*s)) { - delete [] tmp; - notice_lang(s_ChanServ, u, LIST_INCORRECT_RANGE); - return MOD_CONT; - } - } - from = atoi(tmp); - delete [] tmp; - tmp = myStrGetTokenRemainder(pattern, '-', 1); /* Read TO out */ - if (!tmp) { + } + from = atoi(tmp); + delete [] tmp; + tmp = myStrGetTokenRemainder(pattern, '-', 1); /* Read TO out */ + if (!tmp) + { + notice_lang(s_ChanServ, u, LIST_INCORRECT_RANGE); + return MOD_CONT; + } + for (s = tmp; *s; ++s) + { + if (!isdigit(*s)) + { + delete [] tmp; notice_lang(s_ChanServ, u, LIST_INCORRECT_RANGE); return MOD_CONT; } - for (s = tmp; *s; s++) { - if (!isdigit(*s)) { - delete [] tmp; - notice_lang(s_ChanServ, u, LIST_INCORRECT_RANGE); - return MOD_CONT; - } - } - to = atoi(tmp); - delete [] tmp; - pattern = sstrdup("*"); - tofree = 1; } + to = atoi(tmp); + delete [] tmp; + pattern = sstrdup("*"); + tofree = 1; } nnicks = 0; - while (is_servadmin && (keyword = strtok(NULL, " "))) { - if (stricmp(keyword, "FORBIDDEN") == 0) - matchflags |= NS_VERBOTEN; - if (stricmp(keyword, "NOEXPIRE") == 0) - matchflags |= NS_NO_EXPIRE; - if (stricmp(keyword, "SUSPENDED") == 0) - susp_keyword = 1; - if (stricmp(keyword, "UNCONFIRMED") == 0) - nronly = 1; + if (is_servadmin && params.size() > 1) + { + std::string keyword; + spacesepstream keywords(params[1]); + while (keywords.GetString(keyword)) + { + if (!stricmp(keyword.c_str(), "FORBIDDEN")) + matchflags |= NS_VERBOTEN; + if (!stricmp(keyword.c_str(), "NOEXPIRE")) + matchflags |= NS_NO_EXPIRE; + if (!stricmp(keyword.c_str(), "SUSPENDED")) + susp_keyword = 1; + if (!stricmp(keyword.c_str(), "UNCONFIRMED")) + nronly = 1; + } } - mync = (nick_identified(u) ? u->na->nc : NULL); + mync = nick_identified(u) ? u->na->nc : NULL; notice_lang(s_NickServ, u, NICK_LIST_HEADER, pattern); - if (nronly != 1) { - for (i = 0; i < 1024; i++) { - for (na = nalists[i]; na; na = na->next) { + if (!nronly) + { + for (i = 0; i < 1024; ++i) + { + for (na = nalists[i]; na; na = na->next) + { /* Don't show private and forbidden nicks to non-services admins. */ if ((na->status & NS_VERBOTEN) && !is_servadmin) continue; - if ((na->nc->flags & NI_PRIVATE) && !is_servadmin - && na->nc != mync) + if ((na->nc->flags & NI_PRIVATE) && !is_servadmin && na->nc != mync) continue; - if ((matchflags != 0) && !(na->status & matchflags) && (susp_keyword == 0)) + if (matchflags && !(na->status & matchflags) && !susp_keyword) continue; - else if ((susp_keyword == 1) && !(na->nc->flags & NI_SUSPENDED)) + else if (susp_keyword && !(na->nc->flags & NI_SUSPENDED)) continue; /* We no longer compare the pattern against the output buffer. * Instead we build a nice nick!user@host buffer to compare. * The output is then generated separately. -TheShadow */ - snprintf(buf, sizeof(buf), "%s!%s", na->nick, - (na->last_usermask - && !(na->status & NS_VERBOTEN)) ? na-> - last_usermask : "*@*"); - if (stricmp(pattern, na->nick) == 0 - || match_wild_nocase(pattern, buf)) { - - if ((((count + 1 >= from) && (count + 1 <= to)) - || ((from == 0) && (to == 0))) - && (++nnicks <= NSListMax)) { - if (is_servadmin - && (na->status & NS_NO_EXPIRE)) + snprintf(buf, sizeof(buf), "%s!%s", na->nick, na->last_usermask && !(na->status & NS_VERBOTEN) ? na->last_usermask : "*@*"); + if (!stricmp(pattern, na->nick) || match_wild_nocase(pattern, buf)) + { + if (((count + 1 >= from && count + 1 <= to) || (!from && !to)) && ++nnicks <= NSListMax) + { + if (is_servadmin && (na->status & NS_NO_EXPIRE)) noexpire_char = '!'; - else { + else noexpire_char = ' '; - } - if ((na->nc->flags & NI_HIDE_MASK) - && !is_servadmin && na->nc != mync) { - snprintf(buf, sizeof(buf), - "%-20s [Hostname Hidden]", - na->nick); - } else if (na->status & NS_VERBOTEN) { - snprintf(buf, sizeof(buf), - "%-20s [Forbidden]", na->nick); - } else if (na->nc->flags & NI_SUSPENDED) { - snprintf(buf, sizeof(buf), - "%-20s [Suspended]", na->nick); - } else { - snprintf(buf, sizeof(buf), "%-20s %s", - na->nick, na->last_usermask); - } - notice_user(s_NickServ, u, " %c%s", - noexpire_char, buf); + if ((na->nc->flags & NI_HIDE_MASK) && !is_servadmin && na->nc != mync) + snprintf(buf, sizeof(buf), "%-20s [Hostname Hidden]", na->nick); + else if (na->status & NS_VERBOTEN) + snprintf(buf, sizeof(buf), "%-20s [Forbidden]", na->nick); + else if (na->nc->flags & NI_SUSPENDED) + snprintf(buf, sizeof(buf), "%-20s [Suspended]", na->nick); + else + snprintf(buf, sizeof(buf), "%-20s %s", na->nick, na->last_usermask); + notice_user(s_NickServ, u, " %c%s", noexpire_char, buf); } - count++; + ++count; } } } } - if (nronly == 1 || (is_servadmin && matchflags == 0)) { + if (nronly || (is_servadmin && !matchflags)) + { noexpire_char = ' '; - for (i = 0; i < 1024; i++) { - for (nr = nrlists[i]; nr; nr = nr->next) { + for (i = 0; i < 1024; ++i) + { + for (nr = nrlists[i]; nr; nr = nr->next) + { snprintf(buf, sizeof(buf), "%s!*@*", nr->nick); - if (stricmp(pattern, nr->nick) == 0 - || match_wild_nocase(pattern, buf)) { - if (++nnicks <= NSListMax) { - snprintf(buf, sizeof(buf), - "%-20s [UNCONFIRMED]", nr->nick); - notice_user(s_NickServ, u, " %c%s", - noexpire_char, buf); + if (!stricmp(pattern, nr->nick) || match_wild_nocase(pattern, buf)) + { + if (++nnicks <= NSListMax) + { + snprintf(buf, sizeof(buf), "%-20s [UNCONFIRMED]", nr->nick); + notice_user(s_NickServ, u, " %c%s", noexpire_char, buf); } } } } } - notice_lang(s_NickServ, u, NICK_LIST_RESULTS, - nnicks > NSListMax ? NSListMax : nnicks, nnicks); + notice_lang(s_NickServ, u, NICK_LIST_RESULTS, nnicks > NSListMax ? NSListMax : nnicks, nnicks); + if (tofree) + delete [] pattern; + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (is_services_admin(u)) + notice_lang(s_NickServ, u, NICK_SERVADMIN_HELP_LIST); + else + notice_lang(s_NickServ, u, NICK_HELP_LIST); } - if (tofree) - delete [] pattern; - return MOD_CONT; + + void OnSyntaxError(User *u) + { + if (is_services_admin(u)) + syntax_error(s_NickServ, u, "LIST", NICK_LIST_SERVADMIN_SYNTAX); + else + syntax_error(s_NickServ, u, "LIST", NICK_LIST_SYNTAX); + } +}; + +class NSList : public Module +{ + public: + NSList(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + + this->AddCommand(NICKSERV, new CommandNSList(), MOD_UNIQUE); + + this->SetNickHelp(myNickServHelp); + } +}; + +/** + * Add the help response to anopes /ns help output. + * @param u The user who is requesting help + **/ +void myNickServHelp(User *u) +{ + if (!NSListOpersOnly || is_oper(u)) + notice_lang(s_NickServ, u, NICK_HELP_CMD_LIST); } MODULE_INIT("ns_list", NSList) diff --git a/src/core/ns_logout.c b/src/core/ns_logout.c index c277cb1c3..2afca939e 100644 --- a/src/core/ns_logout.c +++ b/src/core/ns_logout.c @@ -15,104 +15,114 @@ #include "module.h" -#define TO_COLLIDE 0 /* Collide the user with this nick */ -#define TO_RELEASE 1 /* Release a collided nick */ +#define TO_COLLIDE 0 /* Collide the user with this nick */ +#define TO_RELEASE 1 /* Release a collided nick */ -int do_logout(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); + +class CommandNSLogout : public Command +{ + public: + CommandNSLogout() : Command("LOGOUT", 0, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + char *nick = params.size() ? params[0].c_str() : NULL; + char *param = params.size() > 1 ? params[1].c_str() : NULL; + User *u2; + + if (!is_services_admin(u) && nick) + this->OnSyntaxError(u); + else if (!(u2 = (nick ? finduser(nick) : u))) + notice_lang(s_NickServ, u, NICK_X_NOT_IN_USE, nick); + else if (!u2->na) + { + if (nick) + notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + else + notice_lang(s_NickServ, u, NICK_NOT_REGISTERED); + } + else if (u2->na->status & NS_VERBOTEN) + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, u2->na->nick); + else if (!nick && !nick_identified(u)) + notice_lang(s_NickServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + else if (nick && is_services_admin(u2)) + notice_lang(s_NickServ, u, NICK_LOGOUT_SERVICESADMIN, nick); + else + { + if (nick && param && !stricmp(param, "REVALIDATE")) + { + cancel_user(u2); + validate_user(u2); + } + else + u2->na->status &= ~(NS_IDENTIFIED | NS_RECOGNIZED); + + if (ircd->modeonreg) + common_svsmode(u2, ircd->modeonunreg, "1"); + + u2->isSuperAdmin = 0; /* Dont let people logout and remain a SuperAdmin */ + alog("%s: %s!%s@%s logged out nickname %s", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, u2->nick); + + if (nick) + notice_lang(s_NickServ, u, NICK_LOGOUT_X_SUCCEEDED, nick); + else + notice_lang(s_NickServ, u, NICK_LOGOUT_SUCCEEDED); + + /* Stop nick tracking if enabled */ + if (NSNickTracking) + nsStopNickTracking(u2); + + /* Clear any timers again */ + if (u->na->nc->flags & NI_KILLPROTECT) + del_ns_timeout(u->na, TO_COLLIDE); + + /* Send out an event */ + send_event(EVENT_NICK_LOGOUT, 1, u2->nick); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (is_services_admin(u)) + notice_lang(s_NickServ, u, NICK_SERVADMIN_HELP_LOGOUT); + else + notice_lang(s_NickServ, u, NICK_HELP_LOGOUT); + + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "LOGOUT", NICK_LOGOUT_SYNTAX); + } +}; class NSLogout : public Module { public: NSLogout(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("LOGOUT", do_logout, NULL, -1, NICK_HELP_LOGOUT, -1, NICK_SERVADMIN_HELP_LOGOUT, NICK_SERVADMIN_HELP_LOGOUT); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + this->AddCommand(NICKSERV, new CommandNSLogout(), MOD_UNIQUE); this->SetNickHelp(myNickServHelp); } }; - - /** * Add the help response to anopes /ns help output. * @param u The user who is requesting help **/ -void myNickServHelp(User * u) +void myNickServHelp(User *u) { notice_lang(s_NickServ, u, NICK_HELP_CMD_LOGOUT); } -/** - * The /ns logout command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_logout(User * u) -{ - char *nick = strtok(NULL, " "); - char *param = strtok(NULL, " "); - User *u2; - - if (!is_services_admin(u) && nick) { - syntax_error(s_NickServ, u, "LOGOUT", NICK_LOGOUT_SYNTAX); - } else if (!(u2 = (nick ? finduser(nick) : u))) { - notice_lang(s_NickServ, u, NICK_X_NOT_IN_USE, nick); - } else if (!u2->na) { - if (nick) - notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); - else - notice_lang(s_NickServ, u, NICK_NOT_REGISTERED); - } else if (u2->na->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, u2->na->nick); - } else if (!nick && !nick_identified(u)) { - notice_lang(s_NickServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); - } else if (nick && is_services_admin(u2)) { - notice_lang(s_NickServ, u, NICK_LOGOUT_SERVICESADMIN, nick); - } else { - if (nick && param && !stricmp(param, "REVALIDATE")) { - cancel_user(u2); - validate_user(u2); - } else { - u2->na->status &= ~(NS_IDENTIFIED | NS_RECOGNIZED); - } - - if (ircd->modeonreg) { - common_svsmode(u2, ircd->modeonunreg, "1"); - } - - u->isSuperAdmin = 0; /* Dont let people logout and remain a SuperAdmin */ - alog("%s: %s!%s@%s logged out nickname %s", s_NickServ, u->nick, - u->username, u->host, u2->nick); - - if (nick) - notice_lang(s_NickServ, u, NICK_LOGOUT_X_SUCCEEDED, nick); - else - notice_lang(s_NickServ, u, NICK_LOGOUT_SUCCEEDED); - - /* Stop nick tracking if enabled */ - if (NSNickTracking) - /* Shouldn't this be u2? -GD */ - nsStopNickTracking(u); - - /* Clear any timers again */ - if (u->na->nc->flags & NI_KILLPROTECT) { - del_ns_timeout(u->na, TO_COLLIDE); - } - - ircdproto->SendAccountLogout(u2, u2->na->nc); - - /* Send out an event */ - send_event(EVENT_NICK_LOGOUT, 1, u2->nick); - } - return MOD_CONT; -} - MODULE_INIT("ns_logout", NSLogout) diff --git a/src/core/ns_recover.c b/src/core/ns_recover.c index 4cf8c4653..95df90c7b 100644 --- a/src/core/ns_recover.c +++ b/src/core/ns_recover.c @@ -15,11 +15,90 @@ #include "module.h" -Command *c; +void myNickServHelp(User *u); -int do_recover(User * u); -void myNickServHelp(User * u); -int myHelpResonse(User * u); +class CommandNSRecover : public Command +{ + public: + CommandNSRecover() : Command("RECOVER", 1, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + char *nick = params[0].c_str(); + char *pass = params.size() > 1 ? params[1].c_str() : NULL; + NickAlias *na; + User *u2; + + if (!(u2 = finduser(nick))) + notice_lang(s_NickServ, u, NICK_X_NOT_IN_USE, nick); + else if (!(na = u2->na)) + notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + else if (na->status & NS_VERBOTEN) + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); + else if (na->nc->flags & NI_SUSPENDED) + notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); + else if (!stricmp(nick, u->nick)) + notice_lang(s_NickServ, u, NICK_NO_RECOVER_SELF); + else if (pass) + { + int res = enc_check_password(pass, na->nc->pass); + + if (res == 1) + { + char relstr[192]; + + notice_lang(s_NickServ, u2, FORCENICKCHANGE_NOW); + collide(na, 0); + + /* Convert NSReleaseTimeout seconds to string format */ + duration(u2->na, relstr, sizeof(relstr), NSReleaseTimeout); + + notice_lang(s_NickServ, u, NICK_RECOVERED, s_NickServ, nick, relstr); + } + else + { + notice_lang(s_NickServ, u, ACCESS_DENIED); + if (!res) + { + alog("%s: RECOVER: invalid password for %s by %s!%s@%s", s_NickServ, nick, u->nick, u->GetIdent().c_str(), u->host); + bad_password(u); + } + } + } + else + { + if (group_identified(u, na->nc) || (!(na->nc->flags & NI_SECURE) && is_on_access(u, na->nc))) + { + notice_lang(s_NickServ, u2, FORCENICKCHANGE_NOW); + collide(na, 0); + notice_lang(s_NickServ, u, NICK_RECOVERED, s_NickServ, nick); + } + else + notice_lang(s_NickServ, u, ACCESS_DENIED); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + char relstr[192]; + + /* Convert NSReleaseTimeout seconds to string format */ + duration(u->na, relstr, sizeof(relstr), NSReleaseTimeout); + + notice_help(s_NickServ, u, NICK_HELP_RECOVER, relstr); + do_help_limited(s_NickServ, u, this); + + return MOD_CONT; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "RECOVER", NICK_RECOVER_SYNTAX); + } +}; class NSRecover : public Module { @@ -30,99 +109,19 @@ class NSRecover : public Module this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("RECOVER", do_recover, NULL, -1, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - moduleAddHelp(c, myHelpResonse); + this->AddCommand(NICKSERV, new CommandNSRecover(), MOD_UNIQUE); this->SetNickHelp(myNickServHelp); } }; - /** * Add the help response to anopes /ns help output. * @param u The user who is requesting help **/ -void myNickServHelp(User * u) +void myNickServHelp(User *u) { notice_lang(s_NickServ, u, NICK_HELP_CMD_RECOVER); } -/** - * Show the extended help on the RECOVER command. - * @param u The user who is requesting help - **/ -int myHelpResonse(User * u) -{ - char relstr[192]; - - /* Convert NSReleaseTimeout seconds to string format */ - duration(u->na, relstr, sizeof(relstr), NSReleaseTimeout); - - notice_help(s_NickServ, u, NICK_HELP_RECOVER, relstr); - do_help_limited(s_NickServ, u, c); - - return MOD_CONT; -} - -/** - * The /ns recover command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_recover(User * u) -{ - char *nick = strtok(NULL, " "); - char *pass = strtok(NULL, " "); - NickAlias *na; - User *u2; - - if (!nick) { - syntax_error(s_NickServ, u, "RECOVER", NICK_RECOVER_SYNTAX); - } else if (!(u2 = finduser(nick))) { - notice_lang(s_NickServ, u, NICK_X_NOT_IN_USE, nick); - } else if (!(na = u2->na)) { - notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); - } else if (na->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); - } else if (na->nc->flags & NI_SUSPENDED) { - notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); - } else if (stricmp(nick, u->nick) == 0) { - notice_lang(s_NickServ, u, NICK_NO_RECOVER_SELF); - } else if (pass) { - int res = enc_check_password(pass, na->nc->pass); - - if (res == 1) { - char relstr[192]; - - notice_lang(s_NickServ, u2, FORCENICKCHANGE_NOW); - collide(na, 0); - - /* Convert NSReleaseTimeout seconds to string format */ - duration(u2->na, relstr, sizeof(relstr), NSReleaseTimeout); - - notice_lang(s_NickServ, u, NICK_RECOVERED, s_NickServ, nick, relstr); - } else { - notice_lang(s_NickServ, u, ACCESS_DENIED); - if (res == 0) { - alog("%s: RECOVER: invalid password for %s by %s!%s@%s", - s_NickServ, nick, u->nick, u->username, u->host); - bad_password(u); - } - } - } else { - if (group_identified(u, na->nc) - || (!(na->nc->flags & NI_SECURE) && is_on_access(u, na->nc))) { - notice_lang(s_NickServ, u2, FORCENICKCHANGE_NOW); - collide(na, 0); - notice_lang(s_NickServ, u, NICK_RECOVERED, s_NickServ, nick); - } else { - notice_lang(s_NickServ, u, ACCESS_DENIED); - } - } - return MOD_CONT; -} - -/* EOF */ - MODULE_INIT("ns_recover", NSRecover) diff --git a/src/core/ns_register.c b/src/core/ns_register.c index 188c4b626..73ea39f6b 100644 --- a/src/core/ns_register.c +++ b/src/core/ns_register.c @@ -16,384 +16,458 @@ #include "module.h" #include "encrypt.h" -int do_confirm(User * u); -int do_register(User * u); -int do_resend(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); NickRequest *makerequest(const char *nick); NickAlias *makenick(const char *nick); -int do_sendregmail(User * u, NickRequest * nr); -int ns_do_register(User * u); +int do_sendregmail(User *u, NickRequest *nr); -class NSRegister : public Module +class CommandNSConfirm : public Command { - public: - NSRegister(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + CommandResult DoConfirm(User *u, std::vector<std::string> ¶ms) { - Command *c; + NickRequest *nr = NULL; + NickAlias *na = NULL; + char *passcode = params.size() ? params[0].c_str() : NULL; + char *email = NULL; + int forced = 0; + User *utmp = NULL; + char modes[512]; + int len; + + nr = findrequestnick(u->nick); + + if (NSEmailReg) + { + if (!passcode) + { + notice_lang(s_NickServ, u, NICK_CONFIRM_INVALID); + return MOD_CONT; + } - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); + if (!nr) + { + if (is_services_admin(u)) + { + /* If an admin, their nick is obviously already regged, so look at the passcode to get the nick + of the user they are trying to validate, and push that user through regardless of passcode */ + nr = findrequestnick(passcode); + if (nr) + { + utmp = finduser(passcode); + if (utmp) + { + sprintf(passcode, "FORCE_ACTIVATION_DUE_TO_OPER_CONFIRM %s", nr->passcode); + passcode = strtok(passcode, " "); + notice_lang(s_NickServ, u, NICK_FORCE_REG, nr->nick); + do_confirm(utmp); + return MOD_CONT; + } + else + { + passcode = sstrdup(nr->passcode); + forced = 1; + } + } + else + { + notice_lang(s_NickServ, u, NICK_CONFIRM_NOT_FOUND, s_NickServ); + return MOD_CONT; + } + } + else + { + notice_lang(s_NickServ, u, NICK_CONFIRM_NOT_FOUND, s_NickServ); + return MOD_CONT; + } + } - c = createCommand("REGISTER", do_register, NULL, NICK_HELP_REGISTER, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + if (stricmp(nr->passcode, passcode)) + { + notice_lang(s_NickServ, u, NICK_CONFIRM_INVALID); + if (forced) + delete [] passcode; + return MOD_CONT; + } + } - c = createCommand("CONFIRM", do_confirm, NULL, NICK_HELP_CONFIRM, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + if (!nr) + { + notice_lang(s_NickServ, u, NICK_REGISTRATION_FAILED); + if (forced) + delete [] passcode; + return MOD_CONT; + } - c = createCommand("RESEND", do_resend, NULL, NICK_HELP_RESEND, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + if (nr->email) + email = sstrdup(nr->email); + na = makenick(nr->nick); + + if (na) + { + int i; + char tsbuf[16]; + char tmp_pass[PASSMAX]; + + memcpy(na->nc->pass, nr->password, PASSMAX); + na->status = static_cast<int16>(NS_IDENTIFIED | NS_RECOGNIZED); + /* na->nc->flags |= NI_ENCRYPTEDPW; */ + + na->nc->flags |= NSDefFlags; + for (i = 0; i < RootNumber; ++i) + { + if (!stricmp(ServicesRoots[i], nr->nick)) + { + na->nc->flags |= NI_SERVICES_ROOT; + break; + } + } + na->nc->memos.memomax = MSMaxMemos; - this->SetNickHelp(myNickServHelp); - } -}; - + if (forced == 1) + { + na->last_usermask = sstrdup("*@*"); + na->last_realname = sstrdup("unknown"); + } + else + { + na->last_usermask = new char[u->GetIdent().length() + u->GetDisplayedHost().length() + 2]; + sprintf(na->last_usermask, "%s@%s", u->GetIdent().c_str(), u->GetDisplayedHost().c_str()); + na->last_realname = sstrdup(u->realname); + } + na->time_registered = na->last_seen = time(NULL); + if (NSAddAccessOnReg) + { + na->nc->accesscount = 1; + na->nc->access = static_cast<char **>(scalloc(sizeof(char *), 1)); + na->nc->access[0] = create_mask(u); + } + else + { + na->nc->accesscount = 0; + na->nc->access = NULL; + } + na->nc->language = NSDefLanguage; + if (email) + na->nc->email = sstrdup(email); + if (forced != 1) + { + u->na = na; + na->u = u; + alog("%s: '%s' registered by %s@%s (e-mail: %s)", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, email ? email : "none"); + if (NSAddAccessOnReg) + notice_lang(s_NickServ, u, NICK_REGISTERED, u->nick, na->nc->access[0]); + else + notice_lang(s_NickServ, u, NICK_REGISTERED_NO_MASK, u->nick); + send_event(EVENT_NICK_REGISTERED, 1, u->nick); + + if (enc_decrypt(na->nc->pass, tmp_pass, PASSMAX - 1) == 1) + notice_lang(s_NickServ, u, NICK_PASSWORD_IS, tmp_pass); + + u->lastnickreg = time(NULL); + if (ircd->modeonreg) + { + len = strlen(ircd->modeonreg); + strncpy(modes, ircd->modeonreg, 512); + if (ircd->rootmodeonid && is_services_root(u)) + strncat(modes, ircd->rootmodeonid, 512 - len); + else if (ircd->adminmodeonid && is_services_admin(u)) + strncat(modes, ircd->adminmodeonid, 512 - len); + else if (ircd->opermodeonid && is_services_oper(u)) + strncat(modes, ircd->opermodeonid, 512 - len); + + if (ircd->tsonmode) + { + snprintf(tsbuf, sizeof(tsbuf), "%lu", static_cast<unsigned long>(u->timestamp)); + common_svsmode(u, modes, tsbuf); + } + else + common_svsmode(u, modes, NULL); + } + } + else + notice_lang(s_NickServ, u, NICK_FORCE_REG, nr->nick); + delnickrequest(nr); /* remove the nick request */ + } + else + { + alog("%s: makenick(%s) failed", s_NickServ, u->nick); + notice_lang(s_NickServ, u, NICK_REGISTRATION_FAILED); + } + /* Enable nick tracking if enabled */ + if (NSNickTracking) + nsStartNickTracking(u); -/** - * Add the help response to anopes /ns help output. - * @param u The user who is requesting help - **/ -void myNickServHelp(User * u) -{ - notice_lang(s_NickServ, u, NICK_HELP_CMD_REGISTER); - if (NSEmailReg) { - notice_lang(s_NickServ, u, NICK_HELP_CMD_CONFIRM); - notice_lang(s_NickServ, u, NICK_HELP_CMD_RESEND); - } -} + if (forced) + delete [] passcode; + if (email) + delete [] email; -/** - * The /ns register command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_register(User * u) -{ - NickRequest *nr = NULL, *anr = NULL; - NickCore *nc = NULL; - int prefixlen = strlen(NSGuestNickPrefix); - int nicklen = strlen(u->nick); - char *pass = strtok(NULL, " "); - char *email = strtok(NULL, " "); - char passcode[11]; - int idx, min = 1, max = 62, i = 0; - int chars[] = - { ' ', 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', - 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', - 'z', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', - 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', - 'Z', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9' - }; - - if (readonly) { - notice_lang(s_NickServ, u, NICK_REGISTRATION_DISABLED); return MOD_CONT; } - - if (checkDefCon(DEFCON_NO_NEW_NICKS)) { - notice_lang(s_NickServ, u, OPER_DEFCON_DENIED); - return MOD_CONT; + public: + CommandNSConfirm() : Command("CONFIRM", 0, 1) + { } - if (!is_oper(u) && NickRegDelay - && ((time(NULL) - u->my_signon) < NickRegDelay)) { - notice_lang(s_NickServ, u, NICK_REG_DELAY, NickRegDelay); - return MOD_CONT; + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + return this->DoConfirm(u, params); } - if ((anr = findrequestnick(u->nick))) { - notice_lang(s_NickServ, u, NICK_REQUESTED); - return MOD_CONT; - } - /* Prevent "Guest" nicks from being registered. -TheShadow */ - - /* Guest nick can now have a series of between 1 and 7 digits. - * --lara - */ - if (nicklen <= prefixlen + 7 && nicklen >= prefixlen + 1 && - stristr(u->nick, NSGuestNickPrefix) == u->nick && - strspn(u->nick + prefixlen, "1234567890") == nicklen - prefixlen) { - notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, u->nick); - return MOD_CONT; + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_NickServ, u, NICK_HELP_CONFIRM); + return true; } +}; - if (!ircdproto->IsNickValid(u->nick)) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, u->nick); - return MOD_CONT; +class CommandNSRegister : public CommandNSConfirm +{ + public: + CommandNSRegister() : Command("REGISTER", 1, 2) + { } - if (RestrictOperNicks) { - for (i = 0; i < RootNumber; i++) { - if (stristr(u->nick, ServicesRoots[i]) && !is_oper(u)) { - notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, - u->nick); - return MOD_CONT; - } - } - for (i = 0; i < servadmins.count && (nc = static_cast<NickCore *>(servadmins.list[i])); i++) { - if (stristr(u->nick, nc->display) && !is_oper(u)) { - notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, - u->nick); - return MOD_CONT; - } - } - for (i = 0; i < servopers.count && (nc = static_cast<NickCore *>(servopers.list[i])); i++) { - if (stristr(u->nick, nc->display) && !is_oper(u)) { - notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, - u->nick); - return MOD_CONT; - } + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + NickRequest *nr = NULL, *anr = NULL; + NickCore *nc = NULL; + int prefixlen = strlen(NSGuestNickPrefix); + int nicklen = strlen(u->nick); + char *pass = params[0].c_str(); + char *email = params.size() > 1 ? params[1].c_str() : NULL; + char passcode[11]; + int idx, min = 1, max = 62, i = 0; + int chars[] = + { ' ', 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', + 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', + 'z', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', + 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', + 'Z', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9' + }; + + if (readonly) + { + notice_lang(s_NickServ, u, NICK_REGISTRATION_DISABLED); + return MOD_CONT; } - } - if (!pass) { - if (NSForceEmail) { - syntax_error(s_NickServ, u, "REGISTER", - NICK_REGISTER_SYNTAX_EMAIL); - } else { - syntax_error(s_NickServ, u, "REGISTER", NICK_REGISTER_SYNTAX); - } - } else if (NSForceEmail && !email) { - syntax_error(s_NickServ, u, "REGISTER", - NICK_REGISTER_SYNTAX_EMAIL); - } else if (time(NULL) < u->lastnickreg + NSRegDelay) { - notice_lang(s_NickServ, u, NICK_REG_PLEASE_WAIT, NSRegDelay); - } else if (u->na) { /* i.e. there's already such a nick regged */ - if (u->na->status & NS_VERBOTEN) { - alog("%s: %s@%s tried to register FORBIDden nick %s", - s_NickServ, u->username, u->host, u->nick); - notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, u->nick); - } else { - notice_lang(s_NickServ, u, NICK_ALREADY_REGISTERED, u->nick); - } - } else if (stricmp(u->nick, pass) == 0 - || (StrictPasswords && strlen(pass) < 5)) { - notice_lang(s_NickServ, u, MORE_OBSCURE_PASSWORD); - } else if (enc_encrypt_check_len(strlen(pass), PASSMAX - 1)) { - notice_lang(s_NickServ, u, PASSWORD_TOO_LONG); - } else if (email && !MailValidate(email)) { - notice_lang(s_NickServ, u, MAIL_X_INVALID, email); - } else { - for (idx = 0; idx < 9; idx++) { - passcode[idx] = - chars[(1 + - static_cast<int>((static_cast<float>(max - min)) * getrandom16() / - (65535 + 1.0)) + min)]; - } passcode[idx] = '\0'; - nr = makerequest(u->nick); - nr->passcode = sstrdup(passcode); - strscpy(nr->password, pass, PASSMAX); - memset(pass, 0, strlen(pass)); - /* We are paranoid about keeping a plain text pass in memory, yet we would write - * it to a database.. - Viper */ - enc_encrypt_in_place(nr->password, PASSMAX); - if (email) { - nr->email = sstrdup(email); - } - nr->requested = time(NULL); - if (NSEmailReg) { - if (do_sendregmail(u, nr) == 0) { - notice_lang(s_NickServ, u, NICK_ENTER_REG_CODE, email, - s_NickServ); - alog("%s: sent registration verification code to %s", - s_NickServ, nr->email); - } else { - alog("%s: Unable to send registration verification mail", - s_NickServ); - notice_lang(s_NickServ, u, NICK_REG_UNABLE); - delnickrequest(nr); /* Delete the NickRequest if we couldnt send the mail */ - return MOD_CONT; - } - } else { - do_confirm(u); + if (checkDefCon(DEFCON_NO_NEW_NICKS)) + { + notice_lang(s_NickServ, u, OPER_DEFCON_DENIED); + return MOD_CONT; } - } - return MOD_CONT; -} - -/*************************************************************************/ - -int ns_do_register(User * u) -{ - return do_register(u); -} - + if (!is_oper(u) && NickRegDelay && time(NULL) - u->my_signon < NickRegDelay) + { + notice_lang(s_NickServ, u, NICK_REG_DELAY, NickRegDelay); + return MOD_CONT; + } -int do_confirm(User * u) -{ + if ((anr = findrequestnick(u->nick))) + { + notice_lang(s_NickServ, u, NICK_REQUESTED); + return MOD_CONT; + } - NickRequest *nr = NULL; - NickAlias *na = NULL; - char *passcode = strtok(NULL, " "); - char *email = NULL; - int forced = 0; - User *utmp = NULL; - char modes[512]; - int len; + /* Prevent "Guest" nicks from being registered. -TheShadow */ - nr = findrequestnick(u->nick); + /* Guest nick can now have a series of between 1 and 7 digits. + * --lara + */ + if (nicklen <= prefixlen + 7 && nicklen >= prefixlen + 1 && stristr(u->nick, NSGuestNickPrefix) == u->nick && strspn(u->nick + prefixlen, "1234567890") == nicklen - prefixlen) + { + notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, u->nick); + return MOD_CONT; + } - if (NSEmailReg) { - if (!passcode) { - notice_lang(s_NickServ, u, NICK_CONFIRM_INVALID); + if (!ircdproto->IsNickValid(u->nick)) + { + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, u->nick); return MOD_CONT; } - if (!nr) { - if (is_services_admin(u)) { -/* If an admin, their nick is obviously already regged, so look at the passcode to get the nick - of the user they are trying to validate, and push that user through regardless of passcode */ - nr = findrequestnick(passcode); - if (nr) { - utmp = finduser(passcode); - if (utmp) { - sprintf(passcode, - "FORCE_ACTIVATION_DUE_TO_OPER_CONFIRM %s", - nr->passcode); - passcode = strtok(passcode, " "); - notice_lang(s_NickServ, u, NICK_FORCE_REG, - nr->nick); - do_confirm(utmp); - return MOD_CONT; - } else { - passcode = sstrdup(nr->passcode); - forced = 1; - } - } else { - notice_lang(s_NickServ, u, NICK_CONFIRM_NOT_FOUND, - s_NickServ); + if (RestrictOperNicks) + { + for (i = 0; i < RootNumber; ++i) + { + if (stristr(u->nick, ServicesRoots[i]) && !is_oper(u)) + { + notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, u->nick); + return MOD_CONT; + } + } + for (i = 0; i < servadmins.count && (nc = static_cast<NickCore *>(servadmins.list[i])); ++i) + { + if (stristr(u->nick, nc->display) && !is_oper(u)) + { + notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, u->nick); + return MOD_CONT; + } + } + for (i = 0; i < servopers.count && (nc = static_cast<NickCore *>(servopers.list[i])); ++i) + { + if (stristr(u->nick, nc->display) && !is_oper(u)) + { + notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, u->nick); return MOD_CONT; } - } else { - notice_lang(s_NickServ, u, NICK_CONFIRM_NOT_FOUND, - s_NickServ); - return MOD_CONT; } } - if (stricmp(nr->passcode, passcode) != 0) { - notice_lang(s_NickServ, u, NICK_CONFIRM_INVALID); - if (forced) - delete [] passcode; - return MOD_CONT; + if (NSForceEmail && !email) + this->OnSyntaxError(u); + else if (time(NULL) < u->lastnickreg + NSRegDelay) + notice_lang(s_NickServ, u, NICK_REG_PLEASE_WAIT, NSRegDelay); + else if (u->na) /* i.e. there's already such a nick regged */ + { + if (u->na->status & NS_VERBOTEN) + { + alog("%s: %s@%s tried to register FORBIDden nick %s", s_NickServ, u->GetIdent().c_str(), u->host, u->nick); + notice_lang(s_NickServ, u, NICK_CANNOT_BE_REGISTERED, u->nick); + } + else + notice_lang(s_NickServ, u, NICK_ALREADY_REGISTERED, u->nick); + } + else if (!stricmp(u->nick, pass) || (StrictPasswords && strlen(pass) < 5)) + notice_lang(s_NickServ, u, MORE_OBSCURE_PASSWORD); + else if (enc_encrypt_check_len(strlen(pass), PASSMAX - 1)) + notice_lang(s_NickServ, u, PASSWORD_TOO_LONG); + else if (email && !MailValidate(email)) + notice_lang(s_NickServ, u, MAIL_X_INVALID, email); + else + { + for (idx = 0; idx < 9; ++idx) + passcode[idx] = chars[1 + static_cast<int>((static_cast<float>(max - min)) * getrandom16() / 65536.0) + min]; + passcode[idx] = '\0'; + nr = makerequest(u->nick); + nr->passcode = sstrdup(passcode); + strscpy(nr->password, pass, PASSMAX); + memset(pass, 0, strlen(pass)); + /* We are paranoid about keeping a plain text pass in memory, yet we would write + * it to a database.. - Viper */ + enc_encrypt_in_place(nr->password, PASSMAX); + if (email) + nr->email = sstrdup(email); + nr->requested = time(NULL); + if (NSEmailReg) + { + if (!do_sendregmail(u, nr)) + { + notice_lang(s_NickServ, u, NICK_ENTER_REG_CODE, email, s_NickServ); + alog("%s: sent registration verification code to %s", s_NickServ, nr->email); + } + else + { + alog("%s: Unable to send registration verification mail", s_NickServ); + notice_lang(s_NickServ, u, NICK_REG_UNABLE); + delnickrequest(nr); /* Delete the NickRequest if we couldnt send the mail */ + return MOD_CONT; + } + } + else + { + std::vector<std::string> empty_params; + return this->DoConfirm(u, empty_params); + } } - } - if (!nr) { - notice_lang(s_NickServ, u, NICK_REGISTRATION_FAILED); - if (forced) - delete [] passcode; return MOD_CONT; } - if (nr->email) { - email = sstrdup(nr->email); + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_NickServ, u, NICK_HELP_REGISTER); + return true; } - na = makenick(nr->nick); - - if (na) { - int i; - char tsbuf[16]; - char tmp_pass[PASSMAX]; - - memcpy(na->nc->pass, nr->password, PASSMAX); - na->status = static_cast<int16>(NS_IDENTIFIED | NS_RECOGNIZED); -/* na->nc->flags |= NI_ENCRYPTEDPW; */ - - na->nc->flags |= NSDefFlags; - for (i = 0; i < RootNumber; i++) { - if (!stricmp(ServicesRoots[i], nr->nick)) { - na->nc->flags |= NI_SERVICES_ROOT; - break; - } - } - na->nc->memos.memomax = MSMaxMemos; + void OnSyntaxError(User *u) + { + if (NSForceEmail) + syntax_error(s_NickServ, u, "REGISTER", NICK_REGISTER_SYNTAX_EMAIL); + else + syntax_error(s_NickServ, u, "REGISTER", NICK_REGISTER_SYNTAX); + } +}; - if (forced == 1) { - na->last_usermask = sstrdup("*@*"); - na->last_realname = sstrdup("unknown"); - } else { - na->last_usermask = new char[strlen(common_get_vident(u)) + strlen(common_get_vhost(u)) + 2]; - sprintf(na->last_usermask, "%s@%s", common_get_vident(u), - common_get_vhost(u)); - na->last_realname = sstrdup(u->realname); - } - na->time_registered = na->last_seen = time(NULL); - if (NSAddAccessOnReg) { - na->nc->accesscount = 1; - na->nc->access = static_cast<char **>(scalloc(sizeof(char *), 1)); - na->nc->access[0] = create_mask(u); - } else { - na->nc->accesscount = 0; - na->nc->access = NULL; - } - na->nc->language = NSDefLanguage; - if (email) - na->nc->email = sstrdup(email); - if (forced != 1) { - u->na = na; - na->u = u; - alog("%s: '%s' registered by %s@%s (e-mail: %s)", s_NickServ, - u->nick, u->username, u->host, (email ? email : "none")); - if (NSAddAccessOnReg) - notice_lang(s_NickServ, u, NICK_REGISTERED, u->nick, - na->nc->access[0]); - else - notice_lang(s_NickServ, u, NICK_REGISTERED_NO_MASK, - u->nick); - ircdproto->SendAccountLogin(u, na->nc); - send_event(EVENT_NICK_REGISTERED, 1, u->nick); - - if(enc_decrypt(na->nc->pass, tmp_pass, PASSMAX - 1)==1) - notice_lang(s_NickServ, u, NICK_PASSWORD_IS, tmp_pass); - - u->lastnickreg = time(NULL); - if (ircd->modeonreg) { - len = strlen(ircd->modeonreg); - strncpy(modes,ircd->modeonreg,512); - if(ircd->rootmodeonid && is_services_root(u)) { - strncat(modes,ircd->rootmodeonid,512-len); - } else if(ircd->adminmodeonid && is_services_admin(u)) { - strncat(modes,ircd->adminmodeonid,512-len); - } else if(ircd->opermodeonid && is_services_oper(u)) { - strncat(modes,ircd->opermodeonid,512-len); - } +class CommandNSResend : public Command +{ + public: + CommandNSResend() : Command("RESEND", 0, 0) + { + } - if (ircd->tsonmode) { - snprintf(tsbuf, sizeof(tsbuf), "%lu", - static_cast<unsigned long>(u->timestamp)); - common_svsmode(u, modes, tsbuf); - } else { - common_svsmode(u, modes, NULL); + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + NickRequest *nr = NULL; + if (NSEmailReg) + { + if ((nr = findrequestnick(u->nick))) + { + if (time(NULL) < nr->lastmail + NSResendDelay) + { + notice_lang(s_NickServ, u, MAIL_LATER); + return MOD_CONT; + } + if (!do_sendregmail(u, nr)) + { + nr->lastmail = time(NULL); + notice_lang(s_NickServ, u, NICK_REG_RESENT, nr->email); + alog("%s: re-sent registration verification code for %s to %s", s_NickServ, nr->nick, nr->email); + } + else + { + alog("%s: Unable to re-send registration verification mail for %s", s_NickServ, nr->nick); + return MOD_CONT; } } - - } else { - notice_lang(s_NickServ, u, NICK_FORCE_REG, nr->nick); } - delnickrequest(nr); /* remove the nick request */ - } else { - alog("%s: makenick(%s) failed", s_NickServ, u->nick); - notice_lang(s_NickServ, u, NICK_REGISTRATION_FAILED); + return MOD_CONT; } - /* Enable nick tracking if enabled */ - if (NSNickTracking) - nsStartNickTracking(u); + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_NickServ, u, NICK_HELP_RESEND); + return true; + } +}; - if (forced) - delete [] passcode; - if (email) - delete [] email; +class NSRegister : public Module +{ + public: + NSRegister(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); - return MOD_CONT; + this->AddCommand(NICKSERV, new CommandNSRegister(), MOD_UNIQUE); + this->AddCommand(NICKSERV, new CommandNSConfirm(), MOD_UNIQUE); + this->AddCommand(NICKSERV, new CommandNSResend(), MOD_UNIQUE); + + this->SetNickHelp(myNickServHelp); + } +}; + +/** + * Add the help response to anopes /ns help output. + * @param u The user who is requesting help + **/ +void myNickServHelp(User *u) +{ + notice_lang(s_NickServ, u, NICK_HELP_CMD_REGISTER); + if (NSEmailReg) + { + notice_lang(s_NickServ, u, NICK_HELP_CMD_CONFIRM); + notice_lang(s_NickServ, u, NICK_HELP_CMD_RESEND); + } } +/*************************************************************************/ + NickRequest *makerequest(const char *nick) { NickRequest *nr; @@ -406,7 +480,6 @@ NickRequest *makerequest(const char *nick) } /* Creates a full new nick (alias + core) in NickServ database. */ - NickAlias *makenick(const char *nick) { NickAlias *na; @@ -428,61 +501,31 @@ NickAlias *makenick(const char *nick) return na; } -/* Register a nick. */ - -int do_resend(User * u) -{ - NickRequest *nr = NULL; - if (NSEmailReg) { - if ((nr = findrequestnick(u->nick))) { - if (time(NULL) < nr->lastmail + NSResendDelay) { - notice_lang(s_NickServ, u, MAIL_LATER); - return MOD_CONT; - } - if (do_sendregmail(u, nr) == 0) { - nr->lastmail = time(NULL); - notice_lang(s_NickServ, u, NICK_REG_RESENT, nr->email); - alog("%s: re-sent registration verification code for %s to %s", s_NickServ, nr->nick, nr->email); - } else { - alog("%s: Unable to re-send registration verification mail for %s", s_NickServ, nr->nick); - return MOD_CONT; - } - } - } - return MOD_CONT; -} - -int do_sendregmail(User * u, NickRequest * nr) +int do_sendregmail(User *u, NickRequest *nr) { MailInfo *mail = NULL; char buf[BUFSIZE]; - if (!(nr || u)) { + if (!nr && !u) return -1; - } - snprintf(buf, sizeof(buf), getstring2(NULL, NICK_REG_MAIL_SUBJECT), - nr->nick); + snprintf(buf, sizeof(buf), getstring2(NULL, NICK_REG_MAIL_SUBJECT), nr->nick); mail = MailRegBegin(u, nr, buf, s_NickServ); - if (!mail) { + if (!mail) return -1; - } fprintf(mail->pipe, getstring2(NULL, NICK_REG_MAIL_HEAD)); fprintf(mail->pipe, "\n\n"); fprintf(mail->pipe, getstring2(NULL, NICK_REG_MAIL_LINE_1), nr->nick); fprintf(mail->pipe, "\n\n"); - fprintf(mail->pipe, getstring2(NULL, NICK_REG_MAIL_LINE_2), s_NickServ, - nr->passcode); + fprintf(mail->pipe, getstring2(NULL, NICK_REG_MAIL_LINE_2), s_NickServ, nr->passcode); fprintf(mail->pipe, "\n\n"); fprintf(mail->pipe, getstring2(NULL, NICK_REG_MAIL_LINE_3)); fprintf(mail->pipe, "\n\n"); fprintf(mail->pipe, getstring2(NULL, NICK_REG_MAIL_LINE_4)); fprintf(mail->pipe, "\n\n"); - fprintf(mail->pipe, getstring2(NULL, NICK_REG_MAIL_LINE_5), - NetworkName); + fprintf(mail->pipe, getstring2(NULL, NICK_REG_MAIL_LINE_5), NetworkName); fprintf(mail->pipe, "\n.\n"); MailEnd(mail); return 0; } - MODULE_INIT("ns_register", NSRegister) diff --git a/src/core/ns_release.c b/src/core/ns_release.c index aa7dfec3b..5ac5861a2 100644 --- a/src/core/ns_release.c +++ b/src/core/ns_release.c @@ -15,11 +15,78 @@ #include "module.h" -Command *c; +void myNickServHelp(User *u); -int do_release(User * u); -void myNickServHelp(User * u); -int myHelpResonse(User * u); +class CommandNSRelease : public Command +{ + public: + CommandNSRelease() : Command("RELEASE", 1, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[0].c_str(); + const char *pass = params.size() > 1 ? params[1].c_str() : NULL; + NickAlias *na; + + if (!(na = findnick(nick))) + notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + else if (na->status & NS_VERBOTEN) + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); + else if (na->nc->flags & NI_SUSPENDED) + notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); + else if (!(na->status & NS_KILL_HELD)) + notice_lang(s_NickServ, u, NICK_RELEASE_NOT_HELD, nick); + else if (pass) + { + int res = enc_check_password(pass, na->nc->pass); + if (res == 1) + { + release(na, 0); + notice_lang(s_NickServ, u, NICK_RELEASED); + } + else + { + notice_lang(s_NickServ, u, ACCESS_DENIED); + if (!res) + { + alog("%s: RELEASE: invalid password for %s by %s!%s@%s", s_NickServ, nick, u->nick, u->GetIdent().c_str(), u->host); + bad_password(u); + } + } + } + else + { + if (group_identified(u, na->nc) || (!(na->nc->flags & NI_SECURE) && is_on_access(u, na->nc))) + { + release(na, 0); + notice_lang(s_NickServ, u, NICK_RELEASED); + } + else + notice_lang(s_NickServ, u, ACCESS_DENIED); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + char relstr[192]; + + /* Convert NSReleaseTimeout seconds to string format */ + duration(u->na, relstr, sizeof(relstr), NSReleaseTimeout); + + notice_help(s_NickServ, u, NICK_HELP_RELEASE, relstr); + do_help_limited(s_NickServ, u, this); + + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "RELEASE", NICK_RELEASE_SYNTAX); + } +}; class NSRelease : public Module { @@ -30,89 +97,19 @@ class NSRelease : public Module this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("RELEASE", do_release, NULL, -1, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - moduleAddHelp(c, myHelpResonse); + this->AddCommand(NICKSERV, new CommandNSRelease(), MOD_UNIQUE); this->SetNickHelp(myNickServHelp); } }; - - - /** * Add the help response to anopes /ns help output. * @param u The user who is requesting help **/ -void myNickServHelp(User * u) +void myNickServHelp(User *u) { notice_lang(s_NickServ, u, NICK_HELP_CMD_RELEASE); } -/** - * Show the extended help on the RELEASE command. - * @param u The user who is requesting help - **/ -int myHelpResonse(User * u) -{ - char relstr[192]; - - /* Convert NSReleaseTimeout seconds to string format */ - duration(u->na, relstr, sizeof(relstr), NSReleaseTimeout); - - notice_help(s_NickServ, u, NICK_HELP_RELEASE, relstr); - do_help_limited(s_NickServ, u, c); - - return MOD_CONT; -} - -/** - * The /ns release command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_release(User * u) -{ - char *nick = strtok(NULL, " "); - char *pass = strtok(NULL, " "); - NickAlias *na; - - if (!nick) { - syntax_error(s_NickServ, u, "RELEASE", NICK_RELEASE_SYNTAX); - } else if (!(na = findnick(nick))) { - notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); - } else if (na->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); - } else if (na->nc->flags & NI_SUSPENDED) { - notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); - } else if (!(na->status & NS_KILL_HELD)) { - notice_lang(s_NickServ, u, NICK_RELEASE_NOT_HELD, nick); - } else if (pass) { - int res = enc_check_password(pass, na->nc->pass); - if (res == 1) { - release(na, 0); - notice_lang(s_NickServ, u, NICK_RELEASED); - } else { - notice_lang(s_NickServ, u, ACCESS_DENIED); - if (res == 0) { - alog("%s: RELEASE: invalid password for %s by %s!%s@%s", - s_NickServ, nick, u->nick, u->username, u->host); - bad_password(u); - } - } - } else { - if (group_identified(u, na->nc) - || (!(na->nc->flags & NI_SECURE) && is_on_access(u, na->nc))) { - release(na, 0); - notice_lang(s_NickServ, u, NICK_RELEASED); - } else { - notice_lang(s_NickServ, u, ACCESS_DENIED); - } - } - return MOD_CONT; -} - -/* EOF */ - MODULE_INIT("ns_release", NSRelease) diff --git a/src/core/ns_saset.c b/src/core/ns_saset.c index 6938b5545..0747c658c 100644 --- a/src/core/ns_saset.c +++ b/src/core/ns_saset.c @@ -16,491 +16,583 @@ #include "module.h" #include "encrypt.h" -int do_saset(User * u); -int do_saset_display(User * u, NickCore * nc, char *param); -int do_saset_password(User * u, NickCore * nc, char *param); -int do_saset_url(User * u, NickCore * nc, char *param); -int do_saset_email(User * u, NickCore * nc, char *param); -int do_saset_greet(User * u, NickCore * nc, char *param); -int do_saset_icq(User * u, NickCore * nc, char *param); -int do_saset_kill(User * u, NickCore * nc, char *param); -int do_saset_secure(User * u, NickCore * nc, char *param); -int do_saset_private(User * u, NickCore * nc, char *param); -int do_saset_msg(User * u, NickCore * nc, char *param); -int do_saset_hide(User * u, NickCore * nc, char *param); -int do_saset_noexpire(User * u, NickAlias * nc, char *param); -int do_saset_autoop(User * u, NickCore * nc, char *param); -int do_saset_language(User * u, NickCore * nc, char *param); -void myNickServHelp(User * u); +void myNickServHelp(User *u); -class NSSASet : public Module +class CommandNSSASet : public Command { - public: - NSSASet(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + CommandResult DoSetDisplay(User *u, std::vector<std::string> ¶ms, NickCore *nc) { - Command *c; + const char *param = params.size() > 2 ? params[2].c_str() : NULL; + int i; + NickAlias *na; + + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } - this->SetAuthor("Anope"); - this->SetVersion("$Id: ns_set.c 850 2005-08-07 14:52:04Z geniusdex $"); - this->SetType(CORE); + /* First check whether param is a valid nick of the group */ + for (i = 0; i < nc->aliases.count; ++i) + { + na = static_cast<NickAlias *>(nc->aliases.list[i]); + if (!stricmp(na->nick, param)) + { + param = na->nick; /* Because case may differ */ + break; + } + } + + if (i == nc->aliases.count) + { + notice_lang(s_NickServ, u, NICK_SASET_DISPLAY_INVALID, nc->display); + return MOD_CONT; + } - c = createCommand("SASET", do_saset, is_services_oper, -1, -1, -1, NICK_HELP_SASET, NICK_HELP_SASET); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SASET DISPLAY", NULL, is_services_oper, NICK_HELP_SASET_DISPLAY, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SASET PASSWORD", NULL, is_services_oper, NICK_HELP_SASET_PASSWORD, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SASET URL", NULL, is_services_oper, NICK_HELP_SASET_URL, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SASET EMAIL", NULL, is_services_oper, NICK_HELP_SASET_EMAIL, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SASET ICQ", NULL, is_services_oper, NICK_HELP_SASET_ICQ, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SASET GREET", NULL, is_services_oper, NICK_HELP_SASET_GREET, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SASET KILL", NULL, is_services_oper, NICK_HELP_SASET_KILL, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SASET SECURE", NULL, is_services_oper, NICK_HELP_SASET_SECURE, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SASET PRIVATE", NULL, is_services_oper, NICK_HELP_SASET_PRIVATE, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SASET MSG", NULL, is_services_oper, NICK_HELP_SASET_MSG, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SASET HIDE", NULL, is_services_oper, NICK_HELP_SASET_HIDE, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SASET NOEXPIRE", NULL, is_services_oper, -1, -1, -1, NICK_HELP_SASET_NOEXPIRE, NICK_HELP_SASET_NOEXPIRE); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SASET AUTOOP", NULL, is_services_oper, -1, -1, -1, NICK_HELP_SASET_AUTOOP, NICK_HELP_SASET_AUTOOP); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SASET LANGUAGE", NULL, is_services_oper, -1, -1, -1, -1, NICK_HELP_SASET_LANGUAGE); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + change_core_display(nc, param); + notice_lang(s_NickServ, u, NICK_SASET_DISPLAY_CHANGED, nc->display); - this->SetNickHelp(myNickServHelp); + /* Enable nick tracking if enabled */ + if (NSNickTracking) + nsStartNickTracking(u); + + return MOD_CONT; } -}; + CommandResult DoSetPassword(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 2 ? params[2].c_str() : NULL; + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } -/** - * Add the help response to anopes /ns help output. - * @param u The user who is requesting help - **/ -void myNickServHelp(User * u) -{ - if (is_services_oper(u)) - notice_lang(s_NickServ, u, NICK_HELP_CMD_SASET); -} + int len = strlen(param); + char tmp_pass[PASSMAX]; -/** - * The /ns saset command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_saset(User * u) -{ - char *nick = strtok(NULL, " "); - char *cmd = strtok(NULL, " "); - char *param = strtok(NULL, " "); + if (NSSecureAdmins && u->na->nc != nc && nick_is_services_admin(nc) && !is_services_root(u)) + { + notice_lang(s_NickServ, u, PERMISSION_DENIED); + return MOD_CONT; + } + else if (!stricmp(nc->display, param) || (StrictPasswords && len < 5)) + { + notice_lang(s_NickServ, u, MORE_OBSCURE_PASSWORD); + return MOD_CONT; + } + else if (enc_encrypt_check_len(len, PASSMAX - 1)) + { + notice_lang(s_NickServ, u, PASSWORD_TOO_LONG); + return MOD_CONT; + } - NickAlias *na; + if (enc_encrypt(param, len, nc->pass, PASSMAX - 1) < 0) + { + params[2].clear(); + alog("%s: Failed to encrypt password for %s (set)", s_NickServ, nc->display); + notice_lang(s_NickServ, u, NICK_SASET_PASSWORD_FAILED, nc->display); + return MOD_CONT; + } + params[2].clear(); - if (readonly) { - notice_lang(s_NickServ, u, NICK_SASET_DISABLED); - return MOD_CONT; - } - if (!nick) { - syntax_error(s_NickServ, u, "SASET", NICK_SASET_SYNTAX); + if (enc_decrypt(nc->pass, tmp_pass, PASSMAX - 1) == 1) + notice_lang(s_NickServ, u, NICK_SASET_PASSWORD_CHANGED_TO, nc->display, tmp_pass); + else + notice_lang(s_NickServ, u, NICK_SASET_PASSWORD_CHANGED, nc->display); + + alog("%s: %s!%s@%s used SASET PASSWORD on %s (e-mail: %s)", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, nc->display, nc->email ? nc->email : "none"); + if (WallSetpass) + ircdproto->SendGlobops(s_NickServ, "\2%s\2 used SASET PASSWORD on \2%s\2", u->nick, nc->display); return MOD_CONT; } - if (!(na = findnick(nick))) { - notice_lang(s_NickServ, u, NICK_SASET_BAD_NICK, nick); + + CommandResult DoSetUrl(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 2 ? params[2].c_str() : NULL; + + if (nc->url) + delete [] nc->url; + + if (param) + { + nc->url = sstrdup(param); + notice_lang(s_NickServ, u, NICK_SASET_URL_CHANGED, nc->display, param); + } + else + { + nc->url = NULL; + notice_lang(s_NickServ, u, NICK_SASET_URL_UNSET, nc->display); + } return MOD_CONT; } - if (!param - && (!cmd - || (stricmp(cmd, "URL") != 0 && stricmp(cmd, "EMAIL") != 0 - && stricmp(cmd, "GREET") != 0 - && stricmp(cmd, "ICQ") != 0))) { - syntax_error(s_NickServ, u, "SASET", NICK_SASET_SYNTAX); - } else if (!na) { - notice_lang(s_NickServ, u, NICK_NOT_REGISTERED, nick); - } else if (na->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); - } else if (na->nc->flags & NI_SUSPENDED) { - notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); - } else if (stricmp(cmd, "DISPLAY") == 0) { - do_saset_display(u, na->nc, param); - } else if (stricmp(cmd, "PASSWORD") == 0) { - do_saset_password(u, na->nc, param); - } else if (stricmp(cmd, "URL") == 0) { - do_saset_url(u, na->nc, param); - } else if (stricmp(cmd, "EMAIL") == 0) { - do_saset_email(u, na->nc, param); - } else if (stricmp(cmd, "ICQ") == 0) { - do_saset_icq(u, na->nc, param); - } else if (stricmp(cmd, "GREET") == 0) { - do_saset_greet(u, na->nc, param); - } else if (stricmp(cmd, "KILL") == 0) { - do_saset_kill(u, na->nc, param); - } else if (stricmp(cmd, "SECURE") == 0) { - do_saset_secure(u, na->nc, param); - } else if (stricmp(cmd, "PRIVATE") == 0) { - do_saset_private(u, na->nc, param); - } else if (stricmp(cmd, "MSG") == 0) { - do_saset_msg(u, na->nc, param); - } else if (stricmp(cmd, "HIDE") == 0) { - do_saset_hide(u, na->nc, param); - } else if (stricmp(cmd, "NOEXPIRE") == 0) { - do_saset_noexpire(u, na, param); - } else if (stricmp(cmd, "AUTOOP") == 0) { - do_saset_autoop(u, na->nc, param); - } else if (stricmp(cmd, "LANGUAGE") == 0) { - do_saset_language(u, na->nc, param); - } else { - notice_lang(s_NickServ, u, NICK_SASET_UNKNOWN_OPTION, cmd); - } - return MOD_CONT; -} + CommandResult DoSetEmail(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 2 ? params[2].c_str() : NULL; -int do_saset_display(User * u, NickCore * nc, char *param) -{ - int i; - NickAlias *na; + if (!param && NSForceEmail) + { + notice_lang(s_NickServ, u, NICK_SASET_EMAIL_UNSET_IMPOSSIBLE); + return MOD_CONT; + } + else if (NSSecureAdmins && u->na->nc != nc && nick_is_services_admin(nc) && !is_services_root(u)) + { + notice_lang(s_NickServ, u, PERMISSION_DENIED); + return MOD_CONT; + } + else if (param && !MailValidate(param)) + { + notice_lang(s_NickServ, u, MAIL_X_INVALID, param); + return MOD_CONT; + } + + alog("%s: %s!%s@%s used SASET EMAIL on %s (e-mail: %s)", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, nc->display, nc->email ? nc->email : "none"); - /* First check whether param is a valid nick of the group */ - for (i = 0; i < nc->aliases.count; i++) { - na = static_cast<NickAlias *>(nc->aliases.list[i]); - if (stricmp(na->nick, param) == 0) { - param = na->nick; /* Because case may differ */ - break; + if (nc->email) + delete [] nc->email; + + if (param) + { + nc->email = sstrdup(param); + notice_lang(s_NickServ, u, NICK_SASET_EMAIL_CHANGED, nc->display, param); + } + else + { + nc->email = NULL; + notice_lang(s_NickServ, u, NICK_SASET_EMAIL_UNSET, nc->display); } + return MOD_CONT; } - if (i == nc->aliases.count) { - notice_lang(s_NickServ, u, NICK_SASET_DISPLAY_INVALID, - nc->display); + CommandResult DoSetICQ(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 2 ? params[2].c_str() : NULL; + + if (param) + { + int32 tmp = atol(param); + if (!tmp) + notice_lang(s_NickServ, u, NICK_SASET_ICQ_INVALID, param); + else + { + nc->icq = tmp; + notice_lang(s_NickServ, u, NICK_SASET_ICQ_CHANGED, nc->display, + param); + } + } + else + { + nc->icq = 0; + notice_lang(s_NickServ, u, NICK_SASET_ICQ_UNSET, nc->display); + } return MOD_CONT; } - change_core_display(nc, param); - notice_lang(s_NickServ, u, NICK_SASET_DISPLAY_CHANGED, nc->display); + CommandResult DoSetGreet(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 2 ? params[2].c_str() : NULL; - /* Enable nick tracking if enabled */ - if (NSNickTracking) - nsStartNickTracking(u); + if (nc->greet) + delete [] nc->greet; - return MOD_CONT; -} + if (param) + { + char buf[BUFSIZE]; + const char *rest = params.size() > 3 ? params[3].c_str() : NULL; -int do_saset_password(User * u, NickCore * nc, char *param) -{ - int len = strlen(param); - char tmp_pass[PASSMAX]; + snprintf(buf, sizeof(buf), "%s%s%s", param, rest ? " " : "", rest ? rest : ""); - if (NSSecureAdmins && u->na->nc != nc && nick_is_services_admin(nc) - && !is_services_root(u)) { - notice_lang(s_NickServ, u, PERMISSION_DENIED); - return MOD_CONT; - } else if (stricmp(nc->display, param) == 0 - || (StrictPasswords && len < 5)) { - notice_lang(s_NickServ, u, MORE_OBSCURE_PASSWORD); - return MOD_CONT; - } else if (enc_encrypt_check_len(len ,PASSMAX - 1)) { - notice_lang(s_NickServ, u, PASSWORD_TOO_LONG); + nc->greet = sstrdup(buf); + notice_lang(s_NickServ, u, NICK_SASET_GREET_CHANGED, nc->display, buf); + } + else + { + nc->greet = NULL; + notice_lang(s_NickServ, u, NICK_SASET_GREET_UNSET, nc->display); + } return MOD_CONT; } - if (enc_encrypt(param, len, nc->pass, PASSMAX - 1) < 0) { - memset(param, 0, len); - alog("%s: Failed to encrypt password for %s (set)", s_NickServ, - nc->display); - notice_lang(s_NickServ, u, NICK_SASET_PASSWORD_FAILED, - nc->display); + CommandResult DoSetKill(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 2 ? params[2].c_str() : NULL; + + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + if (!stricmp(param, "ON")) + { + nc->flags |= NI_KILLPROTECT; + nc->flags &= ~(NI_KILL_QUICK | NI_KILL_IMMED); + notice_lang(s_NickServ, u, NICK_SASET_KILL_ON, nc->display); + } + else if (!stricmp(param, "QUICK")) + { + nc->flags |= NI_KILLPROTECT | NI_KILL_QUICK; + nc->flags &= ~NI_KILL_IMMED; + notice_lang(s_NickServ, u, NICK_SASET_KILL_QUICK, nc->display); + } + else if (!stricmp(param, "IMMED")) + { + if (NSAllowKillImmed) + { + nc->flags |= NI_KILLPROTECT | NI_KILL_IMMED; + nc->flags &= ~NI_KILL_QUICK; + notice_lang(s_NickServ, u, NICK_SASET_KILL_IMMED, nc->display); + } + else + notice_lang(s_NickServ, u, NICK_SASET_KILL_IMMED_DISABLED); + } + else if (!stricmp(param, "OFF")) + { + nc->flags &= ~(NI_KILLPROTECT | NI_KILL_QUICK | NI_KILL_IMMED); + notice_lang(s_NickServ, u, NICK_SASET_KILL_OFF, nc->display); + } + else + syntax_error(s_NickServ, u, "SASET KILL", NSAllowKillImmed ? NICK_SASET_KILL_IMMED_SYNTAX : NICK_SASET_KILL_SYNTAX); return MOD_CONT; } - memset(param, 0, len); - if(enc_decrypt(nc->pass,tmp_pass,PASSMAX - 1)==1) { - notice_lang(s_NickServ, u, NICK_SASET_PASSWORD_CHANGED_TO, nc->display, - tmp_pass); - } else { - notice_lang(s_NickServ, u, NICK_SASET_PASSWORD_CHANGED, nc->display); - } + CommandResult DoSetSecure(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 2 ? params[2].c_str() : NULL; - alog("%s: %s!%s@%s used SASET PASSWORD on %s (e-mail: %s)", s_NickServ, - u->nick, u->username, u->host, nc->display, - (nc->email ? nc->email : "none")); - if (WallSetpass) - ircdproto->SendGlobops(s_NickServ, - "\2%s\2 used SASET PASSWORD on \2%s\2", - u->nick, nc->display); - return MOD_CONT; -} + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } -int do_saset_url(User * u, NickCore * nc, char *param) -{ - if (nc->url) - delete [] nc->url; - - if (param) { - nc->url = sstrdup(param); - notice_lang(s_NickServ, u, NICK_SASET_URL_CHANGED, nc->display, - param); - } else { - nc->url = NULL; - notice_lang(s_NickServ, u, NICK_SASET_URL_UNSET, nc->display); + if (!stricmp(param, "ON")) + { + nc->flags |= NI_SECURE; + notice_lang(s_NickServ, u, NICK_SASET_SECURE_ON, nc->display); + } + else if (!stricmp(param, "OFF")) + { + nc->flags &= ~NI_SECURE; + notice_lang(s_NickServ, u, NICK_SASET_SECURE_OFF, nc->display); + } + else + syntax_error(s_NickServ, u, "SASET SECURE", NICK_SASET_SECURE_SYNTAX); + return MOD_CONT; } - return MOD_CONT; -} -int do_saset_email(User * u, NickCore * nc, char *param) -{ - if (!param && NSForceEmail) { - notice_lang(s_NickServ, u, NICK_SASET_EMAIL_UNSET_IMPOSSIBLE); - return MOD_CONT; - } else if (NSSecureAdmins && u->na->nc != nc - && nick_is_services_admin(nc) - && !is_services_root(u)) { - notice_lang(s_NickServ, u, PERMISSION_DENIED); - return MOD_CONT; - } else if (param && !MailValidate(param)) { - notice_lang(s_NickServ, u, MAIL_X_INVALID, param); + CommandResult DoSetPrivate(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 2 ? params[2].c_str() : NULL; + + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + if (!stricmp(param, "ON")) + { + nc->flags |= NI_PRIVATE; + notice_lang(s_NickServ, u, NICK_SASET_PRIVATE_ON, nc->display); + } + else if (!stricmp(param, "OFF")) + { + nc->flags &= ~NI_PRIVATE; + notice_lang(s_NickServ, u, NICK_SASET_PRIVATE_OFF, nc->display); + } + else + syntax_error(s_NickServ, u, "SASET PRIVATE", NICK_SASET_PRIVATE_SYNTAX); return MOD_CONT; } - alog("%s: %s!%s@%s used SASET EMAIL on %s (e-mail: %s)", s_NickServ, - u->nick, u->username, u->host, nc->display, - (nc->email ? nc->email : "none")); + CommandResult DoSetMsg(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 2 ? params[2].c_str() : NULL; - if (nc->email) - delete [] nc->email; + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } - if (param) { - nc->email = sstrdup(param); - notice_lang(s_NickServ, u, NICK_SASET_EMAIL_CHANGED, nc->display, - param); - } else { - nc->email = NULL; - notice_lang(s_NickServ, u, NICK_SASET_EMAIL_UNSET, nc->display); - } - return MOD_CONT; -} + if (!UsePrivmsg) + { + notice_lang(s_NickServ, u, NICK_SASET_OPTION_DISABLED, "MSG"); + return MOD_CONT; + } -int do_saset_icq(User * u, NickCore * nc, char *param) -{ - if (param) { - int32 tmp = atol(param); - if (tmp == 0) { - notice_lang(s_NickServ, u, NICK_SASET_ICQ_INVALID, param); - } else { - nc->icq = tmp; - notice_lang(s_NickServ, u, NICK_SASET_ICQ_CHANGED, nc->display, - param); - } - } else { - nc->icq = 0; - notice_lang(s_NickServ, u, NICK_SASET_ICQ_UNSET, nc->display); + if (!stricmp(param, "ON")) + { + nc->flags |= NI_MSG; + notice_lang(s_NickServ, u, NICK_SASET_MSG_ON, nc->display); + } + else if (!stricmp(param, "OFF")) + { + nc->flags &= ~NI_MSG; + notice_lang(s_NickServ, u, NICK_SASET_MSG_OFF, nc->display); + } + else + syntax_error(s_NickServ, u, "SASET MSG", NICK_SASET_MSG_SYNTAX); + return MOD_CONT; } - return MOD_CONT; -} -int do_saset_greet(User * u, NickCore * nc, char *param) -{ - if (nc->greet) - delete [] nc->greet; - - if (param) { - char buf[BUFSIZE]; - char *end = strtok(NULL, ""); - - snprintf(buf, sizeof(buf), "%s%s%s", param, (end ? " " : ""), - (end ? end : "")); - - nc->greet = sstrdup(buf); - notice_lang(s_NickServ, u, NICK_SASET_GREET_CHANGED, nc->display, - buf); - } else { - nc->greet = NULL; - notice_lang(s_NickServ, u, NICK_SASET_GREET_UNSET, nc->display); - } - return MOD_CONT; -} + CommandResult DoSetHide(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 2 ? params[2].c_str() : NULL; -int do_saset_kill(User * u, NickCore * nc, char *param) -{ - if (stricmp(param, "ON") == 0) { - nc->flags |= NI_KILLPROTECT; - nc->flags &= ~(NI_KILL_QUICK | NI_KILL_IMMED); - notice_lang(s_NickServ, u, NICK_SASET_KILL_ON, nc->display); - } else if (stricmp(param, "QUICK") == 0) { - nc->flags |= NI_KILLPROTECT | NI_KILL_QUICK; - nc->flags &= ~NI_KILL_IMMED; - notice_lang(s_NickServ, u, NICK_SASET_KILL_QUICK, nc->display); - } else if (stricmp(param, "IMMED") == 0) { - if (NSAllowKillImmed) { - nc->flags |= NI_KILLPROTECT | NI_KILL_IMMED; - nc->flags &= ~NI_KILL_QUICK; - notice_lang(s_NickServ, u, NICK_SASET_KILL_IMMED, nc->display); - } else { - notice_lang(s_NickServ, u, NICK_SASET_KILL_IMMED_DISABLED); - } - } else if (stricmp(param, "OFF") == 0) { - nc->flags &= ~(NI_KILLPROTECT | NI_KILL_QUICK | NI_KILL_IMMED); - notice_lang(s_NickServ, u, NICK_SASET_KILL_OFF, nc->display); - } else { - syntax_error(s_NickServ, u, "SASET KILL", - NSAllowKillImmed ? NICK_SASET_KILL_IMMED_SYNTAX : - NICK_SASET_KILL_SYNTAX); - } - return MOD_CONT; -} + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } -int do_saset_secure(User * u, NickCore * nc, char *param) -{ - if (stricmp(param, "ON") == 0) { - nc->flags |= NI_SECURE; - notice_lang(s_NickServ, u, NICK_SASET_SECURE_ON, nc->display); - } else if (stricmp(param, "OFF") == 0) { - nc->flags &= ~NI_SECURE; - notice_lang(s_NickServ, u, NICK_SASET_SECURE_OFF, nc->display); - } else { - syntax_error(s_NickServ, u, "SASET SECURE", - NICK_SASET_SECURE_SYNTAX); - } - return MOD_CONT; -} + int flag, onmsg, offmsg; -int do_saset_private(User * u, NickCore * nc, char *param) -{ - if (stricmp(param, "ON") == 0) { - nc->flags |= NI_PRIVATE; - notice_lang(s_NickServ, u, NICK_SASET_PRIVATE_ON, nc->display); - } else if (stricmp(param, "OFF") == 0) { - nc->flags &= ~NI_PRIVATE; - notice_lang(s_NickServ, u, NICK_SASET_PRIVATE_OFF, nc->display); - } else { - syntax_error(s_NickServ, u, "SASET PRIVATE", - NICK_SASET_PRIVATE_SYNTAX); - } - return MOD_CONT; -} + if (!stricmp(param, "EMAIL")) + { + flag = NI_HIDE_EMAIL; + onmsg = NICK_SASET_HIDE_EMAIL_ON; + offmsg = NICK_SASET_HIDE_EMAIL_OFF; + } + else if (!stricmp(param, "USERMASK")) + { + flag = NI_HIDE_MASK; + onmsg = NICK_SASET_HIDE_MASK_ON; + offmsg = NICK_SASET_HIDE_MASK_OFF; + } + else if (!stricmp(param, "STATUS")) + { + flag = NI_HIDE_STATUS; + onmsg = NICK_SASET_HIDE_STATUS_ON; + offmsg = NICK_SASET_HIDE_STATUS_OFF; + } + else if (!stricmp(param, "QUIT")) + { + flag = NI_HIDE_QUIT; + onmsg = NICK_SASET_HIDE_QUIT_ON; + offmsg = NICK_SASET_HIDE_QUIT_OFF; + } + else + { + syntax_error(s_NickServ, u, "SASET HIDE", NICK_SASET_HIDE_SYNTAX); + return MOD_CONT; + } -int do_saset_msg(User * u, NickCore * nc, char *param) -{ - if (!UsePrivmsg) { - notice_lang(s_NickServ, u, NICK_SASET_OPTION_DISABLED, "MSG"); + param = params.size() > 3 ? params[3].c_str() : NULL; + if (!param) + syntax_error(s_NickServ, u, "SASET HIDE", NICK_SASET_HIDE_SYNTAX); + else if (!stricmp(param, "ON")) + { + nc->flags |= flag; + notice_lang(s_NickServ, u, onmsg, nc->display, s_NickServ); + } + else if (!stricmp(param, "OFF")) + { + nc->flags &= ~flag; + notice_lang(s_NickServ, u, offmsg, nc->display, s_NickServ); + } + else + syntax_error(s_NickServ, u, "SASET HIDE", NICK_SASET_HIDE_SYNTAX); return MOD_CONT; } - if (stricmp(param, "ON") == 0) { - nc->flags |= NI_MSG; - notice_lang(s_NickServ, u, NICK_SASET_MSG_ON, nc->display); - } else if (stricmp(param, "OFF") == 0) { - nc->flags &= ~NI_MSG; - notice_lang(s_NickServ, u, NICK_SASET_MSG_OFF, nc->display); - } else { - syntax_error(s_NickServ, u, "SASET MSG", NICK_SASET_MSG_SYNTAX); - } - return MOD_CONT; -} + CommandResult DoSetNoExpire(User *u, std::vector<std::string> ¶ms, NickAlias *na) + { + const char *param = params.size() > 2 ? params[2].c_str() : NULL; -int do_saset_hide(User * u, NickCore * nc, char *param) -{ - int flag, onmsg, offmsg; - - if (stricmp(param, "EMAIL") == 0) { - flag = NI_HIDE_EMAIL; - onmsg = NICK_SASET_HIDE_EMAIL_ON; - offmsg = NICK_SASET_HIDE_EMAIL_OFF; - } else if (stricmp(param, "USERMASK") == 0) { - flag = NI_HIDE_MASK; - onmsg = NICK_SASET_HIDE_MASK_ON; - offmsg = NICK_SASET_HIDE_MASK_OFF; - } else if (stricmp(param, "STATUS") == 0) { - flag = NI_HIDE_STATUS; - onmsg = NICK_SASET_HIDE_STATUS_ON; - offmsg = NICK_SASET_HIDE_STATUS_OFF; - } else if (stricmp(param, "QUIT") == 0) { - flag = NI_HIDE_QUIT; - onmsg = NICK_SASET_HIDE_QUIT_ON; - offmsg = NICK_SASET_HIDE_QUIT_OFF; - } else { - syntax_error(s_NickServ, u, "SASET HIDE", NICK_SASET_HIDE_SYNTAX); + if (!param) + { + syntax_error(s_NickServ, u, "SASET NOEXPIRE", NICK_SASET_NOEXPIRE_SYNTAX); + return MOD_CONT; + } + + if (!stricmp(param, "ON")) + { + na->status |= NS_NO_EXPIRE; + notice_lang(s_NickServ, u, NICK_SASET_NOEXPIRE_ON, na->nick); + } + else if (!stricmp(param, "OFF")) + { + na->status &= ~NS_NO_EXPIRE; + notice_lang(s_NickServ, u, NICK_SASET_NOEXPIRE_OFF, na->nick); + } + else + syntax_error(s_NickServ, u, "SASET NOEXPIRE", NICK_SASET_NOEXPIRE_SYNTAX); return MOD_CONT; } - param = strtok(NULL, " "); - if (!param) { - syntax_error(s_NickServ, u, "SASET HIDE", NICK_SASET_HIDE_SYNTAX); - } else if (stricmp(param, "ON") == 0) { - nc->flags |= flag; - notice_lang(s_NickServ, u, onmsg, nc->display, s_NickServ); - } else if (stricmp(param, "OFF") == 0) { - nc->flags &= ~flag; - notice_lang(s_NickServ, u, offmsg, nc->display, s_NickServ); - } else { - syntax_error(s_NickServ, u, "SASET HIDE", NICK_SASET_HIDE_SYNTAX); + CommandResult DoSetAutoOP(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 2 ? params[2].c_str() : NULL; + + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + if (!stricmp(param, "ON")) + { + nc->flags &= ~NI_AUTOOP; + notice_lang(s_NickServ, u, NICK_SASET_AUTOOP_ON, nc->display); + } + else if (!stricmp(param, "OFF")) + { + nc->flags |= NI_AUTOOP; + notice_lang(s_NickServ, u, NICK_SASET_AUTOOP_OFF, nc->display); + } + else + syntax_error(s_NickServ, u, "SET AUTOOP", NICK_SASET_AUTOOP_SYNTAX); + + return MOD_CONT; } - return MOD_CONT; -} -int do_saset_noexpire(User * u, NickAlias * na, char *param) -{ - if (!param) { - syntax_error(s_NickServ, u, "SASET NOEXPIRE", - NICK_SASET_NOEXPIRE_SYNTAX); + CommandResult DoSetLanguage(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 2 ? params[2].c_str() : NULL; + + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + int langnum; + + if (param[strspn(param, "0123456789")]) /* i.e. not a number */ + { + syntax_error(s_NickServ, u, "SASET LANGUAGE", NICK_SASET_LANGUAGE_SYNTAX); + return MOD_CONT; + } + langnum = atoi(param) - 1; + if (langnum < 0 || langnum >= NUM_LANGS || langlist[langnum] < 0) + { + notice_lang(s_NickServ, u, NICK_SASET_LANGUAGE_UNKNOWN, langnum + 1, s_NickServ); + return MOD_CONT; + } + nc->language = langlist[langnum]; + notice_lang(s_NickServ, u, NICK_SASET_LANGUAGE_CHANGED); + return MOD_CONT; } - if (stricmp(param, "ON") == 0) { - na->status |= NS_NO_EXPIRE; - notice_lang(s_NickServ, u, NICK_SASET_NOEXPIRE_ON, na->nick); - } else if (stricmp(param, "OFF") == 0) { - na->status &= ~NS_NO_EXPIRE; - notice_lang(s_NickServ, u, NICK_SASET_NOEXPIRE_OFF, na->nick); - } else { - syntax_error(s_NickServ, u, "SASET NOEXPIRE", - NICK_SASET_NOEXPIRE_SYNTAX); + public: + CommandNSSASet() : Command("SASET", 2, 4) + { } - return MOD_CONT; -} -int do_saset_autoop(User * u, NickCore * nc, char *param) -{ - if (stricmp(param, "ON") == 0) { - nc->flags &= ~NI_AUTOOP; - notice_lang(s_NickServ, u, NICK_SASET_AUTOOP_ON, nc->display); - } else if (stricmp(param, "OFF") == 0) { - nc->flags |= NI_AUTOOP; - notice_lang(s_NickServ, u, NICK_SASET_AUTOOP_OFF, nc->display); - } else { - syntax_error(s_NickServ, u, "SET AUTOOP", NICK_SASET_AUTOOP_SYNTAX); - } + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[0].c_str(); + const char *cmd = params[1].c_str(); - return MOD_CONT; -} + NickAlias *na; -int do_saset_language(User * u, NickCore * nc, char *param) -{ - int langnum; + if (readonly) + { + notice_lang(s_NickServ, u, NICK_SASET_DISABLED); + return MOD_CONT; + } + if (!(na = findnick(nick))) + { + notice_lang(s_NickServ, u, NICK_SASET_BAD_NICK, nick); + return MOD_CONT; + } - if (param[strspn(param, "0123456789")] != 0) { /* i.e. not a number */ - syntax_error(s_NickServ, u, "SASET LANGUAGE", - NICK_SASET_LANGUAGE_SYNTAX); + if (na->status & NS_VERBOTEN) + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); + else if (na->nc->flags & NI_SUSPENDED) + notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); + else if (!stricmp(cmd, "DISPLAY")) + return this->DoSetDisplay(u, params, na->nc); + else if (!stricmp(cmd, "PASSWORD")) + return this->DoSetPassword(u, params, na->nc); + else if (!stricmp(cmd, "URL")) + return this->DoSetUrl(u, params, na->nc); + else if (!stricmp(cmd, "EMAIL")) + return this->DoSetEmail(u, params, na->nc); + else if (!stricmp(cmd, "ICQ")) + return this->DoSetICQ(u, params, na->nc); + else if (!stricmp(cmd, "GREET")) + return this->DoSetGreet(u, params, na->nc); + else if (!stricmp(cmd, "KILL")) + return this->DoSetKill(u, params, na->nc); + else if (!stricmp(cmd, "SECURE")) + return this->DoSetSecure(u, params, na->nc); + else if (!stricmp(cmd, "PRIVATE")) + return this->DoSetPrivate(u, params, na->nc); + else if (!stricmp(cmd, "MSG")) + return this->DoSetMsg(u, params, na->nc); + else if (!stricmp(cmd, "HIDE")) + return this->DoSetHide(u, params, na->nc); + else if (!stricmp(cmd, "NOEXPIRE")) + return this->DoSetNoExpire(u, params, na); + else if (!stricmp(cmd, "AUTOOP")) + return this->DoSetAutoOP(u, params, na->nc); + else if (!stricmp(cmd, "LANGUAGE")) { + return this->DoSetLanguage(u, params, na->nc); + else + notice_lang(s_NickServ, u, NICK_SASET_UNKNOWN_OPTION, cmd); return MOD_CONT; } - langnum = atoi(param) - 1; - if (langnum < 0 || langnum >= NUM_LANGS || langlist[langnum] < 0) { - notice_lang(s_NickServ, u, NICK_SASET_LANGUAGE_UNKNOWN, langnum + 1, - s_NickServ); - return MOD_CONT; + + bool OnHelp(User *u, const std::string &subcommand) + { + // This needs to change XXX + if (!is_services_oper(u)) + return false; + + notice_lang(s_NickServ, u, NICK_HELP_SASET); + notice_lang(s_NickServ, u, NICK_HELP_SASET_DISPLAY); + notice_lang(s_NickServ, u, NICK_HELP_SASET_PASSWORD); + notice_lang(s_NickServ, u, NICK_HELP_SASET_URL); + notice_lang(s_NickServ, u, NICK_HELP_SASET_EMAIL); + notice_lang(s_NickServ, u, NICK_HELP_SASET_ICQ); + notice_lang(s_NickServ, u, NICK_HELP_SASET_GREET); + notice_lang(s_NickServ, u, NICK_HELP_SASET_KILL); + notice_lang(s_NickServ, u, NICK_HELP_SASET_SECURE); + notice_lang(s_NickServ, u, NICK_HELP_SASET_PRIVATE); + notice_lang(s_NickServ, u, NICK_HELP_SASET_MSG); + notice_lang(s_NickServ, u, NICK_HELP_SASET_HIDE); + notice_lang(s_NickServ, u, NICK_HELP_SASET_NOEXPIRE); + notice_lang(s_NickServ, u, NICK_HELP_SASET_AUTOOP); + notice_lang(s_NickServ, u, NICK_HELP_SASET_LANGUAGE); + + return true; } - nc->language = langlist[langnum]; - notice_lang(s_NickServ, u, NICK_SASET_LANGUAGE_CHANGED); - return MOD_CONT; -} + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "SASET", NICK_SASET_SYNTAX); + } +}; + +class NSSASet : public Module +{ + public: + NSSASet(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id: ns_set.c 850 2005-08-07 14:52:04Z geniusdex $"); + this->SetType(CORE); + + this->AddCommand(NICKSERV, new CommandNSSASet(), MOD_UNIQUE); -/* EOF */ + this->SetNickHelp(myNickServHelp); + } +}; + +/** + * Add the help response to anopes /ns help output. + * @param u The user who is requesting help + **/ +void myNickServHelp(User *u) +{ + if (is_services_oper(u)) + notice_lang(s_NickServ, u, NICK_HELP_CMD_SASET); +} MODULE_INIT("ns_saset", NSSASet) diff --git a/src/core/ns_sendpass.c b/src/core/ns_sendpass.c index 8861ad82e..37238daf8 100644 --- a/src/core/ns_sendpass.c +++ b/src/core/ns_sendpass.c @@ -15,29 +15,91 @@ #include "module.h" -int do_sendpass(User * u); +void myNickServHelp(User *u); -void myNickServHelp(User * u); +class CommandNSSendPass : public Command +{ + public: + CommandNSSendPass() : Command("SENDPASS", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[0].c_str(); + NickAlias *na; + + if (RestrictMail && !is_services_oper(u)) + notice_lang(s_NickServ, u, PERMISSION_DENIED); + else if (!(na = findnick(nick))) + notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + else if (na->status & NS_VERBOTEN) + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); + else + { + char buf[BUFSIZE]; + char tmp_pass[PASSMAX]; + if (enc_decrypt(na->nc->pass,tmp_pass,PASSMAX - 1) == 1) + { + MailInfo *mail; + + snprintf(buf, sizeof(buf), getstring(na, NICK_SENDPASS_SUBJECT), na->nick); + mail = MailBegin(u, na->nc, buf, s_NickServ); + if (!mail) + return MOD_CONT; + + fprintf(mail->pipe, getstring(na, NICK_SENDPASS_HEAD)); + fprintf(mail->pipe, "\n\n"); + fprintf(mail->pipe, getstring(na, NICK_SENDPASS_LINE_1), na->nick); + fprintf(mail->pipe, "\n\n"); + fprintf(mail->pipe, getstring(na, NICK_SENDPASS_LINE_2), tmp_pass); + fprintf(mail->pipe, "\n\n"); + fprintf(mail->pipe, getstring(na, NICK_SENDPASS_LINE_3)); + fprintf(mail->pipe, "\n\n"); + fprintf(mail->pipe, getstring(na, NICK_SENDPASS_LINE_4)); + fprintf(mail->pipe, "\n\n"); + fprintf(mail->pipe, getstring(na, NICK_SENDPASS_LINE_5), NetworkName); + fprintf(mail->pipe, "\n.\n"); + + MailEnd(mail); + + alog("%s: %s!%s@%s used SENDPASS on %s", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, nick); + notice_lang(s_NickServ, u, NICK_SENDPASS_OK, nick); + } + else + notice_lang(s_NickServ, u, NICK_SENDPASS_UNAVAILABLE); + } + + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_NickServ, u, NICK_HELP_SENDPASS); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "SENDPASS", NICK_SENDPASS_SYNTAX); + } +}; class NSSendPass : public Module { public: NSSendPass(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("SENDPASS", do_sendpass, NULL, NICK_HELP_SENDPASS, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + this->AddCommand(NICKSERV, new CommandNSSendPass(), MOD_UNIQUE); this->SetNickHelp(myNickServHelp); + if (!UseMail) - { throw ModuleException("Not using mail, whut."); - } } }; @@ -45,68 +107,9 @@ class NSSendPass : public Module * Add the help response to anopes /ns help output. * @param u The user who is requesting help **/ -void myNickServHelp(User * u) +void myNickServHelp(User *u) { notice_lang(s_NickServ, u, NICK_HELP_CMD_SENDPASS); } -/** - * The /ns sendpass command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_sendpass(User * u) -{ - - char *nick = strtok(NULL, " "); - NickAlias *na; - - if (!nick) { - syntax_error(s_NickServ, u, "SENDPASS", NICK_SENDPASS_SYNTAX); - } else if (RestrictMail && !is_services_oper(u)) { - notice_lang(s_NickServ, u, PERMISSION_DENIED); - } else if (!(na = findnick(nick))) { - notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); - } else if (na->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); - } else { - char buf[BUFSIZE]; - char tmp_pass[PASSMAX]; - if(enc_decrypt(na->nc->pass,tmp_pass,PASSMAX - 1)==1) { - MailInfo *mail; - - snprintf(buf, sizeof(buf), getstring(na, NICK_SENDPASS_SUBJECT), - na->nick); - mail = MailBegin(u, na->nc, buf, s_NickServ); - if (!mail) - return MOD_CONT; - - fprintf(mail->pipe, getstring(na, NICK_SENDPASS_HEAD)); - fprintf(mail->pipe, "\n\n"); - fprintf(mail->pipe, getstring(na, NICK_SENDPASS_LINE_1), na->nick); - fprintf(mail->pipe, "\n\n"); - fprintf(mail->pipe, getstring(na, NICK_SENDPASS_LINE_2), - tmp_pass); - fprintf(mail->pipe, "\n\n"); - fprintf(mail->pipe, getstring(na, NICK_SENDPASS_LINE_3)); - fprintf(mail->pipe, "\n\n"); - fprintf(mail->pipe, getstring(na, NICK_SENDPASS_LINE_4)); - fprintf(mail->pipe, "\n\n"); - fprintf(mail->pipe, getstring(na, NICK_SENDPASS_LINE_5), - NetworkName); - fprintf(mail->pipe, "\n.\n"); - - MailEnd(mail); - - alog("%s: %s!%s@%s used SENDPASS on %s", s_NickServ, u->nick, - u->username, u->host, nick); - notice_lang(s_NickServ, u, NICK_SENDPASS_OK, nick); - } else { - notice_lang(s_NickServ, u, NICK_SENDPASS_UNAVAILABLE); - } - } - - return MOD_CONT; -} - MODULE_INIT("ns_sendpass", NSSendPass) diff --git a/src/core/ns_set.c b/src/core/ns_set.c index 42192438c..7b7772bc6 100644 --- a/src/core/ns_set.c +++ b/src/core/ns_set.c @@ -16,438 +16,538 @@ #include "module.h" #include "encrypt.h" -int do_set(User * u); -int do_set_display(User * u, NickCore * nc, char *param); -int do_set_password(User * u, NickCore * nc, char *param); -int do_set_language(User * u, NickCore * nc, char *param); -int do_set_url(User * u, NickCore * nc, char *param); -int do_set_email(User * u, NickCore * nc, char *param); -int do_set_greet(User * u, NickCore * nc, char *param); -int do_set_icq(User * u, NickCore * nc, char *param); -int do_set_kill(User * u, NickCore * nc, char *param); -int do_set_secure(User * u, NickCore * nc, char *param); -int do_set_private(User * u, NickCore * nc, char *param); -int do_set_msg(User * u, NickCore * nc, char *param); -int do_set_hide(User * u, NickCore * nc, char *param); -int do_set_autoop(User *u, NickCore *nc, char *param); -void myNickServHelp(User * u); +void myNickServHelp(User *u); -class NSSet : public Module +class CommandNSSet : public Command { - public: - NSSet(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + CommandResult DoSetDisplay(User *u, std::vector<std::string> ¶ms, NickCore *nc) { - Command *c; + const char *param = params.size() > 1 ? params[1].c_str() : NULL; - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } - c = createCommand("SET", do_set, NULL, NICK_HELP_SET, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SET DISPLAY", NULL, NULL, NICK_HELP_SET_DISPLAY, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SET PASSWORD", NULL, NULL, NICK_HELP_SET_PASSWORD, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SET URL", NULL, NULL, NICK_HELP_SET_URL, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SET EMAIL", NULL, NULL, NICK_HELP_SET_EMAIL, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SET ICQ", NULL, NULL, NICK_HELP_SET_ICQ, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SET GREET", NULL, NULL, NICK_HELP_SET_GREET, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SET KILL", NULL, NULL, NICK_HELP_SET_KILL, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SET SECURE", NULL, NULL, NICK_HELP_SET_SECURE, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SET PRIVATE", NULL, NULL, NICK_HELP_SET_PRIVATE, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SET MSG", NULL, NULL, NICK_HELP_SET_MSG, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SET HIDE", NULL, NULL, NICK_HELP_SET_HIDE, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("SET AUTOOP", NULL, NULL, NICK_HELP_SET_AUTOOP, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + int i; + NickAlias *na; + + /* First check whether param is a valid nick of the group */ + for (i = 0; i < nc->aliases.count; ++i) + { + na = static_cast<NickAlias *>(nc->aliases.list[i]); + if (!stricmp(na->nick, param)) + { + param = na->nick; /* Because case may differ */ + break; + } + } - this->SetNickHelp(myNickServHelp); + if (i == nc->aliases.count) + { + notice_lang(s_NickServ, u, NICK_SET_DISPLAY_INVALID); + return MOD_CONT; + } + + change_core_display(nc, param); + notice_lang(s_NickServ, u, NICK_SET_DISPLAY_CHANGED, nc->display); + + /* Enable nick tracking if enabled */ + if (NSNickTracking) + nsStartNickTracking(u); + + return MOD_CONT; } -}; + CommandResult DoSetPassword(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 1 ? params[1].c_str() : NULL; + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } -/** - * Add the help response to anopes /ns help output. - * @param u The user who is requesting help - **/ -void myNickServHelp(User * u) -{ - notice_lang(s_NickServ, u, NICK_HELP_CMD_SET); -} + int len = strlen(param); + char tmp_pass[PASSMAX]; -/** - * The /ns set command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_set(User * u) -{ - char *cmd = strtok(NULL, " "); - char *param = strtok(NULL, " "); - NickAlias *na = u->na; + if (!stricmp(nc->display, param) || (StrictPasswords && len < 5)) + { + notice_lang(s_NickServ, u, MORE_OBSCURE_PASSWORD); + return MOD_CONT; + } + else if (enc_encrypt_check_len(len, PASSMAX - 1)) + { + notice_lang(s_NickServ, u, PASSWORD_TOO_LONG); + return MOD_CONT; + } + + if (enc_encrypt(param, len, nc->pass, PASSMAX - 1) < 0) + { + params[1].clear(); + alog("%s: Failed to encrypt password for %s (set)", s_NickServ, nc->display); + notice_lang(s_NickServ, u, NICK_SET_PASSWORD_FAILED); + return MOD_CONT; + } + params[1].clear(); + + if (enc_decrypt(nc->pass, tmp_pass, PASSMAX - 1) == 1) + notice_lang(s_NickServ, u, NICK_SET_PASSWORD_CHANGED_TO, tmp_pass); + else + notice_lang(s_NickServ, u, NICK_SET_PASSWORD_CHANGED); + + alog("%s: %s!%s@%s (e-mail: %s) changed its password.", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, nc->email ? nc->email : "none"); - if (readonly) { - notice_lang(s_NickServ, u, NICK_SET_DISABLED); return MOD_CONT; } - if (!param - && (!cmd - || (stricmp(cmd, "URL") != 0 && stricmp(cmd, "EMAIL") != 0 - && stricmp(cmd, "GREET") != 0 - && stricmp(cmd, "ICQ") != 0))) { - syntax_error(s_NickServ, u, "SET", NICK_SET_SYNTAX); - } else if (!na) { - notice_lang(s_NickServ, u, NICK_NOT_REGISTERED); - } else if (na->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); - } else if (na->nc->flags & NI_SUSPENDED) { - notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); - } else if (!nick_identified(u)) { - notice_lang(s_NickServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); - } else if (stricmp(cmd, "DISPLAY") == 0) { - do_set_display(u, na->nc, param); - } else if (stricmp(cmd, "PASSWORD") == 0) { - do_set_password(u, na->nc, param); - } else if (stricmp(cmd, "LANGUAGE") == 0) { - do_set_language(u, na->nc, param); - } else if (stricmp(cmd, "URL") == 0) { - do_set_url(u, na->nc, param); - } else if (stricmp(cmd, "EMAIL") == 0) { - do_set_email(u, na->nc, param); - } else if (stricmp(cmd, "ICQ") == 0) { - do_set_icq(u, na->nc, param); - } else if (stricmp(cmd, "GREET") == 0) { - do_set_greet(u, na->nc, param); - } else if (stricmp(cmd, "KILL") == 0) { - do_set_kill(u, na->nc, param); - } else if (stricmp(cmd, "SECURE") == 0) { - do_set_secure(u, na->nc, param); - } else if (stricmp(cmd, "PRIVATE") == 0) { - do_set_private(u, na->nc, param); - } else if (stricmp(cmd, "MSG") == 0) { - do_set_msg(u, na->nc, param); - } else if (stricmp(cmd, "HIDE") == 0) { - do_set_hide(u, na->nc, param); - } else if (stricmp(cmd, "AUTOOP") == 0) { - do_set_autoop(u, na->nc, param); - } else { - notice_lang(s_NickServ, u, NICK_SET_UNKNOWN_OPTION, cmd); - } - return MOD_CONT; -} + CommandResult DoSetLanguage(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 1 ? params[1].c_str() : NULL; -int do_set_display(User * u, NickCore * nc, char *param) -{ - int i; - NickAlias *na; + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } - /* First check whether param is a valid nick of the group */ - for (i = 0; i < nc->aliases.count; i++) { - na = static_cast<NickAlias *>(nc->aliases.list[i]); - if (!stricmp(na->nick, param)) { - param = na->nick; /* Because case may differ */ - break; + int langnum; + + if (param[strspn(param, "0123456789")]) /* i.e. not a number */ + { + syntax_error(s_NickServ, u, "SET LANGUAGE", NICK_SET_LANGUAGE_SYNTAX); + return MOD_CONT; + } + langnum = atoi(param) - 1; + if (langnum < 0 || langnum >= NUM_LANGS || langlist[langnum] < 0) + { + notice_lang(s_NickServ, u, NICK_SET_LANGUAGE_UNKNOWN, langnum + 1, s_NickServ); + return MOD_CONT; } + nc->language = langlist[langnum]; + notice_lang(s_NickServ, u, NICK_SET_LANGUAGE_CHANGED); + return MOD_CONT; } - if (i == nc->aliases.count) { - notice_lang(s_NickServ, u, NICK_SET_DISPLAY_INVALID); + CommandResult DoSetUrl(User *u, std::vector<std::string> ¶ms) + { + const char *param = params.size() > 1 ? params[1].c_str() : NULL; + + if (nc->url) + delete [] nc->url; + + if (param) + { + nc->url = sstrdup(param); + notice_lang(s_NickServ, u, NICK_SET_URL_CHANGED, param); + } + else + { + nc->url = NULL; + notice_lang(s_NickServ, u, NICK_SET_URL_UNSET); + } return MOD_CONT; } - change_core_display(nc, param); - notice_lang(s_NickServ, u, NICK_SET_DISPLAY_CHANGED, nc->display); + CommandResult DoSetEmail(User *u, std::vector<std::string> ¶ms) + { + const char *param = params.size() > 1 ? params[1].c_str() : NULL; - /* Enable nick tracking if enabled */ - if (NSNickTracking) - nsStartNickTracking(u); + if (!param && NSForceEmail) + { + notice_lang(s_NickServ, u, NICK_SET_EMAIL_UNSET_IMPOSSIBLE); + return MOD_CONT; + } + else if (param && !MailValidate(param)) + { + notice_lang(s_NickServ, u, MAIL_X_INVALID, param); + return MOD_CONT; + } - return MOD_CONT; -} + alog("%s: %s!%s@%s (e-mail: %s) changed its e-mail to %s.", s_NickServ, u->nick, u->GetIdent().c_str(), u->host, nc->email ? nc->email : "none", param ? param : "none"); -int do_set_password(User * u, NickCore * nc, char *param) -{ - int len = strlen(param); - char tmp_pass[PASSMAX]; + if (nc->email) + delete [] nc->email; - if (stricmp(nc->display, param) == 0 || (StrictPasswords && len < 5)) { - notice_lang(s_NickServ, u, MORE_OBSCURE_PASSWORD); - return MOD_CONT; - } else if (enc_encrypt_check_len(len ,PASSMAX - 1)) { - notice_lang(s_NickServ, u, PASSWORD_TOO_LONG); + if (param) + { + nc->email = sstrdup(param); + notice_lang(s_NickServ, u, NICK_SET_EMAIL_CHANGED, param); + } + else + { + nc->email = NULL; + notice_lang(s_NickServ, u, NICK_SET_EMAIL_UNSET); + } return MOD_CONT; } - if (enc_encrypt(param, len, nc->pass, PASSMAX - 1) < 0) { - memset(param, 0, len); - alog("%s: Failed to encrypt password for %s (set)", s_NickServ, - nc->display); - notice_lang(s_NickServ, u, NICK_SET_PASSWORD_FAILED); + CommandResult DoSetICQ(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 1 ? params[1].c_str() : NULL; + + if (param) + { + int32 tmp = atol(param); + if (!tmp) + notice_lang(s_NickServ, u, NICK_SET_ICQ_INVALID, param); + else + { + nc->icq = tmp; + notice_lang(s_NickServ, u, NICK_SET_ICQ_CHANGED, param); + } + } + else + { + nc->icq = 0; + notice_lang(s_NickServ, u, NICK_SET_ICQ_UNSET); + } return MOD_CONT; } - memset(param, 0, len); - if(enc_decrypt(nc->pass,tmp_pass,PASSMAX - 1)==1) { - notice_lang(s_NickServ, u, NICK_SET_PASSWORD_CHANGED_TO, tmp_pass); - } else { - notice_lang(s_NickServ, u, NICK_SET_PASSWORD_CHANGED); - } + CommandResult DoSetGreet(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 1 ? params[1].c_str() : NULL; - alog("%s: %s!%s@%s (e-mail: %s) changed its password.", s_NickServ, - u->nick, u->username, u->host, (nc->email ? nc->email : "none")); + if (nc->greet) + delete [] nc->greet; - return MOD_CONT; -} + if (param) + { + char buf[BUFSIZE]; + const char *rest = params.size() > 1 ? params[2].c_str() : NULL; -int do_set_language(User * u, NickCore * nc, char *param) -{ - int langnum; + snprintf(buf, sizeof(buf), "%s%s%s", param, rest ? " " : "", rest ? rest : ""); - if (param[strspn(param, "0123456789")] != 0) { /* i.e. not a number */ - syntax_error(s_NickServ, u, "SET LANGUAGE", - NICK_SET_LANGUAGE_SYNTAX); + nc->greet = sstrdup(buf); + notice_lang(s_NickServ, u, NICK_SET_GREET_CHANGED, buf); + } + else + { + nc->greet = NULL; + notice_lang(s_NickServ, u, NICK_SET_GREET_UNSET); + } return MOD_CONT; } - langnum = atoi(param) - 1; - if (langnum < 0 || langnum >= NUM_LANGS || langlist[langnum] < 0) { - notice_lang(s_NickServ, u, NICK_SET_LANGUAGE_UNKNOWN, langnum + 1, - s_NickServ); + + CommandResult DoSetKill(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 1 ? params[1].c_str() : NULL; + + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + if (!stricmp(param, "ON")) + { + nc->flags |= NI_KILLPROTECT; + nc->flags &= ~(NI_KILL_QUICK | NI_KILL_IMMED); + notice_lang(s_NickServ, u, NICK_SET_KILL_ON); + } + else if (!stricmp(param, "QUICK")) + { + nc->flags |= NI_KILLPROTECT | NI_KILL_QUICK; + nc->flags &= ~NI_KILL_IMMED; + notice_lang(s_NickServ, u, NICK_SET_KILL_QUICK); + } + else if (!stricmp(param, "IMMED")) + { + if (NSAllowKillImmed) + { + nc->flags |= NI_KILLPROTECT | NI_KILL_IMMED; + nc->flags &= ~NI_KILL_QUICK; + notice_lang(s_NickServ, u, NICK_SET_KILL_IMMED); + } + else + notice_lang(s_NickServ, u, NICK_SET_KILL_IMMED_DISABLED); + } + else if (!stricmp(param, "OFF")) + { + nc->flags &= ~(NI_KILLPROTECT | NI_KILL_QUICK | NI_KILL_IMMED); + notice_lang(s_NickServ, u, NICK_SET_KILL_OFF); + } + else + syntax_error(s_NickServ, u, "SET KILL", NSAllowKillImmed ? NICK_SET_KILL_IMMED_SYNTAX : NICK_SET_KILL_SYNTAX); return MOD_CONT; } - nc->language = langlist[langnum]; - notice_lang(s_NickServ, u, NICK_SET_LANGUAGE_CHANGED); - return MOD_CONT; -} -int do_set_url(User * u, NickCore * nc, char *param) -{ - if (nc->url) - delete [] nc->url; - - if (param) { - nc->url = sstrdup(param); - notice_lang(s_NickServ, u, NICK_SET_URL_CHANGED, param); - } else { - nc->url = NULL; - notice_lang(s_NickServ, u, NICK_SET_URL_UNSET); - } - return MOD_CONT; -} + CommandResult DoSetSecure(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 1 ? params[1].c_str() : NULL; -int do_set_email(User * u, NickCore * nc, char *param) -{ - if (!param && NSForceEmail) { - notice_lang(s_NickServ, u, NICK_SET_EMAIL_UNSET_IMPOSSIBLE); - return MOD_CONT; - } else if (param && !MailValidate(param)) { - notice_lang(s_NickServ, u, MAIL_X_INVALID, param); + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + if (!stricmp(param, "ON")) + { + nc->flags |= NI_SECURE; + notice_lang(s_NickServ, u, NICK_SET_SECURE_ON); + } + else if (!stricmp(param, "OFF")) + { + nc->flags &= ~NI_SECURE; + notice_lang(s_NickServ, u, NICK_SET_SECURE_OFF); + } + else + syntax_error(s_NickServ, u, "SET SECURE", NICK_SET_SECURE_SYNTAX); return MOD_CONT; } - alog("%s: %s!%s@%s (e-mail: %s) changed its e-mail to %s.", - s_NickServ, u->nick, u->username, u->host, - (nc->email ? nc->email : "none"), (param ? param : "none")); + CommandResult DoSetPrivate(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 1 ? params[1].c_str() : NULL; - if (nc->email) - delete [] nc->email; + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } - if (param) { - nc->email = sstrdup(param); - notice_lang(s_NickServ, u, NICK_SET_EMAIL_CHANGED, param); - } else { - nc->email = NULL; - notice_lang(s_NickServ, u, NICK_SET_EMAIL_UNSET); + if (!stricmp(param, "ON")) + { + nc->flags |= NI_PRIVATE; + notice_lang(s_NickServ, u, NICK_SET_PRIVATE_ON); + } + else if (!stricmp(param, "OFF")) + { + nc->flags &= ~NI_PRIVATE; + notice_lang(s_NickServ, u, NICK_SET_PRIVATE_OFF); + } + else + syntax_error(s_NickServ, u, "SET PRIVATE", NICK_SET_PRIVATE_SYNTAX); + return MOD_CONT; } - return MOD_CONT; -} -int do_set_icq(User * u, NickCore * nc, char *param) -{ - if (param) { - int32 tmp = atol(param); - if (!tmp) { - notice_lang(s_NickServ, u, NICK_SET_ICQ_INVALID, param); - } else { - nc->icq = tmp; - notice_lang(s_NickServ, u, NICK_SET_ICQ_CHANGED, param); - } - } else { - nc->icq = 0; - notice_lang(s_NickServ, u, NICK_SET_ICQ_UNSET); + CommandResult DoSetMsg(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 1 ? params[1].c_str() : NULL; + + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + if (!UsePrivmsg) + { + notice_lang(s_NickServ, u, NICK_SET_OPTION_DISABLED, "MSG"); + return MOD_CONT; + } + + if (!stricmp(param, "ON")) + { + nc->flags |= NI_MSG; + notice_lang(s_NickServ, u, NICK_SET_MSG_ON); + } + else if (!stricmp(param, "OFF")) + { + nc->flags &= ~NI_MSG; + notice_lang(s_NickServ, u, NICK_SET_MSG_OFF); + } + else + syntax_error(s_NickServ, u, "SET MSG", NICK_SET_MSG_SYNTAX); + return MOD_CONT; } - return MOD_CONT; -} -int do_set_greet(User * u, NickCore * nc, char *param) -{ - if (nc->greet) - delete [] nc->greet; + CommandResult DoSetHide(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 1 ? params[1].c_str() : NULL; - if (param) { - char buf[BUFSIZE]; - char *end = strtok(NULL, ""); + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } - snprintf(buf, sizeof(buf), "%s%s%s", param, (end ? " " : ""), - (end ? end : "")); + int flag, onmsg, offmsg; - nc->greet = sstrdup(buf); - notice_lang(s_NickServ, u, NICK_SET_GREET_CHANGED, buf); - } else { - nc->greet = NULL; - notice_lang(s_NickServ, u, NICK_SET_GREET_UNSET); - } - return MOD_CONT; -} + if (!stricmp(param, "EMAIL")) + { + flag = NI_HIDE_EMAIL; + onmsg = NICK_SET_HIDE_EMAIL_ON; + offmsg = NICK_SET_HIDE_EMAIL_OFF; + } + else if (!stricmp(param, "USERMASK")) + { + flag = NI_HIDE_MASK; + onmsg = NICK_SET_HIDE_MASK_ON; + offmsg = NICK_SET_HIDE_MASK_OFF; + } + else if (!stricmp(param, "STATUS")) + { + flag = NI_HIDE_STATUS; + onmsg = NICK_SET_HIDE_STATUS_ON; + offmsg = NICK_SET_HIDE_STATUS_OFF; + } + else if (!stricmp(param, "QUIT")) + { + flag = NI_HIDE_QUIT; + onmsg = NICK_SET_HIDE_QUIT_ON; + offmsg = NICK_SET_HIDE_QUIT_OFF; + } + else + { + syntax_error(s_NickServ, u, "SET HIDE", NICK_SET_HIDE_SYNTAX); + return MOD_CONT; + } -int do_set_kill(User * u, NickCore * nc, char *param) -{ - if (stricmp(param, "ON") == 0) { - nc->flags |= NI_KILLPROTECT; - nc->flags &= ~(NI_KILL_QUICK | NI_KILL_IMMED); - notice_lang(s_NickServ, u, NICK_SET_KILL_ON); - } else if (stricmp(param, "QUICK") == 0) { - nc->flags |= NI_KILLPROTECT | NI_KILL_QUICK; - nc->flags &= ~NI_KILL_IMMED; - notice_lang(s_NickServ, u, NICK_SET_KILL_QUICK); - } else if (stricmp(param, "IMMED") == 0) { - if (NSAllowKillImmed) { - nc->flags |= NI_KILLPROTECT | NI_KILL_IMMED; - nc->flags &= ~NI_KILL_QUICK; - notice_lang(s_NickServ, u, NICK_SET_KILL_IMMED); - } else { - notice_lang(s_NickServ, u, NICK_SET_KILL_IMMED_DISABLED); - } - } else if (stricmp(param, "OFF") == 0) { - nc->flags &= ~(NI_KILLPROTECT | NI_KILL_QUICK | NI_KILL_IMMED); - notice_lang(s_NickServ, u, NICK_SET_KILL_OFF); - } else { - syntax_error(s_NickServ, u, "SET KILL", - NSAllowKillImmed ? NICK_SET_KILL_IMMED_SYNTAX : - NICK_SET_KILL_SYNTAX); + param = params.size() > 2 ? params[2].c_str() : NULL; + if (!param) + syntax_error(s_NickServ, u, "SET HIDE", NICK_SET_HIDE_SYNTAX); + else if (!stricmp(param, "ON")) + { + nc->flags |= flag; + notice_lang(s_NickServ, u, onmsg, s_NickServ); + } + else if (!stricmp(param, "OFF")) + { + nc->flags &= ~flag; + notice_lang(s_NickServ, u, offmsg, s_NickServ); + } + else + syntax_error(s_NickServ, u, "SET HIDE", NICK_SET_HIDE_SYNTAX); + return MOD_CONT; } - return MOD_CONT; -} -int do_set_secure(User * u, NickCore * nc, char *param) -{ - if (stricmp(param, "ON") == 0) { - nc->flags |= NI_SECURE; - notice_lang(s_NickServ, u, NICK_SET_SECURE_ON); - } else if (stricmp(param, "OFF") == 0) { - nc->flags &= ~NI_SECURE; - notice_lang(s_NickServ, u, NICK_SET_SECURE_OFF); - } else { - syntax_error(s_NickServ, u, "SET SECURE", NICK_SET_SECURE_SYNTAX); - } - return MOD_CONT; -} + CommandResult DoSetAutoOP(User *u, std::vector<std::string> ¶ms, NickCore *nc) + { + const char *param = params.size() > 1 ? params[1].c_str() : NULL; -int do_set_private(User * u, NickCore * nc, char *param) -{ - if (stricmp(param, "ON") == 0) { - nc->flags |= NI_PRIVATE; - notice_lang(s_NickServ, u, NICK_SET_PRIVATE_ON); - } else if (stricmp(param, "OFF") == 0) { - nc->flags &= ~NI_PRIVATE; - notice_lang(s_NickServ, u, NICK_SET_PRIVATE_OFF); - } else { - syntax_error(s_NickServ, u, "SET PRIVATE", - NICK_SET_PRIVATE_SYNTAX); - } - return MOD_CONT; -} + if (!param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + /** + * This works the other way around, the absence of this flag denotes ON + * This is so when people upgrade, and dont have the flag + * the default is on + **/ + if (!stricmp(param, "ON")) + { + nc->flags &= ~NI_AUTOOP; + notice_lang(s_NickServ, u, NICK_SET_AUTOOP_ON); + } + else if (!stricmp(param, "OFF")) + { + nc->flags |= NI_AUTOOP; + notice_lang(s_NickServ, u, NICK_SET_AUTOOP_OFF); + } + else + syntax_error(s_NickServ, u, "SET AUTOOP", NICK_SET_AUTOOP_SYNTAX); -int do_set_msg(User * u, NickCore * nc, char *param) -{ - if (!UsePrivmsg) { - notice_lang(s_NickServ, u, NICK_SET_OPTION_DISABLED, "MSG"); return MOD_CONT; } - - if (stricmp(param, "ON") == 0) { - nc->flags |= NI_MSG; - notice_lang(s_NickServ, u, NICK_SET_MSG_ON); - } else if (stricmp(param, "OFF") == 0) { - nc->flags &= ~NI_MSG; - notice_lang(s_NickServ, u, NICK_SET_MSG_OFF); - } else { - syntax_error(s_NickServ, u, "SET MSG", NICK_SET_MSG_SYNTAX); + public: + CommandNSSet() : Command("SET", 1, 3) + { } - return MOD_CONT; -} -int do_set_hide(User * u, NickCore * nc, char *param) -{ - int flag, onmsg, offmsg; - - if (stricmp(param, "EMAIL") == 0) { - flag = NI_HIDE_EMAIL; - onmsg = NICK_SET_HIDE_EMAIL_ON; - offmsg = NICK_SET_HIDE_EMAIL_OFF; - } else if (stricmp(param, "USERMASK") == 0) { - flag = NI_HIDE_MASK; - onmsg = NICK_SET_HIDE_MASK_ON; - offmsg = NICK_SET_HIDE_MASK_OFF; - } else if (stricmp(param, "STATUS") == 0) { - flag = NI_HIDE_STATUS; - onmsg = NICK_SET_HIDE_STATUS_ON; - offmsg = NICK_SET_HIDE_STATUS_OFF; - } else if (stricmp(param, "QUIT") == 0) { - flag = NI_HIDE_QUIT; - onmsg = NICK_SET_HIDE_QUIT_ON; - offmsg = NICK_SET_HIDE_QUIT_OFF; - } else { - syntax_error(s_NickServ, u, "SET HIDE", NICK_SET_HIDE_SYNTAX); + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + NickAlias *na = u->na; + + if (readonly) + { + notice_lang(s_NickServ, u, NICK_SET_DISABLED); + return MOD_CONT; + } + + if (!na) + notice_lang(s_NickServ, u, NICK_NOT_REGISTERED); + else if (na->status & NS_VERBOTEN) + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); + else if (na->nc->flags & NI_SUSPENDED) + notice_lang(s_NickServ, u, NICK_X_SUSPENDED, na->nick); + else if (!nick_identified(u)) + notice_lang(s_NickServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + else if (!stricmp(cmd, "DISPLAY")) + return this->DoSetDisplay(u, params, na->nc); + else if (!stricmp(cmd, "PASSWORD")) + return this->DoSetPassword(u, params, na->nc); + else if (!stricmp(cmd, "LANGUAGE")) + return this->DoSetLanguage(u, params, na->nc); + else if (!stricmp(cmd, "URL")) + return this->DoSetUrl(u, params, na->nc); + else if (!stricmp(cmd, "EMAIL")) + return this->DoSetEmail(u, params, na->nc); + else if (!stricmp(cmd, "ICQ")) + return this->DoSetICQ(u, params, na->nc); + else if (!stricmp(cmd, "GREET")) + return this->DoSetGreet(u, params, na->nc); + else if (!stricmp(cmd, "KILL")) + return this->DoSetKill(u, params, na->nc); + else if (!stricmp(cmd, "SECURE")) + return this->DoSetSecure(u, params, na->nc); + else if (!stricmp(cmd, "PRIVATE")) + return this->DoSetPrivate(u, params, na->nc); + else if (!stricmp(cmd, "MSG")) + return this->DoSetMsg(u, params, na->nc); + else if (!stricmp(cmd, "HIDE")) + return this->DoSetHide(u, params, na->nc); + else if (!stricmp(cmd, "AUTOOP")) + return this->DoSetAutoOP(u, params, na->nc); + else + notice_lang(s_NickServ, u, NICK_SET_UNKNOWN_OPTION, cmd); return MOD_CONT; } - param = strtok(NULL, " "); - if (!param) { - syntax_error(s_NickServ, u, "SET HIDE", NICK_SET_HIDE_SYNTAX); - } else if (stricmp(param, "ON") == 0) { - nc->flags |= flag; - notice_lang(s_NickServ, u, onmsg, s_NickServ); - } else if (stricmp(param, "OFF") == 0) { - nc->flags &= ~flag; - notice_lang(s_NickServ, u, offmsg, s_NickServ); - } else { - syntax_error(s_NickServ, u, "SET HIDE", NICK_SET_HIDE_SYNTAX); + bool OnHelp(User *u, const std::string &subcommand) + { + // This needs to change XXX + notice_lang(s_NickServ, u, NICK_HELP_SET); + notice_lang(s_NickServ, u, NICK_HELP_SET_DISPLAY); + notice_lang(s_NickServ, u, NICK_HELP_SET_PASSWORD); + notice_lang(s_NickServ, u, NICK_HELP_SET_URL); + notice_lang(s_NickServ, u, NICK_HELP_SET_EMAIL); + notice_lang(s_NickServ, u, NICK_HELP_SET_ICQ); + notice_lang(s_NickServ, u, NICK_HELP_SET_GREET); + notice_lang(s_NickServ, u, NICK_HELP_SET_KILL); + notice_lang(s_NickServ, u, NICK_HELP_SET_SECURE); + notice_lang(s_NickServ, u, NICK_HELP_SET_PRIVATE); + notice_lang(s_NickServ, u, NICK_HELP_SET_MSG); + notice_lang(s_NickServ, u, NICK_HELP_SET_HIDE); + notice_lang(s_NickServ, u, NICK_HELP_SET_AUTOOP); } - return MOD_CONT; -} -int do_set_autoop(User *u, NickCore *nc, char *param) { - - /** - * This works the other way around, the absence of this flag denotes ON - * This is so when people upgrade, and dont have the flag - * the default is on - **/ - if (stricmp(param, "ON") == 0) { - nc->flags &= ~NI_AUTOOP; - notice_lang(s_NickServ, u, NICK_SET_AUTOOP_ON); - } else if (stricmp(param, "OFF") == 0) { - nc->flags |= NI_AUTOOP; - notice_lang(s_NickServ, u, NICK_SET_AUTOOP_OFF); - } else { - syntax_error(s_NickServ, u, "SET AUTOOP", NICK_SET_AUTOOP_SYNTAX); + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "SET", NICK_SET_SYNTAX); } +}; - return MOD_CONT; -} +class NSSet : public Module +{ + public: + NSSet(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + + this->AddCommand(NICKSERV, new CommandNSSet(), MOD_UNIQUE); + this->SetNickHelp(myNickServHelp); + } +}; -/* EOF */ +/** + * Add the help response to anopes /ns help output. + * @param u The user who is requesting help + **/ +void myNickServHelp(User *u) +{ + notice_lang(s_NickServ, u, NICK_HELP_CMD_SET); +} MODULE_INIT("ns_set", NSSet) diff --git a/src/core/ns_status.c b/src/core/ns_status.c index 360772ba3..c2ece7657 100644 --- a/src/core/ns_status.c +++ b/src/core/ns_status.c @@ -15,22 +15,63 @@ #include "module.h" -int do_status(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); + +class CommandNSStatus : public Command +{ + public: + CommandNSStatus() : Command("STATUS", 0, 16) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + User *u2; + NickAlias *na = NULL; + int i = 0; + const char *nick = params.size() ? params[0].c_str() : NULL; + + /* If no nickname is given, we assume that the user + * is asking for himself */ + if (!nick) + nick = u->nick; + + while (nick && i++ < 16) + { + if (!(u2 = finduser(nick))) /* Nick is not online */ + notice_lang(s_NickServ, u, NICK_STATUS_0, nick); + else if (nick_identified(u2)) /* Nick is identified */ + notice_lang(s_NickServ, u, NICK_STATUS_3, nick); + else if (nick_recognized(u2)) /* Nick is recognised, but NOT identified */ + notice_lang(s_NickServ, u, NICK_STATUS_2, nick); + else if (!(na = findnick(nick))) /* Nick is online, but NOT a registered */ + notice_lang(s_NickServ, u, NICK_STATUS_0, nick); + else + notice_lang(s_NickServ, u, NICK_STATUS_1, nick); + + /* Get the next nickname */ + nick = params.size() > i ? params[i].c_str() : NULL; + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_NickServ, u, NICK_HELP_STATUS); + return true; + } +}; class NSStatus : public Module { public: NSStatus(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("STATUS", do_status, NULL, NICK_HELP_STATUS, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + this->AddCommand(NICKSERV, new CommandNSStatus(), MOD_UNIQUE); this->SetNickHelp(myNickServHelp); } @@ -40,44 +81,9 @@ class NSStatus : public Module * Add the help response to anopes /ns help output. * @param u The user who is requesting help **/ -void myNickServHelp(User * u) +void myNickServHelp(User *u) { notice_lang(s_NickServ, u, NICK_HELP_CMD_STATUS); } -/** - * The /ns status command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_status(User * u) -{ - User *u2; - NickAlias *na = NULL; - int i = 0; - char *nick = strtok(NULL, " "); - - /* If no nickname is given, we assume that the user - * is asking for himself */ - if (!nick) - nick = u->nick; - - while (nick && (i++ < 16)) { - if (!(u2 = finduser(nick))) /* Nick is not online */ - notice_lang(s_NickServ, u, NICK_STATUS_0, nick); - else if (nick_identified(u2)) /* Nick is identified */ - notice_lang(s_NickServ, u, NICK_STATUS_3, nick); - else if (nick_recognized(u2)) /* Nick is recognised, but NOT identified */ - notice_lang(s_NickServ, u, NICK_STATUS_2, nick); - else if ((na = findnick(nick)) == NULL) /* Nick is online, but NOT a registered */ - notice_lang(s_NickServ, u, NICK_STATUS_0, nick); - else - notice_lang(s_NickServ, u, NICK_STATUS_1, nick); - - /* Get the next nickname */ - nick = strtok(NULL, " "); - } - return MOD_CONT; -} - MODULE_INIT("ns_status", NSStatus) diff --git a/src/core/ns_suspend.c b/src/core/ns_suspend.c index 07e13482a..f5cfa5d88 100644 --- a/src/core/ns_suspend.c +++ b/src/core/ns_suspend.c @@ -15,165 +15,189 @@ #include "module.h" -int do_suspend(User * u); -int do_unsuspend(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); -class NSSuspend : public Module +class CommandNSSuspend : public Command { public: - NSSuspend(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandNSSuspend() : Command("SUSPEND", 2, 2) { - Command *c; + } - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + NickAlias *na, *na2; + const char *nick = params[0].c_str(); + const char *reason = params[1].c_str(); + int i; + + if (readonly) + { + notice_lang(s_NickServ, u, READ_ONLY_MODE); + return MOD_CONT; + } - c = createCommand("SUSPEND", do_suspend, is_services_oper, -1, -1, -1, NICK_SERVADMIN_HELP_SUSPEND, NICK_SERVADMIN_HELP_SUSPEND); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); - c = createCommand("UNSUSPEND", do_unsuspend, is_services_oper, -1, -1, -1, NICK_SERVADMIN_HELP_UNSUSPEND, NICK_SERVADMIN_HELP_UNSUSPEND); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + if (!(na = findnick(nick))) + { + notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + return MOD_CONT; + } - this->SetNickHelp(myNickServHelp); - } -}; + if (na->status & NS_VERBOTEN) + { + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); + return MOD_CONT; + } -/** - * Add the help response to anopes /ns help output. - * @param u The user who is requesting help - **/ -void myNickServHelp(User * u) -{ - if (is_services_oper(u)) { - notice_lang(s_NickServ, u, NICK_HELP_CMD_SUSPEND); - notice_lang(s_NickServ, u, NICK_HELP_CMD_UNSUSPEND); - } -} + if (NSSecureAdmins && nick_is_services_admin(na->nc) && !is_services_root(u)) + { + notice_lang(s_NickServ, u, PERMISSION_DENIED); + return MOD_CONT; + } -/** - * The /ns suspend command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_suspend(User * u) -{ - NickAlias *na, *na2; - char *nick = strtok(NULL, " "); - char *reason = strtok(NULL, ""); - int i; + if (na) + { + na->nc->flags |= NI_SUSPENDED; + na->nc->flags |= NI_SECURE; + na->nc->flags &= ~(NI_KILLPROTECT | NI_KILL_QUICK | NI_KILL_IMMED); + + for (i = 0; i < na->nc->aliases.count; ++i) + { + na2 = static_cast<NickAlias *>(na->nc->aliases.list[i]); + if (na2->nc == na->nc) + { + na2->status &= ~(NS_IDENTIFIED | NS_RECOGNIZED); + na2->last_quit = sstrdup(reason); + } + } - if (!nick || !reason) { - syntax_error(s_NickServ, u, "SUSPEND", NICK_SUSPEND_SYNTAX); - return MOD_CONT; - } + if (WallForbid) + ircdproto->SendGlobops(s_NickServ, "\2%s\2 used SUSPEND on \2%s\2", u->nick, nick); - if (readonly) { - notice_lang(s_NickServ, u, READ_ONLY_MODE); + alog("%s: %s set SUSPEND for nick %s", s_NickServ, u->nick, nick); + notice_lang(s_NickServ, u, NICK_SUSPEND_SUCCEEDED, nick); + send_event(EVENT_NICK_SUSPENDED, 1, nick); + } + else + { + alog("%s: Valid SUSPEND for %s by %s failed", s_NickServ, nick, u->nick); + notice_lang(s_NickServ, u, NICK_SUSPEND_FAILED, nick); + } return MOD_CONT; } - if ((na = findnick(nick)) == NULL) { - notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); - return MOD_CONT; + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_oper(u)) + return false; + + notice_lang(s_NickServ, u, NICK_SERVADMIN_HELP_SUSPEND); + return true; } - if (na->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); - return MOD_CONT; + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "SUSPEND", NICK_SUSPEND_SYNTAX); } +}; - if (NSSecureAdmins && nick_is_services_admin(na->nc) - && !is_services_root(u)) { - notice_lang(s_NickServ, u, PERMISSION_DENIED); - return MOD_CONT; +class CommandNSUnSuspend : public Command +{ + public: + CommandNSUnSuspend() : Command("UNSUSPEND", 1, 1) + { } - if (na) { - na->nc->flags |= NI_SUSPENDED; - na->nc->flags |= NI_SECURE; - na->nc->flags &= ~(NI_KILLPROTECT | NI_KILL_QUICK | NI_KILL_IMMED); + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + NickAlias *na; + const char *nick = params[0].c_str(); - for (i = 0; i < na->nc->aliases.count; i++) { - na2 = (NickAlias *)na->nc->aliases.list[i]; - if (na2->nc == na->nc) { - na2->status &= ~(NS_IDENTIFIED | NS_RECOGNIZED); - na2->last_quit = sstrdup(reason); - } + if (readonly) + { + notice_lang(s_NickServ, u, READ_ONLY_MODE); + return MOD_CONT; } - if (WallForbid) - ircdproto->SendGlobops(s_NickServ, "\2%s\2 used SUSPEND on \2%s\2", - u->nick, nick); - - alog("%s: %s set SUSPEND for nick %s", s_NickServ, u->nick, nick); - notice_lang(s_NickServ, u, NICK_SUSPEND_SUCCEEDED, nick); - send_event(EVENT_NICK_SUSPENDED, 1, nick); - - } else { + if (!(na = findnick(nick))) + { + notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + return MOD_CONT; + } - alog("%s: Valid SUSPEND for %s by %s failed", s_NickServ, nick, - u->nick); - notice_lang(s_NickServ, u, NICK_SUSPEND_FAILED, nick); + if (na->status & NS_VERBOTEN) + { + notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); + return MOD_CONT; + } - } - return MOD_CONT; -} + if (NSSecureAdmins && nick_is_services_admin(na->nc) && !is_services_root(u)) + { + notice_lang(s_NickServ, u, PERMISSION_DENIED); + return MOD_CONT; + } -/*************************************************************************/ + if (na) + { + na->nc->flags &= ~NI_SUSPENDED; -int do_unsuspend(User * u) -{ - NickAlias *na; - char *nick = strtok(NULL, " "); + if (WallForbid) + ircdproto->SendGlobops(s_NickServ, "\2%s\2 used UNSUSPEND on \2%s\2", u->nick, nick); - if (!nick) { - syntax_error(s_NickServ, u, "UNSUSPEND", NICK_UNSUSPEND_SYNTAX); + alog("%s: %s set UNSUSPEND for nick %s", s_NickServ, u->nick, nick); + notice_lang(s_NickServ, u, NICK_UNSUSPEND_SUCCEEDED, nick); + send_event(EVENT_NICK_UNSUSPEND, 1, nick); + } + else + { + alog("%s: Valid UNSUSPEND for %s by %s failed", s_NickServ, nick, u->nick); + notice_lang(s_NickServ, u, NICK_UNSUSPEND_FAILED, nick); + } return MOD_CONT; } - if (readonly) { - notice_lang(s_NickServ, u, READ_ONLY_MODE); - return MOD_CONT; - } + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_oper(u)) + return false; - if ((na = findnick(nick)) == NULL) { - notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); - return MOD_CONT; + notice_lang(s_NickServ, u, NICK_SERVADMIN_HELP_UNSUSPEND); + return true; } - if (na->status & NS_VERBOTEN) { - notice_lang(s_NickServ, u, NICK_X_FORBIDDEN, na->nick); - return MOD_CONT; - } - if (NSSecureAdmins && nick_is_services_admin(na->nc) - && !is_services_root(u)) { - notice_lang(s_NickServ, u, PERMISSION_DENIED); - return MOD_CONT; + void OnSyntaxError(User *u) + { + syntax_error(s_NickServ, u, "UNSUSPEND", NICK_UNSUSPEND_SYNTAX); } +}; - if (na) { - na->nc->flags &= ~NI_SUSPENDED; - - if (WallForbid) - ircdproto->SendGlobops(s_NickServ, "\2%s\2 used UNSUSPEND on \2%s\2", - u->nick, nick); - - alog("%s: %s set UNSUSPEND for nick %s", s_NickServ, u->nick, - nick); - notice_lang(s_NickServ, u, NICK_UNSUSPEND_SUCCEEDED, nick); - send_event(EVENT_NICK_UNSUSPEND, 1, nick); - - } else { +class NSSuspend : public Module +{ + public: + NSSuspend(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); - alog("%s: Valid UNSUSPEND for %s by %s failed", s_NickServ, nick, - u->nick); - notice_lang(s_NickServ, u, NICK_UNSUSPEND_FAILED, nick); + this->AddCommand(NICKSERV, new CommandNSSuspend(), MOD_UNIQUE); + this->AddCommand(NICKSERV, new CommandNSUnSuspend(), MOD_UNIQUE); + this->SetNickHelp(myNickServHelp); } +}; - return MOD_CONT; - +/** + * Add the help response to anopes /ns help output. + * @param u The user who is requesting help + **/ +void myNickServHelp(User *u) +{ + if (is_services_oper(u)) + { + notice_lang(s_NickServ, u, NICK_HELP_CMD_SUSPEND); + notice_lang(s_NickServ, u, NICK_HELP_CMD_UNSUSPEND); + } } MODULE_INIT("ns_suspend", NSSuspend) diff --git a/src/core/ns_update.c b/src/core/ns_update.c index faae8567f..8396ad728 100644 --- a/src/core/ns_update.c +++ b/src/core/ns_update.c @@ -15,65 +15,64 @@ #include "module.h" -int do_nickupdate(User * u); -void myNickServHelp(User * u); +void myNickServHelp(User *u); + +class CommandNSUpdate : public Command +{ + public: + CommandNSUpdate() : Command("UPDATE", 0, 0) + { + } + + CommandReturn Process(User *u, std::vector<std::string> ¶ms) + { + if (!nick_identified(u)) + { + notice_lang(s_NickServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); + return MOD_CONT; + } + + if (NSModeOnID) + do_setmodes(u); + check_memos(u); + if (u->na->last_realname) + delete [] u->na->last_realname; + u->na->last_realname = sstrdup(u->realname); + u->na->status |= NS_IDENTIFIED; + u->na->last_seen = time(NULL); + if (ircd->vhost) + do_on_id(u); + notice_lang(s_NickServ, u, NICK_UPDATE_SUCCESS, s_NickServ); + return MOD_CONT; + } + + bool Help(User *u) + { + notice_lang(s_NickServ, u, NICK_HELP_UPDATE); + } +}; class NSUpdate : public Module { public: NSUpdate(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - - c = createCommand("UPDATE", do_nickupdate, NULL, NICK_HELP_UPDATE, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_UNIQUE); + this->AddCommand(NICKSERV, new CommandNSUpdate(), MOD_UNIQUE); this->SetNickHelp(myNickServHelp); } }; - - /** * Add the help response to anopes /ns help output. * @param u The user who is requesting help **/ -void myNickServHelp(User * u) +void myNickServHelp(User *u) { notice_lang(s_NickServ, u, NICK_HELP_CMD_UPDATE); } -/** - * The /ns update command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_nickupdate(User * u) -{ - NickAlias *na; - - if (!nick_identified(u)) { - notice_lang(s_NickServ, u, NICK_IDENTIFY_REQUIRED, s_NickServ); - } else { - na = u->na; - if (NSModeOnID) - do_setmodes(u); - check_memos(u); - if (na->last_realname) - delete [] na->last_realname; - na->last_realname = sstrdup(u->realname); - na->status |= NS_IDENTIFIED; - na->last_seen = time(NULL); - if (ircd->vhost) { - do_on_id(u); - } - notice_lang(s_NickServ, u, NICK_UPDATE_SUCCESS, s_NickServ); - } - return MOD_CONT; -} - MODULE_INIT("ns_update", NSUpdate) diff --git a/src/core/os_admin.c b/src/core/os_admin.c index c30555979..91b5b8f4b 100644 --- a/src/core/os_admin.c +++ b/src/core/os_admin.c @@ -15,90 +15,64 @@ #include "module.h" -int do_admin(User * u); -int admin_list_callback(SList * slist, int number, void *item, - va_list args); -int admin_list(int number, NickCore * nc, User * u, int *sent_header); -void myOperServHelp(User * u); +int admin_list_callback(SList *slist, int number, void *item, va_list args); +int admin_list(int number, NickCore *nc, User *u, int *sent_header); +void myOperServHelp(User *u); -class OSAdmin : public Module +class CommandOSAdmin : public Command { - public: - OSAdmin(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + CommandResult DoAdd(User *u, std::vector<std::string> ¶ms) { - Command *c; + const char *nick = params.size() > 1 ? params[1].c_str() : NULL; + int res = 0; - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("ADMIN", do_admin, NULL, OPER_HELP_ADMIN, -1, -1, -1, -1); - c->help_param1 = s_NickServ; - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - - this->SetOperHelp(myOperServHelp); - } -}; - - - - -/** - * Add the help response to anopes /os help output. - * @param u The user who is requesting help - **/ -void myOperServHelp(User * u) -{ - notice_lang(s_OperServ, u, OPER_HELP_CMD_ADMIN); -} + if (!nick) + { + this->OnSyntaxError(u); + return MOD_CONT; + } -/** - * The /os admin command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_admin(User * u) -{ - char *cmd = strtok(NULL, " "); - char *nick = strtok(NULL, " "); - NickAlias *na; - int res = 0; - - if (!cmd || (!nick && stricmp(cmd, "LIST") && stricmp(cmd, "CLEAR"))) { - syntax_error(s_OperServ, u, "ADMIN", OPER_ADMIN_SYNTAX); - } else if (!stricmp(cmd, "ADD")) { - if (!is_services_root(u)) { + if (!is_services_root(u)) + { notice_lang(s_OperServ, u, PERMISSION_DENIED); return MOD_CONT; } - if (!(na = findnick(nick))) { + if (!(na = findnick(nick))) + { notice_lang(s_OperServ, u, NICK_X_NOT_REGISTERED, nick); return MOD_CONT; } - if (na->status & NS_VERBOTEN) { + if (na->status & NS_VERBOTEN) + { notice_lang(s_OperServ, u, NICK_X_FORBIDDEN, nick); return MOD_CONT; } - if (na->nc->flags & NI_SERVICES_ADMIN - || slist_indexof(&servadmins, na->nc) != -1) { + if (na->nc->flags & NI_SERVICES_ADMIN || slist_indexof(&servadmins, na->nc) != -1) + { notice_lang(s_OperServ, u, OPER_ADMIN_EXISTS, nick); return MOD_CONT; } res = slist_add(&servadmins, na->nc); - if (res == -2) { + if (res == -2) + { notice_lang(s_OperServ, u, OPER_ADMIN_REACHED_LIMIT, nick); return MOD_CONT; - } else { - if (na->nc->flags & NI_SERVICES_OPER - && (res = slist_indexof(&servopers, na->nc)) != -1) { + } + else + { + if (na->nc->flags & NI_SERVICES_OPER && (res = slist_indexof(&servopers, na->nc)) != -1) + { slist_delete(&servopers, res); na->nc->flags |= NI_SERVICES_ADMIN; notice_lang(s_OperServ, u, OPER_ADMIN_MOVED, nick); - } else { + } + else + { na->nc->flags |= NI_SERVICES_ADMIN; notice_lang(s_OperServ, u, OPER_ADMIN_ADDED, nick); } @@ -106,42 +80,63 @@ int do_admin(User * u) if (readonly) notice_lang(s_OperServ, u, READ_ONLY_MODE); - } else if (!stricmp(cmd, "DEL")) { - if (!is_services_root(u)) { + + return MOD_CONT; + } + + CommandResult DoDel(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params.size() > 1 ? params[1].c_str() : NULL; + int res = 0; + + if (!nick) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + if (!is_services_root(u)) + { notice_lang(s_OperServ, u, PERMISSION_DENIED); return MOD_CONT; } - if (servadmins.count == 0) { + if (!servadmins.count) + { notice_lang(s_OperServ, u, OPER_ADMIN_LIST_EMPTY); return MOD_CONT; } - if (isdigit(*nick) && strspn(nick, "1234567890,-") == strlen(nick)) { + if (isdigit(*nick) && strspn(nick, "1234567890,-") == strlen(nick)) + { /* Deleting a range */ res = slist_delete_range(&servadmins, nick, NULL); - if (res == 0) { + if (!res) + { notice_lang(s_OperServ, u, OPER_ADMIN_NO_MATCH); return MOD_CONT; - } else if (res == 1) { - notice_lang(s_OperServ, u, OPER_ADMIN_DELETED_ONE); - } else { - notice_lang(s_OperServ, u, OPER_ADMIN_DELETED_SEVERAL, - res); } - } else { - if (!(na = findnick(nick))) { + else if (res == 1) + notice_lang(s_OperServ, u, OPER_ADMIN_DELETED_ONE); + else + notice_lang(s_OperServ, u, OPER_ADMIN_DELETED_SEVERAL, res); + } + else + { + if (!(na = findnick(nick))) + { notice_lang(s_OperServ, u, NICK_X_NOT_REGISTERED, nick); return MOD_CONT; } - if (na->status & NS_VERBOTEN) { + if (na->status & NS_VERBOTEN) + { notice_lang(s_OperServ, u, NICK_X_FORBIDDEN, nick); return MOD_CONT; } - if (!(na->nc->flags & NI_SERVICES_ADMIN) - || (res = slist_indexof(&servadmins, na->nc)) == -1) { + if (!(na->nc->flags & NI_SERVICES_ADMIN) || (res = slist_indexof(&servadmins, na->nc)) == -1) + { notice_lang(s_OperServ, u, OPER_ADMIN_NOT_FOUND, nick); return MOD_CONT; } @@ -152,63 +147,118 @@ int do_admin(User * u) if (readonly) notice_lang(s_OperServ, u, READ_ONLY_MODE); - } else if (!stricmp(cmd, "LIST")) { - int sent_header = 0; - if (servadmins.count == 0) { + return MOD_CONT; + } + + CommandResult DoList(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params.size() > 1 ? params[1].c_str() : NULL; + int sent_header = 0, res = 0; + + if (!servadmins.count) + { notice_lang(s_OperServ, u, OPER_ADMIN_LIST_EMPTY); return MOD_CONT; } - if (!nick || (isdigit(*nick) - && strspn(nick, "1234567890,-") == strlen(nick))) { - res = - slist_enum(&servadmins, nick, &admin_list_callback, u, - &sent_header); - if (res == 0) { + if (!nick || (isdigit(*nick) && strspn(nick, "1234567890,-") == strlen(nick))) + { + res = slist_enum(&servadmins, nick, &admin_list_callback, u, &sent_header); + if (!res) + { notice_lang(s_OperServ, u, OPER_ADMIN_NO_MATCH); return MOD_CONT; - } else { - notice_lang(s_OperServ, u, END_OF_ANY_LIST, "Admin"); } - } else { + else + notice_lang(s_OperServ, u, END_OF_ANY_LIST, "Admin"); + } + else + { int i; - for (i = 0; i < servadmins.count; i++) - if (!stricmp - (nick, (static_cast<NickCore *>(servadmins.list[i]))->display) - || match_wild_nocase(nick, - (static_cast<NickCore *>(servadmins. - list[i]))->display)) + for (i = 0; i < servadmins.count; ++i) { + if (!stricmp(nick, (static_cast<NickCore *>(servadmins.list[i]))->display) || match_wild_nocase(nick, (static_cast<NickCore *>(servadmins.list[i]))->display)) admin_list(i + 1, static_cast<NickCore *>(servadmins.list[i]), u, &sent_header); + } if (!sent_header) notice_lang(s_OperServ, u, OPER_ADMIN_NO_MATCH); - else { + else notice_lang(s_OperServ, u, END_OF_ANY_LIST, "Admin"); - } } - } else if (!stricmp(cmd, "CLEAR")) { - if (!is_services_root(u)) { + + return MOD_CONT; + } + + CommandResult DoClear(User *u, std::vector<std::string> ¶ms) + { + if (!is_services_root(u)) + { notice_lang(s_OperServ, u, PERMISSION_DENIED); return MOD_CONT; } - if (servadmins.count == 0) { + if (!servadmins.count) + { notice_lang(s_OperServ, u, OPER_ADMIN_LIST_EMPTY); return MOD_CONT; } slist_clear(&servadmins, 1); notice_lang(s_OperServ, u, OPER_ADMIN_CLEAR); - } else { - syntax_error(s_OperServ, u, "ADMIN", OPER_ADMIN_SYNTAX); + + return MOD_CONT; + } + public: + CommandOSAdmin() : Command("ADMIN", 1, 2) + { + this->help_param1 = s_NickServ; + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + + if (!stricmp(cmd, "ADD")) + return this->DoAdd(u, params); + else if (!stricmp(cmd, "DEL")) + return this->DoDel(u, params); + else if (!stricmp(cmd, "LIST")) + return this->DoList(u, params); + else if (!stricmp(cmd, "CLEAR")) + return this->DoClear(u, params); + else + this->OnSyntaxError(u); + return MOD_CONT; } - return MOD_CONT; +}; + +class OSAdmin : public Module +{ + public: + OSAdmin(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + + this->AddCommand(OPERSERV, new CommandOSAdmin(), MOD_UNIQUE); + + this->SetOperHelp(myOperServHelp); + } +}; + +/** + * Add the help response to anopes /os help output. + * @param u The user who is requesting help + **/ +void myOperServHelp(User *u) +{ + notice_lang(s_OperServ, u, OPER_HELP_CMD_ADMIN); } -int admin_list_callback(SList * slist, int number, void *item, - va_list args) +int admin_list_callback(SList *slist, int number, void *item, va_list args) { User *u = va_arg(args, User *); int *sent_header = va_arg(args, int *); @@ -216,18 +266,18 @@ int admin_list_callback(SList * slist, int number, void *item, return admin_list(number, static_cast<NickCore *>(item), u, sent_header); } -int admin_list(int number, NickCore * nc, User * u, int *sent_header) +int admin_list(int number, NickCore *nc, User *u, int *sent_header) { if (!nc) return 0; - if (!*sent_header) { + if (!*sent_header) + { notice_lang(s_OperServ, u, OPER_ADMIN_LIST_HEADER); *sent_header = 1; } - notice_lang(s_OperServ, u, OPER_ADMIN_LIST_FORMAT, number, - nc->display); + notice_lang(s_OperServ, u, OPER_ADMIN_LIST_FORMAT, number, nc->display); return 1; } diff --git a/src/core/os_akill.c b/src/core/os_akill.c index cca6c09f8..9bd6c6cfd 100644 --- a/src/core/os_akill.c +++ b/src/core/os_akill.c @@ -15,75 +15,31 @@ #include "module.h" -int do_akill(User * u); -int akill_view_callback(SList * slist, int number, void *item, - va_list args); -int akill_view(int number, Akill * ak, User * u, int *sent_header); -int akill_list_callback(SList * slist, int number, void *item, - va_list args); -int akill_list(int number, Akill * ak, User * u, int *sent_header); -void myOperServHelp(User * u); +void myOperServHelp(User *u); +int akill_view_callback(SList *slist, int number, void *item, va_list args); +int akill_list_callback(SList *slist, int number, void *item, va_list args); +int akill_view(int number, Akill *ak, User *u, int *sent_header); +int akill_list(int number, Akill *ak, User *u, int *sent_header); -class OSAKill : public Module -{ - public: - OSAKill(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - c = createCommand("AKILL", do_akill, is_services_oper, OPER_HELP_AKILL, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - - this->SetOperHelp(myOperServHelp); - } -}; - - - -/** - * Add the help response to anopes /os help output. - * @param u The user who is requesting help - **/ -void myOperServHelp(User * u) -{ - if (is_services_oper(u)) { - notice_lang(s_OperServ, u, OPER_HELP_CMD_AKILL); - } -} - -/** - * The /os command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -/* Manage the AKILL list. */ - -int do_akill(User * u) +class CommandOSAKill : public Command { - char *cmd = strtok(NULL, " "); - char breason[BUFSIZE]; - - if (!cmd) + private: + CommandResult DoAdd(User *u, std::vector<std::string> ¶ms) { - syntax_error(s_OperServ, u, "AKILL", OPER_AKILL_SYNTAX); - return MOD_CONT; - } - - if (!stricmp(cmd, "ADD")) { - int deleted = 0; - char *expiry, *mask, *reason; + int deleted = 0, last_param = 2; + const char *expiry, *mask; + char reason[BUFSIZE]; time_t expires; - mask = strtok(NULL, " "); - if (mask && *mask == '+') { + mask = params.size() > 1 ? params[1].c_str() : NULL; + if (mask && *mask == '+') + { expiry = mask; - mask = strtok(NULL, " "); - } else { - expiry = NULL; + mask = params.size() > 2 ? params[2].c_str() : NULL; + last_param = 3; } + else + expiry = NULL; expires = expiry ? dotime(expiry) : AutokillExpiry; /* If the expiry given does not contain a final letter, it's in days, @@ -92,26 +48,36 @@ int do_akill(User * u) if (expiry && isdigit(expiry[strlen(expiry) - 1])) expires *= 86400; /* Do not allow less than a minute expiry time */ - if (expires != 0 && expires < 60) { + if (expires != 0 && expires < 60) + { notice_lang(s_OperServ, u, BAD_EXPIRY_TIME); return MOD_CONT; - } else if (expires > 0) { - expires += time(NULL); } + else if (expires > 0) + expires += time(NULL); - if (mask && (reason = strtok(NULL, ""))) { + if (params.size() < last_param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + snprintf(reason, sizeof(reason), "%s%s%s", params[last_param].c_str(), last_param == 2 ? " " : "", last_param == 2 ? param[3].c_str() : ""); + if (mask && *reason) { /* We first do some sanity check on the proposed mask. */ - if (strchr(mask, '!')) { + if (strchr(mask, '!')) + { notice_lang(s_OperServ, u, OPER_AKILL_NO_NICK); return MOD_CONT; } - if (!strchr(mask, '@')) { + if (!strchr(mask, '@')) + { notice_lang(s_OperServ, u, BAD_USERHOST_MASK); return MOD_CONT; } - if (mask && strspn(mask, "~@.*?") == strlen(mask)) { + if (mask && strspn(mask, "~@.*?") == strlen(mask)) + { notice_lang(s_OperServ, u, USERHOST_MASK_TOO_WIDE, mask); return MOD_CONT; } @@ -121,95 +87,95 @@ int do_akill(User * u) * breason to match bufsize * -Rob **/ - if (AddAkiller) { - snprintf(breason, sizeof(breason), "[%s] %s", u->nick, - reason); - reason = sstrdup(breason); - } + if (AddAkiller) + snprintf(reason, sizeof(reason), "[%s] %s", u->nick, reason); deleted = add_akill(u, mask, u->nick, expires, reason); - if (deleted < 0) { - if (AddAkiller) { - delete [] reason; - } + if (deleted < 0) return MOD_CONT; - } else if (deleted) { - notice_lang(s_OperServ, u, OPER_AKILL_DELETED_SEVERAL, - deleted); - } + else if (deleted) + notice_lang(s_OperServ, u, OPER_AKILL_DELETED_SEVERAL, deleted); notice_lang(s_OperServ, u, OPER_AKILL_ADDED, mask); - if (WallOSAkill) { + if (WallOSAkill) + { char buf[128]; - if (!expires) { + if (!expires) strcpy(buf, "does not expire"); - } else { + else + { int wall_expiry = expires - time(NULL); char *s = NULL; - if (wall_expiry >= 86400) { + if (wall_expiry >= 86400) + { wall_expiry /= 86400; s = "day"; - } else if (wall_expiry >= 3600) { + } + else if (wall_expiry >= 3600) + { wall_expiry /= 3600; s = "hour"; - } else if (wall_expiry >= 60) { + } + else if (wall_expiry >= 60) + { wall_expiry /= 60; s = "minute"; } - snprintf(buf, sizeof(buf), "expires in %d %s%s", - wall_expiry, s, - (wall_expiry == 1) ? "" : "s"); + snprintf(buf, sizeof(buf), "expires in %d %s%s", wall_expiry, s, wall_expiry == 1 ? "" : "s"); } - ircdproto->SendGlobops(s_OperServ, - "%s added an AKILL for %s (%s) (%s)", - u->nick, mask, reason, buf); + ircdproto->SendGlobops(s_OperServ, "%s added an AKILL for %s (%s) (%s)", u->nick, mask, reason, buf); } - if (readonly) { + if (readonly) notice_lang(s_OperServ, u, READ_ONLY_MODE); - } - if (AddAkiller) { - delete [] reason; - } - } else { - syntax_error(s_OperServ, u, "AKILL", OPER_AKILL_SYNTAX); } + else + this->OnSyntaxError(u); - } else if (!stricmp(cmd, "DEL")) { + return MOD_CONT; + } - char *mask; + CommandResult DoDel(User *u, std::vector<std::string> ¶ms) + { + const char *mask; int res = 0; - mask = strtok(NULL, " "); + mask = params.size() > 1 ? params[1].c_str(); - if (!mask) { - syntax_error(s_OperServ, u, "AKILL", OPER_AKILL_SYNTAX); + if (!mask) + { + this->OnSyntaxError(u); return MOD_CONT; } - if (akills.count == 0) { + if (!akills.count) + { notice_lang(s_OperServ, u, OPER_AKILL_LIST_EMPTY); return MOD_CONT; } - if (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask)) { + if (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask)) + { /* Deleting a range */ res = slist_delete_range(&akills, mask, NULL); - if (res == 0) { + if (!res) + { notice_lang(s_OperServ, u, OPER_AKILL_NO_MATCH); return MOD_CONT; - } else if (res == 1) { - notice_lang(s_OperServ, u, OPER_AKILL_DELETED_ONE); - } else { - notice_lang(s_OperServ, u, OPER_AKILL_DELETED_SEVERAL, - res); } - } else { - if ((res = slist_indexof(&akills, mask)) == -1) { + else if (res == 1) + notice_lang(s_OperServ, u, OPER_AKILL_DELETED_ONE); + else + notice_lang(s_OperServ, u, OPER_AKILL_DELETED_SEVERAL, res); + } + else + { + if ((res = slist_indexof(&akills, mask)) == -1) + { notice_lang(s_OperServ, u, OPER_AKILL_NOT_FOUND, mask); return MOD_CONT; } @@ -221,93 +187,167 @@ int do_akill(User * u) if (readonly) notice_lang(s_OperServ, u, READ_ONLY_MODE); - } else if (!stricmp(cmd, "LIST")) { - char *mask; + return MOD_CONT; + } + + CommandResult DoList(User *u, std::vector<std::string> ¶ms) + { + const char *mask; int res, sent_header = 0; - if (akills.count == 0) { + if (!akills.count) + { notice_lang(s_OperServ, u, OPER_AKILL_LIST_EMPTY); return MOD_CONT; } - mask = strtok(NULL, " "); + mask = params.size() > 1 ? params[1].c_str() : NULL; - if (!mask || (isdigit(*mask) - && strspn(mask, "1234567890,-") == strlen(mask))) { - res = - slist_enum(&akills, mask, &akill_list_callback, u, - &sent_header); - if (res == 0) { + if (!mask || (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask))) + { + res = slist_enum(&akills, mask, &akill_list_callback, u, &sent_header); + if (!res) + { notice_lang(s_OperServ, u, OPER_AKILL_NO_MATCH); return MOD_CONT; - } else { - notice_lang(s_OperServ, u, END_OF_ANY_LIST, "Akill"); } - } else { + else + notice_lang(s_OperServ, u, END_OF_ANY_LIST, "Akill"); + } + else + { int i; char amask[BUFSIZE]; - for (i = 0; i < akills.count; i++) { - snprintf(amask, sizeof(amask), "%s@%s", - (static_cast<Akill *>(akills.list[i]))->user, - (static_cast<Akill *>(akills.list[i]))->host); - if (!stricmp(mask, amask) - || match_wild_nocase(mask, amask)) + for (i = 0; i < akills.count; ++i) + { + snprintf(amask, sizeof(amask), "%s@%s", (static_cast<Akill *>(akills.list[i]))->user, (static_cast<Akill *>(akills.list[i]))->host); + if (!stricmp(mask, amask) || match_wild_nocase(mask, amask)) akill_list(i + 1, static_cast<Akill *>(akills.list[i]), u, &sent_header); } if (!sent_header) notice_lang(s_OperServ, u, OPER_AKILL_NO_MATCH); - else { + else notice_lang(s_OperServ, u, END_OF_ANY_LIST, "Akill"); - } } - } else if (!stricmp(cmd, "VIEW")) { - char *mask; + + return MOD_CONT; + } + + CommandResult DoView(User *u, std::vector<std::string> ¶ms) + { + const char *mask; int res, sent_header = 0; - if (akills.count == 0) { + if (!akills.count) + { notice_lang(s_OperServ, u, OPER_AKILL_LIST_EMPTY); return MOD_CONT; } - mask = strtok(NULL, " "); + mask = params.size() > 1 ? params[1].c_str() : NULL; - if (!mask || (isdigit(*mask) - && strspn(mask, "1234567890,-") == strlen(mask))) { - res = - slist_enum(&akills, mask, &akill_view_callback, u, - &sent_header); - if (res == 0) { + if (!mask || (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask))) + { + res = slist_enum(&akills, mask, &akill_view_callback, u, &sent_header); + if (!res) + { notice_lang(s_OperServ, u, OPER_AKILL_NO_MATCH); return MOD_CONT; } - } else { + } + else + { int i; char amask[BUFSIZE]; - for (i = 0; i < akills.count; i++) { - snprintf(amask, sizeof(amask), "%s@%s", - (static_cast<Akill *>(akills.list[i]))->user, - (static_cast<Akill *>(akills.list[i]))->host); - if (!stricmp(mask, amask) - || match_wild_nocase(mask, amask)) + for (i = 0; i < akills.count; ++i) + { + snprintf(amask, sizeof(amask), "%s@%s", (static_cast<Akill *>(akills.list[i]))->user, (static_cast<Akill *>(akills.list[i]))->host); + if (!stricmp(mask, amask) || match_wild_nocase(mask, amask)) akill_view(i + 1, static_cast<Akill *>(akills.list[i]), u, &sent_header); } if (!sent_header) notice_lang(s_OperServ, u, OPER_AKILL_NO_MATCH); } - } else if (!stricmp(cmd, "CLEAR")) { + + return MOD_CONT; + } + + CommandResult DoClear(User *u, std::vector<std::string> ¶ms) + { slist_clear(&akills, 1); notice_lang(s_OperServ, u, OPER_AKILL_CLEAR); - } else { + + return MOD_CONT; + } + public: + CommandOSAKill() : Command("AKILL", 1, 4) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + char breason[BUFSIZE]; + + if (!stricmp(cmd, "ADD")) + return this->DoAdd(u, params); + else if (!stricmp(cmd, "DEL")) + return this->DoDel(u, params); + else if (!stricmp(cmd, "LIST")) + return this->DoList(u, params); + else if (!stricmp(cmd, "VIEW")) + return this->DoView(u, params); + else if (!stricmp(cmd, "CLEAR")) + return this->DoClear(u, params); + else + this->OnSyntaxError(u); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_oper(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_AKILL); + return true; + } + + void OnSyntaxError(User *u) + { syntax_error(s_OperServ, u, "AKILL", OPER_AKILL_SYNTAX); } - return MOD_CONT; +}; + +class OSAKill : public Module +{ + public: + OSAKill(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(OPERSERV, new CommandOSAKill(), MOD_UNIQUE); + + this->SetOperHelp(myOperServHelp); + } +}; + +/** + * Add the help response to anopes /os help output. + * @param u The user who is requesting help + **/ +void myOperServHelp(User *u) +{ + if (is_services_oper(u)) + notice_lang(s_OperServ, u, OPER_HELP_CMD_AKILL); } -int akill_view(int number, Akill * ak, User * u, int *sent_header) +int akill_view(int number, Akill *ak, User *u, int *sent_header) { char mask[BUFSIZE]; char timebuf[32], expirebuf[256]; @@ -316,26 +356,23 @@ int akill_view(int number, Akill * ak, User * u, int *sent_header) if (!ak) return 0; - if (!*sent_header) { + if (!*sent_header) + { notice_lang(s_OperServ, u, OPER_AKILL_VIEW_HEADER); *sent_header = 1; } snprintf(mask, sizeof(mask), "%s@%s", ak->user, ak->host); tm = *localtime(&ak->seton); - strftime_lang(timebuf, sizeof(timebuf), u, STRFTIME_SHORT_DATE_FORMAT, - &tm); + strftime_lang(timebuf, sizeof(timebuf), u, STRFTIME_SHORT_DATE_FORMAT, &tm); expire_left(u->na, expirebuf, sizeof(expirebuf), ak->expires); - notice_lang(s_OperServ, u, OPER_AKILL_VIEW_FORMAT, number, mask, - ak->by, timebuf, expirebuf, ak->reason); + notice_lang(s_OperServ, u, OPER_AKILL_VIEW_FORMAT, number, mask, ak->by, timebuf, expirebuf, ak->reason); return 1; } /* Lists an AKILL entry, prefixing it with the header if needed */ - -int akill_list_callback(SList * slist, int number, void *item, - va_list args) +int akill_list_callback(SList *slist, int number, void *item, va_list args) { User *u = va_arg(args, User *); int *sent_header = va_arg(args, int *); @@ -344,9 +381,7 @@ int akill_list_callback(SList * slist, int number, void *item, } /* Callback for enumeration purposes */ - -int akill_view_callback(SList * slist, int number, void *item, - va_list args) +int akill_view_callback(SList *slist, int number, void *item, va_list args) { User *u = va_arg(args, User *); int *sent_header = va_arg(args, int *); @@ -355,21 +390,21 @@ int akill_view_callback(SList * slist, int number, void *item, } /* Lists an AKILL entry, prefixing it with the header if needed */ -int akill_list(int number, Akill * ak, User * u, int *sent_header) +int akill_list(int number, Akill *ak, User *u, int *sent_header) { char mask[BUFSIZE]; if (!ak) return 0; - if (!*sent_header) { + if (!*sent_header) + { notice_lang(s_OperServ, u, OPER_AKILL_LIST_HEADER); *sent_header = 1; } snprintf(mask, sizeof(mask), "%s@%s", ak->user, ak->host); - notice_lang(s_OperServ, u, OPER_AKILL_LIST_FORMAT, number, mask, - ak->reason); + notice_lang(s_OperServ, u, OPER_AKILL_LIST_FORMAT, number, mask, ak->reason); return 1; } diff --git a/src/core/os_chankill.c b/src/core/os_chankill.c index b96b94991..c3318238a 100644 --- a/src/core/os_chankill.c +++ b/src/core/os_chankill.c @@ -15,108 +15,104 @@ #include "module.h" -int do_chankill(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSChanKill : public Command +{ + public: + CommandOSChanKill() : Command("CHANKILL", 2, 3) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *expiry, *channel; + char reason[BUFSIZE]; + time_t expires; + char breason[BUFSIZE]; + char mask[USERMAX + HOSTMAX + 2]; + struct c_userlist *cu, *next; + int last_param = 1; + Channel *c; + + channel = params[0].c_str(); + if (channel && *channel == '+') + { + expiry = channel; + channel = params[1].c_str(); + last_param = 2; + } + else + expiry = NULL; + + expires = expiry ? dotime(expiry) : ChankillExpiry; + if (expiry && isdigit(expiry[strlen(expiry) - 1])) + expires *= 86400; + if (expires != 0 && expires < 60) + { + notice_lang(s_OperServ, u, BAD_EXPIRY_TIME); + return MOD_CONT; + } + else if (expires > 0) + expires += time(NULL); + + if (params.size() < last_param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + snprintf(reason, sizeof(reason), "%s%s%s", params[last_param].c_str(), last_param == 1 ? " " : "", last_param == 1 ? param[2].c_str() : ""); + if (*reason) + { + + if (AddAkiller) + snprintf(reason, sizeof(reason), "[%s] %s", u->nick, reason); + + if ((c = findchan(channel))) + { + for (cu = c->users; cu; cu = next) + { + next = cu->next; + if (is_oper(cu->user)) + continue; + strncpy(mask, "*@", 3); /* Use *@" for the akill's, */ + strncat(mask, cu->user->host, HOSTMAX); + add_akill(NULL, mask, s_OperServ, expires, reason); + check_akill(cu->user->nick, cu->user->GetIdent().c_str(), cu->user->host, NULL, NULL); + } + if (WallOSAkill) + ircdproto->SendGlobops(s_OperServ, "%s used CHANKILL on %s (%s)", u->nick, channel, reason); + } + else + notice_lang(s_OperServ, u, CHAN_X_NOT_IN_USE, channel); + } + return MOD_CONT; + } +}; class OSChanKill : public Module { public: OSChanKill(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("CHANKILL", do_chankill, is_services_admin, OPER_HELP_CHANKILL, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSChanKill(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } }; - - /** * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_admin(u)) { + if (is_services_admin(u)) notice_lang(s_OperServ, u, OPER_HELP_CMD_CHANKILL); - } -} - -/** - * ChanKill - Akill an entire channel (got botnet?) - * - * /msg OperServ ChanKill +expire #channel reason - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - * - **/ -int do_chankill(User * u) -{ - char *expiry, *channel, *reason; - time_t expires; - char breason[BUFSIZE]; - char mask[USERMAX + HOSTMAX + 2]; - struct c_userlist *cu, *next; - Channel *c; - - channel = strtok(NULL, " "); - if (channel && *channel == '+') { - expiry = channel; - channel = strtok(NULL, " "); - } else { - expiry = NULL; - } - - expires = expiry ? dotime(expiry) : ChankillExpiry; - if (expiry && isdigit(expiry[strlen(expiry) - 1])) - expires *= 86400; - if (expires != 0 && expires < 60) { - notice_lang(s_OperServ, u, BAD_EXPIRY_TIME); - return MOD_CONT; - } else if (expires > 0) { - expires += time(NULL); - } - - if (channel && (reason = strtok(NULL, ""))) { - - if (AddAkiller) { - snprintf(breason, sizeof(breason), "[%s] %s", u->nick, reason); - reason = sstrdup(breason); - } - - if ((c = findchan(channel))) { - for (cu = c->users; cu; cu = next) { - next = cu->next; - if (is_oper(cu->user)) { - continue; - } - strncpy(mask, "*@", 3); /* Use *@" for the akill's, */ - strncat(mask, cu->user->host, HOSTMAX); - add_akill(NULL, mask, s_OperServ, expires, reason); - check_akill(cu->user->nick, cu->user->username, - cu->user->host, NULL, NULL); - } - if (WallOSAkill) { - ircdproto->SendGlobops(s_OperServ, "%s used CHANKILL on %s (%s)", - u->nick, channel, reason); - } - } else { - notice_lang(s_OperServ, u, CHAN_X_NOT_IN_USE, channel); - } - if (AddAkiller) { - delete [] reason; - } - } else { - syntax_error(s_OperServ, u, "CHANKILL", OPER_CHANKILL_SYNTAX); - } - return MOD_CONT; } MODULE_INIT("os_chankill", OSChanKill) diff --git a/src/core/os_chanlist.c b/src/core/os_chanlist.c index e9c780ca5..79edff808 100644 --- a/src/core/os_chanlist.c +++ b/src/core/os_chanlist.c @@ -15,91 +15,95 @@ #include "module.h" -int do_chanlist(User * u); -void myOperServHelp(User * u); -#ifdef _WIN32 -extern MDE int anope_get_private_mode(); -#endif +void myOperServHelp(User *u); + +class CommandOSChanList : public Command +{ + public: + CommandOSChanList() : Command("CHANLIST", 0, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + char *pattern = params.size() > 0 ? params[0].c_str() : NULL; + char *opt = params.size() > 1 ? params[1].c_str() : NULL; + + int modes = 0; + User *u2; + + if (opt && !stricmp(opt, "SECRET")) + modes |= (anope_get_secret_mode() | anope_get_private_mode()); + + if (pattern && (u2 = finduser(pattern))) + { + struct u_chanlist *uc; + + notice_lang(s_OperServ, u, OPER_CHANLIST_HEADER_USER, u2->nick); + + for (uc = u2->chans; uc; uc = uc->next) + { + if (modes && !(uc->chan->mode & modes)) + continue; + notice_lang(s_OperServ, u, OPER_CHANLIST_RECORD, uc->chan->name, uc->chan->usercount, chan_get_modes(uc->chan, 1, 1), uc->chan->topic ? uc->chan->topic : ""); + } + } + else + { + int i; + Channel *c; + + notice_lang(s_OperServ, u, OPER_CHANLIST_HEADER); + + for (i = 0; i < 1024; ++i) + { + for (c = chanlist[i]; c; c = c->next) + { + if (pattern && !match_wild_nocase(pattern, c->name)) + continue; + if (modes && !(c->mode & modes)) + continue; + notice_lang(s_OperServ, u, OPER_CHANLIST_RECORD, c->name, c->usercount, chan_get_modes(c, 1, 1), c->topic ? c->topic : ""); + } + } + } + + notice_lang(s_OperServ, u, OPER_CHANLIST_END); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_oper(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_CHAN_LIST); + return true; + } +}; class OSChanList : public Module { public: OSChanList(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("CHANLIST", do_chanlist, is_services_oper, OPER_HELP_CHANLIST, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSChanList(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } }; - - /** * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { notice_lang(s_OperServ, u, OPER_HELP_CMD_CHANLIST); } -/** - * The /os chanlist command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_chanlist(User * u) -{ - char *pattern = strtok(NULL, " "); - char *opt = strtok(NULL, " "); - - int modes = 0; - User *u2; - - if (opt && !stricmp(opt, "SECRET")) - modes |= (anope_get_secret_mode() | anope_get_private_mode()); - - if (pattern && (u2 = finduser(pattern))) { - struct u_chanlist *uc; - - notice_lang(s_OperServ, u, OPER_CHANLIST_HEADER_USER, u2->nick); - - for (uc = u2->chans; uc; uc = uc->next) { - if (modes && !(uc->chan->mode & modes)) - continue; - notice_lang(s_OperServ, u, OPER_CHANLIST_RECORD, - uc->chan->name, uc->chan->usercount, - chan_get_modes(uc->chan, 1, 1), - (uc->chan->topic ? uc->chan->topic : "")); - } - } else { - int i; - Channel *c; - - notice_lang(s_OperServ, u, OPER_CHANLIST_HEADER); - - for (i = 0; i < 1024; i++) { - for (c = chanlist[i]; c; c = c->next) { - if (pattern && !match_wild_nocase(pattern, c->name)) - continue; - if (modes && !(c->mode & modes)) - continue; - notice_lang(s_OperServ, u, OPER_CHANLIST_RECORD, c->name, - c->usercount, chan_get_modes(c, 1, 1), - (c->topic ? c->topic : "")); - } - } - } - - notice_lang(s_OperServ, u, OPER_CHANLIST_END); - return MOD_CONT; -} - MODULE_INIT("os_chanlist", OSChanList) diff --git a/src/core/os_clearmodes.c b/src/core/os_clearmodes.c index 8d7fd29c8..314f0ed8b 100644 --- a/src/core/os_clearmodes.c +++ b/src/core/os_clearmodes.c @@ -15,283 +15,262 @@ #include "module.h" -int do_clearmodes(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); -class OSClearModes : public Module +class CommandOSClearModes : public Command { public: - OSClearModes(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandOSClearModes() : Command("CLEARMODES", 1, 2) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion - ("$Id$"); - this->SetType(CORE); - - c = createCommand("CLEARMODES", do_clearmodes, is_services_oper, OPER_HELP_CLEARMODES, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - - this->SetOperHelp(myOperServHelp); - } -}; - - -/** - * Add the help response to anopes /os help output. - * @param u The user who is requesting help - **/ -void myOperServHelp(User * u) -{ - if (is_services_oper(u)) { - notice_lang(s_OperServ, u, OPER_HELP_CMD_CLEARMODES); } -} -/** - * The /os clearmodes command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_clearmodes(User * u) -{ - char *s; - const char *argv[2]; - char *chan = strtok(NULL, " "); - Channel *c; - int all = 0; - struct c_userlist *cu, *next; - Entry *entry, *nexte; + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *s; + const char *argv[2]; + const char *chan = params[0].c_str(); + Channel *c; + int all = 0; + struct c_userlist *cu, *next; + Entry *entry, *nexte; - if (!chan) { - syntax_error(s_OperServ, u, "CLEARMODES", OPER_CLEARMODES_SYNTAX); - return MOD_CONT; - } else if (!(c = findchan(chan))) { - notice_lang(s_OperServ, u, CHAN_X_NOT_IN_USE, chan); - return MOD_CONT; - } else if (c->bouncy_modes) { - notice_lang(s_OperServ, u, OPER_BOUNCY_MODES_U_LINE); - return MOD_CONT; - } else { - s = strtok(NULL, " "); - if (s) { - if (stricmp(s, "ALL") == 0) { - all = 1; - } else { - syntax_error(s_OperServ, u, "CLEARMODES", - OPER_CLEARMODES_SYNTAX); - return MOD_CONT; - } + if (!(c = findchan(chan))) + { + notice_lang(s_OperServ, u, CHAN_X_NOT_IN_USE, chan); + return MOD_CONT; } - - if (WallOSClearmodes) { - ircdproto->SendGlobops(s_OperServ, "%s used CLEARMODES%s on %s", - u->nick, all ? " ALL" : "", chan); + else if (c->bouncy_modes) + { + notice_lang(s_OperServ, u, OPER_BOUNCY_MODES_U_LINE); + return MOD_CONT; } - if (all) { - /* Clear mode +o */ - if (ircd->svsmode_ucmode) { - ircdproto->SendSVSModeChan(c->name, "-o", NULL); - for (cu = c->users; cu; cu = next) { - next = cu->next; - if (!chan_has_user_status(c, cu->user, CUS_OP)) { - continue; - } - argv[0] = "-o"; - argv[1] = cu->user->nick; - chan_set_modes(s_OperServ, c, 2, argv, 0); + else + { + s = params.size() > 1 ? params[1].c_str() : NULL; + if (s) { + if (!stricmp(s, "ALL")) + all = 1; + else { + this->OnSyntaxError(u); + return MOD_CONT; } - } else { - for (cu = c->users; cu; cu = next) { + } + + if (WallOSClearmodes) + ircdproto->SendGlobops(s_OperServ, "%s used CLEARMODES%s on %s", u->nick, all ? " ALL" : "", chan); + if (all) + { + /* Clear mode +o */ + if (ircd->svsmode_ucmode) + ircdproto->SendSVSModeChan(c->name, "-o", NULL); + for (cu = c->users; cu; cu = next) + { next = cu->next; if (!chan_has_user_status(c, cu->user, CUS_OP)) continue; argv[0] = "-o"; argv[1] = cu->user->nick; - ircdproto->SendMode(findbot(s_OperServ), c->name, "-o %s", - cu->user->nick); + if (!ircd->svsmode_ucmode) + ircdproto->SendMode(findbot(s_OperServ), c->name, "-o %s", cu->user->nick); chan_set_modes(s_OperServ, c, 2, argv, 0); } - } - if (ircd->svsmode_ucmode) { - ircdproto->SendSVSModeChan(c->name, "-v", NULL); - for (cu = c->users; cu; cu = next) { - next = cu->next; - if (!chan_has_user_status(c, cu->user, CUS_VOICE)) { - continue; - } - argv[0] = "-v"; - argv[1] = cu->user->nick; - chan_set_modes(s_OperServ, c, 2, argv, 0); - } - } else { /* Clear mode +v */ - for (cu = c->users; cu; cu = next) { + if (ircd->svsmode_ucmode) + ircdproto->SendSVSModeChan(c->name, "-v", NULL); + for (cu = c->users; cu; cu = next) + { next = cu->next; if (!chan_has_user_status(c, cu->user, CUS_VOICE)) continue; argv[0] = "-v"; argv[1] = cu->user->nick; - ircdproto->SendMode(findbot(s_OperServ), c->name, "-v %s", - cu->user->nick); + if (!ircd->svsmode_ucmode) + ircdproto->SendMode(findbot(s_OperServ), c->name, "-v %s", cu->user->nick); chan_set_modes(s_OperServ, c, 2, argv, 0); } - } - /* Clear mode +h */ - if (ircd->svsmode_ucmode && ircd->halfop) { - ircdproto->SendSVSModeChan(c->name, "-h", NULL); - for (cu = c->users; cu; cu = next) { - next = cu->next; - if (!chan_has_user_status(c, cu->user, CUS_HALFOP)) { - continue; + /* Clear mode +h */ + if (ircd->halfop) + { + if (ircd->svsmode_ucmode) + ircdproto->SendSVSModeChan(c->name, "-h", NULL); + for (cu = c->users; cu; cu = next) + { + next = cu->next; + if (!chan_has_user_status(c, cu->user, CUS_HALFOP)) + continue; + argv[0] = "-h"; + argv[1] = cu->user->nick; + if (!ircd->svsmode_ucmode) + ircdproto->SendMode(findbot(s_OperServ), c->name, "-h %s", cu->user->nick); + chan_set_modes(s_OperServ, c, 2, argv, 0); } - argv[0] = "-h"; - argv[1] = cu->user->nick; - chan_set_modes(s_OperServ, c, 2, argv, 0); } - } else { - for (cu = c->users; cu; cu = next) { - next = cu->next; - if (!chan_has_user_status(c, cu->user, CUS_HALFOP)) - continue; - argv[0] = "-h"; - argv[1] = cu->user->nick; - ircdproto->SendMode(findbot(s_OperServ), c->name, "-h %s", - cu->user->nick); - chan_set_modes(s_OperServ, c, 2, argv, 0); + + /* Clear mode Owners */ + if (ircd->owner) + { + if (ircd->svsmode_ucmode) + ircdproto->SendSVSModeChan(c->name, ircd->ownerunset, NULL); + for (cu = c->users; cu; cu = next) + { + next = cu->next; + if (!chan_has_user_status(c, cu->user, CUS_OWNER)) + continue; + argv[0] = ircd->ownerunset; + argv[1] = cu->user->nick; + if (!ircd->svsmode_ucmode) + ircdproto->SendMode(findbot(s_OperServ), c->name, "%s %s", ircd->ownerunset, cu->user->nick); + chan_set_modes(s_OperServ, c, 2, argv, 0); + } } - } - /* Clear mode Owners */ - if (ircd->svsmode_ucmode && ircd->owner) { - ircdproto->SendSVSModeChan(c->name, ircd->ownerunset, NULL); - for (cu = c->users; cu; cu = next) { - next = cu->next; - if (!chan_has_user_status(c, cu->user, CUS_HALFOP)) { - continue; + + /* Clear mode protected or admins */ + if (ircd->protect || ircd->admin) + { + if (ircd->svsmode_ucmode) + ircdproto->SendSVSModeChan(c->name, ircd->adminunset, NULL); + for (cu = c->users; cu; cu = next) + { + next = cu->next; + if (!chan_has_user_status(c, cu->user, CUS_PROTECT)) + continue; + argv[0] = ircd->adminunset; + argv[1] = cu->user->nick; + if (!ircd->svsmode_ucmode) + ircdproto->SendMode(findbot(s_OperServ), c->name, "%s %s", ircd->adminunset, cu->user->nick); + chan_set_modes(s_OperServ, c, 2, argv, 0); } - argv[0] = ircd->ownerunset; - argv[1] = cu->user->nick; + } + } + + if (c->mode) + { + /* Clear modes the bulk of the modes */ + ircdproto->SendMode(findbot(s_OperServ), c->name, "%s", ircd->modestoremove); + argv[0] = ircd->modestoremove; + chan_set_modes(s_OperServ, c, 1, argv, 0); + + /* to prevent the internals from complaining send -k, -L, -f by themselves if we need + to send them - TSL */ + if (c->key) + { + ircdproto->SendMode(findbot(s_OperServ), c->name, "-k %s", c->key); + argv[0] = "-k"; + argv[1] = c->key; chan_set_modes(s_OperServ, c, 2, argv, 0); } - } else { - for (cu = c->users; cu; cu = next) { - next = cu->next; - if (!chan_has_user_status(c, cu->user, CUS_OWNER)) - continue; - argv[0] = ircd->ownerunset; - argv[1] = cu->user->nick; - ircdproto->SendMode(findbot(s_OperServ), c->name, "%s %s", - ircd->ownerunset, cu->user->nick); + if (ircd->Lmode && c->redirect) + { + ircdproto->SendMode(findbot(s_OperServ), c->name, "-L %s", c->redirect); + argv[0] = "-L"; + argv[1] = c->redirect; chan_set_modes(s_OperServ, c, 2, argv, 0); } + if (ircd->fmode && c->flood) + { + if (flood_mode_char_remove) + { + ircdproto->SendMode(findbot(s_OperServ), c->name, "%s %s", flood_mode_char_remove, c->flood); + argv[0] = flood_mode_char_remove; + argv[1] = c->flood; + chan_set_modes(s_OperServ, c, 2, argv, 0); + } + else + { + if (debug) + alog("debug: flood_mode_char_remove was not set unable to remove flood/throttle modes"); + } + } } - /* Clear mode protected or admins */ - if (ircd->svsmode_ucmode && (ircd->protect || ircd->admin)) { - ircdproto->SendSVSModeChan(c->name, ircd->adminunset, NULL); - for (cu = c->users; cu; cu = next) { - next = cu->next; - if (!chan_has_user_status(c, cu->user, CUS_HALFOP)) { - continue; - } - argv[0] = ircd->adminunset; - argv[1] = cu->user->nick; + /* Clear bans */ + if (c->bans && c->bans->count) + { + for (entry = c->bans->entries; entry; entry = nexte) + { + nexte = entry->next; + argv[0] = "-b"; + argv[1] = entry->mask; + ircdproto->SendMode(findbot(s_OperServ), c->name, "-b %s", entry->mask); chan_set_modes(s_OperServ, c, 2, argv, 0); } - } else { - for (cu = c->users; cu; cu = next) { - next = cu->next; - if (!chan_has_user_status(c, cu->user, CUS_PROTECT)) - continue; - argv[0] = ircd->adminunset; - argv[1] = cu->user->nick; - ircdproto->SendMode(findbot(s_OperServ), c->name, "%s %s", - ircd->adminunset, cu->user->nick); + } + + /* Clear excepts */ + if (ircd->except && c->excepts && c->excepts->count) + { + for (entry = c->excepts->entries; entry; entry = nexte) + { + nexte = entry->next; + argv[0] = "-e"; + argv[1] = entry->mask; + ircdproto->SendMode(findbot(s_OperServ), c->name, "-e %s", entry->mask); chan_set_modes(s_OperServ, c, 2, argv, 0); } } - - } - - if (c->mode) { - /* Clear modes the bulk of the modes */ - ircdproto->SendMode(findbot(s_OperServ), c->name, "%s", ircd->modestoremove); - argv[0] = ircd->modestoremove; - chan_set_modes(s_OperServ, c, 1, argv, 0); - - /* to prevent the internals from complaining send -k, -L, -f by themselves if we need - to send them - TSL */ - if (c->key) { - ircdproto->SendMode(findbot(s_OperServ), c->name, "-k %s", c->key); - argv[0] = "-k"; - argv[1] = c->key; - chan_set_modes(s_OperServ, c, 2, argv, 0); - } - if (ircd->Lmode && c->redirect) { - ircdproto->SendMode(findbot(s_OperServ), c->name, "-L %s", c->redirect); - argv[0] = "-L"; - argv[1] = c->redirect; - chan_set_modes(s_OperServ, c, 2, argv, 0); - } - if (ircd->fmode && c->flood) { - if (flood_mode_char_remove) { - ircdproto->SendMode(findbot(s_OperServ), c->name, "%s %s", - flood_mode_char_remove, c->flood); - argv[0] = flood_mode_char_remove; - argv[1] = c->flood; + /* Clear invites */ + if (ircd->invitemode && c->invites && c->invites->count) + { + for (entry = c->invites->entries; entry; entry = nexte) + { + nexte = entry->next; + argv[0] = "-I"; + argv[1] = entry->mask; + ircdproto->SendMode(findbot(s_OperServ), c->name, "-I %s", entry->mask); chan_set_modes(s_OperServ, c, 2, argv, 0); - } else { - if (debug) { - alog("debug: flood_mode_char_remove was not set unable to remove flood/throttle modes"); - } } } } - /* Clear bans */ - if (c->bans && c->bans->count) { - for (entry = c->bans->entries; entry; entry = nexte) { - nexte = entry->next; - argv[0] = "-b"; - argv[1] = entry->mask; - ircdproto->SendMode(findbot(s_OperServ), c->name, "-b %s", entry->mask); - chan_set_modes(s_OperServ, c, 2, argv, 0); - } - } + if (all) + notice_lang(s_OperServ, u, OPER_CLEARMODES_ALL_DONE, chan); + else + notice_lang(s_OperServ, u, OPER_CLEARMODES_DONE, chan); - /* Clear excepts */ - if (ircd->except && c->excepts && c->excepts->count) { - for (entry = c->excepts->entries; entry; entry = nexte) { - nexte = entry->next; - argv[0] = "-e"; - argv[1] = entry->mask; - ircdproto->SendMode(findbot(s_OperServ), c->name, "-e %s", entry->mask); - chan_set_modes(s_OperServ, c, 2, argv, 0); - } - } + return MOD_CONT; + } - /* Clear invites */ - if (ircd->invitemode && c->invites && c->invites->count) { - for (entry = c->invites->entries; entry; entry = nexte) { - nexte = entry->next; - argv[0] = "-I"; - argv[1] = entry->mask; - ircdproto->SendMode(findbot(s_OperServ), c->name, "-I %s", entry->mask); - chan_set_modes(s_OperServ, c, 2, argv, 0); - } - } + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_oper(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_CLEARMODES); + return true; } - if (all) { - notice_lang(s_OperServ, u, OPER_CLEARMODES_ALL_DONE, chan); - } else { - notice_lang(s_OperServ, u, OPER_CLEARMODES_DONE, chan); + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "CLEARMODES", OPER_CLEARMODES_SYNTAX); + } +}; + +class OSClearModes : public Module +{ + public: + OSClearModes(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + + this->AddCommand(OPERSERV, new CommandOSClearModes(), MOD_UNIQUE); + + this->SetOperHelp(myOperServHelp); } - return MOD_CONT; +}; + +/** + * Add the help response to anopes /os help output. + * @param u The user who is requesting help + **/ +void myOperServHelp(User *u) +{ + if (is_services_oper(u)) + notice_lang(s_OperServ, u, OPER_HELP_CMD_CLEARMODES); } MODULE_INIT("os_clearmodes", OSClearModes) diff --git a/src/core/os_defcon.c b/src/core/os_defcon.c index 093609fe9..1a3a14317 100644 --- a/src/core/os_defcon.c +++ b/src/core/os_defcon.c @@ -15,144 +15,132 @@ #include "module.h" -#ifdef _WIN32 -extern MDE time_t DefContimer; -extern MDE void runDefCon(); -#endif -int do_defcon(User * u); -void defcon_sendlvls(User * u); +void defcon_sendlvls(User *u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSDEFCON : public Command +{ + public: + CommandOSDEFCON() : Command("DEFCON", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + char *lvl = params[0].c_str(); + int newLevel = 0; + char *langglobal = getstring(NULL, DEFCON_GLOBAL); + + if (!DefConLevel) /* If we dont have a .conf setting! */ + { + notice_lang(s_OperServ, u, OPER_DEFCON_NO_CONF); + return MOD_CONT; + } + + if (!lvl) + { + notice_lang(s_OperServ, u, OPER_DEFCON_CHANGED, DefConLevel); + defcon_sendlvls(u); + return MOD_CONT; + } + newLevel = atoi(lvl); + if (newLevel < 1 || newLevel > 5) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + DefConLevel = newLevel; + send_event(EVENT_DEFCON_LEVEL, 1, lvl); + DefContimer = time(NULL); + notice_lang(s_OperServ, u, OPER_DEFCON_CHANGED, DefConLevel); + defcon_sendlvls(u); + alog("Defcon level changed to %d by Oper %s", newLevel, u->nick); + ircdproto->SendGlobops(s_OperServ, getstring2(NULL, OPER_DEFCON_WALL), u->nick, newLevel); + /* Global notice the user what is happening. Also any Message that + the Admin would like to add. Set in config file. */ + if (GlobalOnDefcon) + { + if (DefConLevel == 5 && DefConOffMessage) + oper_global(NULL, "%s", DefConOffMessage); + else + oper_global(NULL, langglobal, DefConLevel); + } + if (GlobalOnDefconMore) + { + if (!DefConOffMessage || DefConLevel != 5) + oper_global(NULL, "%s", DefconMessage); + } + /* Run any defcon functions, e.g. FORCE CHAN MODE */ + runDefCon(); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_admin(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_DEFCON); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "DEFCON", OPER_DEFCON_SYNTAX); + } +}; class OSDEFCON : public Module { public: OSDEFCON(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("DEFCON", do_defcon, is_services_admin, OPER_HELP_DEFCON, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSDEFCON(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } }; - /** * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_admin(u)) { + if (is_services_admin(u)) notice_lang(s_OperServ, u, OPER_HELP_CMD_DEFCON); - } } /** - * Defcon - A method of impelemting various stages of securty, the hope is this will help serives - * protect a network during an attack, allowing admins to choose the precautions taken at each - * level. - * - * /msg OperServ DefCon [level] - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - * - **/ -int do_defcon(User * u) -{ - char *lvl = strtok(NULL, " "); - int newLevel = 0; - char *langglobal; - langglobal = getstring(NULL, DEFCON_GLOBAL); - - if (!DefConLevel) { /* If we dont have a .conf setting! */ - notice_lang(s_OperServ, u, OPER_DEFCON_NO_CONF); - return MOD_CONT; - } - - if (!lvl) { - notice_lang(s_OperServ, u, OPER_DEFCON_CHANGED, DefConLevel); - defcon_sendlvls(u); - return MOD_CONT; - } - newLevel = atoi(lvl); - if (newLevel < 1 || newLevel > 5) { - notice_lang(s_OperServ, u, OPER_DEFCON_SYNTAX); - return MOD_CONT; - } - DefConLevel = newLevel; - send_event(EVENT_DEFCON_LEVEL, 1, lvl); - DefContimer = time(NULL); - notice_lang(s_OperServ, u, OPER_DEFCON_CHANGED, DefConLevel); - defcon_sendlvls(u); - alog("Defcon level changed to %d by Oper %s", newLevel, u->nick); - ircdproto->SendGlobops(s_OperServ, getstring2(NULL, OPER_DEFCON_WALL), - u->nick, newLevel); - /* Global notice the user what is happening. Also any Message that - the Admin would like to add. Set in config file. */ - if (GlobalOnDefcon) { - if ((DefConLevel == 5) && (DefConOffMessage)) { - oper_global(NULL, "%s", DefConOffMessage); - } else { - oper_global(NULL, langglobal, DefConLevel); - } - } - if (GlobalOnDefconMore) { - if ((DefConOffMessage) && DefConLevel == 5) { - } else { - oper_global(NULL, "%s", DefconMessage); - } - } - /* Run any defcon functions, e.g. FORCE CHAN MODE */ - runDefCon(); - return MOD_CONT; -} - - - -/** * Send a message to the oper about which precautions are "active" for this level **/ -void defcon_sendlvls(User * u) +void defcon_sendlvls(User *u) { - if (checkDefCon(DEFCON_NO_NEW_CHANNELS)) { + if (checkDefCon(DEFCON_NO_NEW_CHANNELS)) notice_lang(s_OperServ, u, OPER_HELP_DEFCON_NO_NEW_CHANNELS); - } - if (checkDefCon(DEFCON_NO_NEW_NICKS)) { + if (checkDefCon(DEFCON_NO_NEW_NICKS)) notice_lang(s_OperServ, u, OPER_HELP_DEFCON_NO_NEW_NICKS); - } - if (checkDefCon(DEFCON_NO_MLOCK_CHANGE)) { + if (checkDefCon(DEFCON_NO_MLOCK_CHANGE)) notice_lang(s_OperServ, u, OPER_HELP_DEFCON_NO_MLOCK_CHANGE); - } - if (checkDefCon(DEFCON_FORCE_CHAN_MODES) && (DefConChanModes)) { - notice_lang(s_OperServ, u, OPER_HELP_DEFCON_FORCE_CHAN_MODES, - DefConChanModes); - } - if (checkDefCon(DEFCON_REDUCE_SESSION)) { - notice_lang(s_OperServ, u, OPER_HELP_DEFCON_REDUCE_SESSION, - DefConSessionLimit); - } - if (checkDefCon(DEFCON_NO_NEW_CLIENTS)) { + if (checkDefCon(DEFCON_FORCE_CHAN_MODES) && DefConChanModes) + notice_lang(s_OperServ, u, OPER_HELP_DEFCON_FORCE_CHAN_MODES, DefConChanModes); + if (checkDefCon(DEFCON_REDUCE_SESSION)) + notice_lang(s_OperServ, u, OPER_HELP_DEFCON_REDUCE_SESSION, DefConSessionLimit); + if (checkDefCon(DEFCON_NO_NEW_CLIENTS)) notice_lang(s_OperServ, u, OPER_HELP_DEFCON_NO_NEW_CLIENTS); - } - if (checkDefCon(DEFCON_OPER_ONLY)) { + if (checkDefCon(DEFCON_OPER_ONLY)) notice_lang(s_OperServ, u, OPER_HELP_DEFCON_OPER_ONLY); - } - if (checkDefCon(DEFCON_SILENT_OPER_ONLY)) { + if (checkDefCon(DEFCON_SILENT_OPER_ONLY)) notice_lang(s_OperServ, u, OPER_HELP_DEFCON_SILENT_OPER_ONLY); - } - if (checkDefCon(DEFCON_AKILL_NEW_CLIENTS)) { + if (checkDefCon(DEFCON_AKILL_NEW_CLIENTS)) notice_lang(s_OperServ, u, OPER_HELP_DEFCON_AKILL_NEW_CLIENTS); - } - if (checkDefCon(DEFCON_NO_NEW_MEMOS)) { + if (checkDefCon(DEFCON_NO_NEW_MEMOS)) notice_lang(s_OperServ, u, OPER_HELP_DEFCON_NO_NEW_MEMOS); - } } MODULE_INIT("os_defcon", OSDEFCON) diff --git a/src/core/os_global.c b/src/core/os_global.c index 2e21e5b91..c05635270 100644 --- a/src/core/os_global.c +++ b/src/core/os_global.c @@ -15,58 +15,63 @@ #include "module.h" -int do_global(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSGlobal : public Command +{ + public: + CommandOSGlobal() : Command("GLOBAL", 1, 1) + { + this->help_param1 = s_GlobalNoticer; + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *msg = params[1].c_str(); + + if (WallOSGlobal) + ircdproto->SendGlobops(s_OperServ, "\2%s\2 just used GLOBAL command.", u->nick); + oper_global(u->nick, "%s", msg); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_admin(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_GLOBAL); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "GLOBAL", OPER_GLOBAL_SYNTAX); + } +}; class OSGlobal : public Module { public: OSGlobal(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("GLOBAL", do_global, is_services_admin, OPER_HELP_GLOBAL, -1, -1, -1, -1); - c->help_param1 = s_GlobalNoticer; - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSGlobal(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } }; - - /** * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_admin(u)) { + if (is_services_admin(u)) notice_lang(s_OperServ, u, OPER_HELP_CMD_GLOBAL); - } -} - -/** - * The /os global command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_global(User * u) -{ - char *msg = strtok(NULL, ""); - - if (!msg) { - syntax_error(s_OperServ, u, "GLOBAL", OPER_GLOBAL_SYNTAX); - return MOD_CONT; - } - if (WallOSGlobal) - ircdproto->SendGlobops(s_OperServ, "\2%s\2 just used GLOBAL command.", - u->nick); - oper_global(u->nick, "%s", msg); - return MOD_CONT; } MODULE_INIT("os_global", OSGlobal) diff --git a/src/core/os_help.c b/src/core/os_help.c index fc76ba420..b2624de37 100644 --- a/src/core/os_help.c +++ b/src/core/os_help.c @@ -6,8 +6,8 @@ * Please read COPYING and README for further details. * * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * + * Based on the original code of Services by Andy Church. + * * $Id$ * */ @@ -15,42 +15,37 @@ #include "module.h" -int do_help(User * u); +class CommandOSHelp : public Command +{ + public: + CommandOSHelp() : Command("HELP", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + mod_help_cmd(s_OperServ, u, OPERSERV, params[0].c_str()); + return MOD_CONT; + } + + void OnSyntaxError(User *u) + { + notice_help(s_OperServ, u, OPER_HELP); + moduleDisplayHelp(5, u); + notice_help(s_OperServ, u, OPER_HELP_LOGGED); + } +}; class OSHelp : public Module { public: OSHelp(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("HELP", do_help, NULL, -1, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSHelp(), MOD_UNIQUE); } }; - - -/** - * The /os help command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_help(User * u) -{ - const char *cmd = strtok(NULL, ""); - - if (!cmd) { - notice_help(s_OperServ, u, OPER_HELP); - moduleDisplayHelp(5, u); - notice_help(s_OperServ, u, OPER_HELP_LOGGED); - } else { - mod_help_cmd(s_OperServ, u, OPERSERV, cmd); - } - return MOD_CONT; -} - MODULE_INIT("os_help", OSHelp) diff --git a/src/core/os_ignore.c b/src/core/os_ignore.c index 4689fe22b..6c8773dc6 100644 --- a/src/core/os_ignore.c +++ b/src/core/os_ignore.c @@ -15,119 +15,149 @@ #include "module.h" -int do_ignorelist(User * u); -void myOperServHelp(User * u); -int do_ignoreuser(User * u); +void myOperServHelp(User *u); -class OSIgnore : public Module +class CommandOSIgnore : public Command { - public: - OSIgnore(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + CommandResult DoAdd(User *u, std::vector<std::string> ¶ms) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - c = createCommand("IGNORE", do_ignoreuser, is_services_admin, OPER_HELP_IGNORE, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - - this->SetOperHelp(myOperServHelp); - } -}; - - -/** - * Add the help response to anopes /os help output. - * @param u The user who is requesting help - **/ -void myOperServHelp(User * u) -{ - if (is_services_admin(u)) { - notice_lang(s_OperServ, u, OPER_HELP_CMD_IGNORE); - } -} - -/** - * The /os ignore command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_ignoreuser(User * u) -{ - char *cmd = strtok(NULL, " "); - int t; - - if (!cmd) { - notice_lang(s_OperServ, u, OPER_IGNORE_SYNTAX); - return MOD_CONT; - } + char *time = params.size() > 1 ? params[1].c_str() : NULL; + char *nick = params.size() > 2 ? params[2].c_str() : NULL; + int t; - if (!stricmp(cmd, "ADD")) { - char *time = strtok(NULL, " "); - char *nick = strtok(NULL, " "); - char *rest = strtok(NULL, ""); - - if (!nick) { - notice_lang(s_OperServ, u, OPER_IGNORE_SYNTAX); - return MOD_CONT; - } else if (!time) { - notice_lang(s_OperServ, u, OPER_IGNORE_SYNTAX); + if (!time || !nick) + { + this->OnSyntaxError(u); return MOD_CONT; - } else { + } + else + { t = dotime(time); - rest = NULL; - if (t <= -1) { + if (t <= -1) + { notice_lang(s_OperServ, u, OPER_IGNORE_VALID_TIME); return MOD_CONT; - } else if (t == 0) { + } + else if (!t) + { add_ignore(nick, t); notice_lang(s_OperServ, u, OPER_IGNORE_PERM_DONE, nick); - } else { + } + else + { add_ignore(nick, t); notice_lang(s_OperServ, u, OPER_IGNORE_TIME_DONE, nick, time); } } - } else if (!stricmp(cmd, "LIST")) { - do_ignorelist(u); - - } else if (!stricmp(cmd, "DEL")) { - char *nick = strtok(NULL, " "); - if (!nick) { - notice_lang(s_OperServ, u, OPER_IGNORE_SYNTAX); - } else { - if (delete_ignore(nick)) { + + return MOD_CONT; + } + + CommandResult DoList(User *u, std::vector<std::string> ¶ms) + { + IgnoreData *id; + + if (!ignore) + { + notice_lang(s_OperServ, u, OPER_IGNORE_LIST_EMPTY); + return MOD_CONT; + } + + notice_lang(s_OperServ, u, OPER_IGNORE_LIST); + for (id = ignore; id; id = id->next) + notice_user(s_OperServ, u, "%s", id->mask); + + return MOD_CONT; + } + + CommandResult DoDel(User *u, std::vector<std::string> ¶ms) + { + char *nick = params.size() > 1 ? params[1].c_str() : NULL; + if (!nick) + this->OnSyntaxError(u); + else + { + if (delete_ignore(nick)) + { notice_lang(s_OperServ, u, OPER_IGNORE_DEL_DONE, nick); return MOD_CONT; } notice_lang(s_OperServ, u, OPER_IGNORE_LIST_NOMATCH, nick); } - } else if (!stricmp(cmd, "CLEAR")) { + + return MOD_CONT; + } + + CommandResult DoClear(User *u, std::vector<std::string> ¶ms) + { clear_ignores(); notice_lang(s_OperServ, u, OPER_IGNORE_LIST_CLEARED); - return MOD_CONT; - } else - notice_lang(s_OperServ, u, OPER_IGNORE_SYNTAX); - return MOD_CONT; -} + return MOD_CONT; + } + public: + CommandOSIgnore() : Command("IGNORE", 1, 4) + { + } -/* shows the Services ignore list */ -int do_ignorelist(User * u) -{ - IgnoreData *id; + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + int t; + + if (!stricmp(cmd, "ADD")) + return this->DoAdd(u, params); + else if (!stricmp(cmd, "LIST")) + return this->DoList(u, params); + else if (!stricmp(cmd, "DEL")) + return this->DoDel(u, params); + else if (!stricmp(cmd, "CLEAR")) + return this->DoCelar(u, params); + else + this->OnSyntaxError(u); - if (!ignore) { - notice_lang(s_OperServ, u, OPER_IGNORE_LIST_EMPTY); return MOD_CONT; } - notice_lang(s_OperServ, u, OPER_IGNORE_LIST); - for (id = ignore; id; id = id->next) - notice_user(s_OperServ, u, "%s", id->mask); + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_admin(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_IGNORE); + return true; + } - return MOD_CONT; + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "IGNORE", OPER_IGNORE_SYNTAX); + } +}; + +class OSIgnore : public Module +{ + public: + OSIgnore(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(OPERSERV, new CommandOSIgnore(), MOD_UNIQUE); + + this->SetOperHelp(myOperServHelp); + } +}; + +/** + * Add the help response to anopes /os help output. + * @param u The user who is requesting help + **/ +void myOperServHelp(User *u) +{ + if (is_services_admin(u)) + notice_lang(s_OperServ, u, OPER_HELP_CMD_IGNORE); } MODULE_INIT("os_ignore", OSIgnore) diff --git a/src/core/os_jupe.c b/src/core/os_jupe.c index c527e4349..5c70b4b4b 100644 --- a/src/core/os_jupe.c +++ b/src/core/os_jupe.c @@ -15,67 +15,74 @@ #include "module.h" -int do_jupe(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSJupe : public Command +{ + public: + CommandOSJupe() : Command("JUPE", 1, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *jserver = params[0].c_str(); + const char *reason = params.size() > 1 ? params[1].c_str() : NULL; + + if (!isValidHost(jserver, 3)) + notice_lang(s_OperServ, u, OPER_JUPE_HOST_ERROR); + else { + char rbuf[256]; + snprintf(rbuf, sizeof(rbuf), "Juped by %s%s%s", u->nick, reason ? ": " : "", reason ? reason : ""); + if (findserver(servlist, jserver)) + ircdproto->SendSquit(jserver, rbuf); + ircdproto->SendServer(jserver, 2, rbuf); + new_server(me_server, jserver, rbuf, SERVER_JUPED, NULL); + + if (WallOSJupe) + ircdproto->SendGlobops(s_OperServ, "\2%s\2 used JUPE on \2%s\2", u->nick, jserver); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_admin(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_JUPE); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "JUPE", OPER_JUPE_SYNTAX); + } +}; class OSJupe : public Module { public: OSJupe(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("JUPE", do_jupe, is_services_admin, OPER_HELP_JUPE, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSJupe(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } }; - /** * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_admin(u)) { + if (is_services_admin(u)) notice_lang(s_OperServ, u, OPER_HELP_CMD_JUPE); - } -} - -/** - * The /os jupe command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_jupe(User * u) -{ - char *jserver = strtok(NULL, " "); - char *reason = strtok(NULL, ""); - - if (!jserver) { - syntax_error(s_OperServ, u, "JUPE", OPER_JUPE_SYNTAX); - } else { - if (!isValidHost(jserver, 3)) { - notice_lang(s_OperServ, u, OPER_JUPE_HOST_ERROR); - } else { - char rbuf[256]; - snprintf(rbuf, sizeof(rbuf), "Juped by %s%s%s", u->nick, reason ? ": " : "", reason ? reason : ""); - if (findserver(servlist, jserver)) ircdproto->SendSquit(jserver, rbuf); - ircdproto->SendServer(jserver, 2, rbuf); - new_server(me_server, jserver, rbuf, SERVER_JUPED, NULL); - - if (WallOSJupe) - ircdproto->SendGlobops(s_OperServ, "\2%s\2 used JUPE on \2%s\2", - u->nick, jserver); - } - } - return MOD_CONT; } MODULE_INIT("os_jupe", OSJupe) diff --git a/src/core/os_kick.c b/src/core/os_kick.c index 89c7a1204..6315835a9 100644 --- a/src/core/os_kick.c +++ b/src/core/os_kick.c @@ -15,75 +15,82 @@ #include "module.h" -int do_os_kick(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSKick : public Command +{ + public: + CommandOSKick() : Command("KICK", 3, 3) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *argv[3]; + const char *chan = params[0].c_str(), *nick = params[1].c_str(), *s = params[2].c_str(); + Channel *c; + + if (!(c = findchan(chan))) + { + notice_lang(s_OperServ, u, CHAN_X_NOT_IN_USE, chan); + return MOD_CONT; + } + else if (c->bouncy_modes) + { + notice_lang(s_OperServ, u, OPER_BOUNCY_MODES_U_LINE); + return MOD_CONT; + } + ircdproto->SendKick(findbot(s_OperServ), chan, nick, "%s (%s)", u->nick, s); + if (WallOSKick) + ircdproto->SendGlobops(s_OperServ, "%s used KICK on %s/%s", u->nick, nick, chan); + argv[0] = sstrdup(chan); + argv[1] = sstrdup(nick); + argv[2] = sstrdup(s); + do_kick(s_OperServ, 3, argv); + delete [] argv[2]; + delete [] argv[1]; + delete [] argv[0]; + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_oper(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_KICK); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "KICK", OPER_KICK_SYNTAX); + } +}; class OSKick : public Module { public: OSKick(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("KICK", do_os_kick, is_services_oper, OPER_HELP_KICK, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSKick(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } }; - /** * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_oper(u)) { + if (is_services_oper(u)) notice_lang(s_OperServ, u, OPER_HELP_CMD_KICK); - } -} - -/** - * The /os kick command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_os_kick(User * u) -{ - const char *argv[3]; - char *chan, *nick, *s; - Channel *c; - - chan = strtok(NULL, " "); - nick = strtok(NULL, " "); - s = strtok(NULL, ""); - if (!chan || !nick || !s) { - syntax_error(s_OperServ, u, "KICK", OPER_KICK_SYNTAX); - return MOD_CONT; - } - if (!(c = findchan(chan))) { - notice_lang(s_OperServ, u, CHAN_X_NOT_IN_USE, chan); - } else if (c->bouncy_modes) { - notice_lang(s_OperServ, u, OPER_BOUNCY_MODES_U_LINE); - return MOD_CONT; - } - ircdproto->SendKick(findbot(s_OperServ), chan, nick, "%s (%s)", u->nick, s); - if (WallOSKick) - ircdproto->SendGlobops(s_OperServ, "%s used KICK on %s/%s", u->nick, - nick, chan); - argv[0] = sstrdup(chan); - argv[1] = sstrdup(nick); - argv[2] = sstrdup(s); - do_kick(s_OperServ, 3, argv); - delete [] argv[2]; - delete [] argv[1]; - delete [] argv[0]; - return MOD_CONT; } MODULE_INIT("os_kick", OSKick) diff --git a/src/core/os_logonnews.c b/src/core/os_logonnews.c deleted file mode 100644 index dea91721d..000000000 --- a/src/core/os_logonnews.c +++ /dev/null @@ -1,94 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2009 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * - * $Id$ - * - */ -/*************************************************************************/ - -#include "module.h" - -Command *c; - -void myOperServHelp(User * u); -int load_config(); -int reload_config(int argc, char **argv); - -class OSLogonNews : public Module -{ - public: - OSLogonNews(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - EvtHook *hook; - char buf[BUFSIZE]; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - /** - * For some unknown reason, do_logonnews is actaully defined in news.c - * we can look at moving it here later - **/ - c = createCommand("LOGONNEWS", do_logonnews, is_services_admin, - NEWS_HELP_LOGON, -1, -1, -1, -1); - snprintf(buf, BUFSIZE, "%d", NewsCount), - c->help_param1 = sstrdup(buf); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - - this->SetOperHelp(myOperServHelp); - - hook = createEventHook(EVENT_RELOAD, reload_config); - if (this->AddEventHook(hook) != MOD_ERR_OK) - { - throw ModuleException("os_logonnews: Can't hook to EVENT_RELOAD event"); - } - } - - ~OSLogonNews() - { - delete [] c->help_param1; - } -}; - - - -/** - * Add the help response to anopes /os help output. - * @param u The user who is requesting help - **/ -void myOperServHelp(User * u) -{ - if (is_services_admin(u)) { - notice_lang(s_OperServ, u, OPER_HELP_CMD_LOGONNEWS); - } -} - - -/** - * Upon /os reload refresh the count - **/ -int reload_config(int argc, char **argv) { - char buf[BUFSIZE]; - - if (argc >= 1) { - if (!stricmp(argv[0], EVENT_START)) { - delete [] c->help_param1; - snprintf(buf, BUFSIZE, "%d", NewsCount), - c->help_param1 = sstrdup(buf); - } - } - - return MOD_CONT; -} - -/* EOF */ - -MODULE_INIT("os_logonnews", OSLogonNews) diff --git a/src/core/os_mode.c b/src/core/os_mode.c index e40e10858..63920702f 100644 --- a/src/core/os_mode.c +++ b/src/core/os_mode.c @@ -15,78 +15,80 @@ #include "module.h" -int do_os_mode(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSMode : public Command +{ + public: + CommandOSMode() : Command("MODE", 2, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + int ac; + const char **av; + char *chan = params[0].c_str(), *modes = params[1].c_str(); + Channel *c; + + if (!(c = findchan(chan))) + notice_lang(s_OperServ, u, CHAN_X_NOT_IN_USE, chan); + else if (c->bouncy_modes) + notice_lang(s_OperServ, u, OPER_BOUNCY_MODES_U_LINE); + else if (ircd->adminmode && !is_services_admin(u) && (c->mode & ircd->adminmode)) + notice_lang(s_OperServ, u, PERMISSION_DENIED); + else + { + ircdproto->SendMode(findbot(s_OperServ), chan, "%s", modes); + + ac = split_buf(modes, &av, 1); + chan_set_modes(s_OperServ, c, ac, av, -1); + free(av); + + if (WallOSMode) + ircdproto->SendGlobops(s_OperServ, "%s used MODE %s on %s", u->nick, modes, chan); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_oper(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_MODE); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "MODE", OPER_MODE_SYNTAX); + } +}; class OSMode : public Module { public: OSMode(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("MODE", do_os_mode, is_services_oper, OPER_HELP_MODE, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSMode(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } }; - - /** * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_oper(u)) { + if (is_services_oper(u)) notice_lang(s_OperServ, u, OPER_HELP_CMD_MODE); - } -} - -/** - * The /os mode command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_os_mode(User * u) -{ - int ac; - const char **av; - char *chan = strtok(NULL, " "), *modes = strtok(NULL, ""); - Channel *c; - - if (!chan || !modes) { - syntax_error(s_OperServ, u, "MODE", OPER_MODE_SYNTAX); - return MOD_CONT; - } - - if (!(c = findchan(chan))) { - notice_lang(s_OperServ, u, CHAN_X_NOT_IN_USE, chan); - } else if (c->bouncy_modes) { - notice_lang(s_OperServ, u, OPER_BOUNCY_MODES_U_LINE); - return MOD_CONT; - } else if ((ircd->adminmode) && (!is_services_admin(u)) - && (c->mode & ircd->adminmode)) { - notice_lang(s_OperServ, u, PERMISSION_DENIED); - return MOD_CONT; - } else { - ircdproto->SendMode(findbot(s_OperServ), chan, "%s", modes); - - ac = split_buf(modes, &av, 1); - chan_set_modes(s_OperServ, c, ac, av, -1); - free(av); - - if (WallOSMode) - ircdproto->SendGlobops(s_OperServ, "%s used MODE %s on %s", u->nick, - modes, chan); - } - return MOD_CONT; } MODULE_INIT("os_mode", OSMode) diff --git a/src/core/os_modinfo.c b/src/core/os_modinfo.c index 840b68d1a..fed7a0b8f 100644 --- a/src/core/os_modinfo.c +++ b/src/core/os_modinfo.c @@ -15,22 +15,67 @@ #include "module.h" -int do_modinfo(User * u); -void myOperServHelp(User * u); -int showModuleCmdLoaded(CommandHash * cmdList, const char *mod_name, User * u); +void myOperServHelp(User *u); +int showModuleCmdLoaded(CommandHash *cmdList, const char *mod_name, User *u); + +class CommandOSModInfo : public Command +{ + public: + CommandOSModInfo() : Command("MODINFO", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *file = params[0].c_str(); + struct tm tm; + char timebuf[64]; + Module *m; + int idx = 0; + + m = findModule(file); + if (m) + { + tm = *localtime(&m->created); + strftime_lang(timebuf, sizeof(timebuf), u, STRFTIME_DATE_TIME_FORMAT, &tm); + notice_lang(s_OperServ, u, OPER_MODULE_INFO_LIST, m->name.c_str(), !m->version.empty() ? m->version.c_str() : "?", !m->author.empty() ? m->author.c_str() : "?", timebuf); + for (idx = 0; idx < MAX_CMD_HASH; ++idx) + { + showModuleCmdLoaded(HOSTSERV[idx], m->name.c_str(), u); + showModuleCmdLoaded(OPERSERV[idx], m->name.c_str(), u); + showModuleCmdLoaded(NICKSERV[idx], m->name.c_str(), u); + showModuleCmdLoaded(CHANSERV[idx], m->name.c_str(), u); + showModuleCmdLoaded(BOTSERV[idx], m->name.c_str(), u); + showModuleCmdLoaded(MEMOSERV[idx], m->name.c_str(), u); + showModuleCmdLoaded(HELPSERV[idx], m->name.c_str(), u); + } + } + else + notice_lang(s_OperServ, u, OPER_MODULE_NO_INFO, file); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_OperServ, u, OPER_HELP_MODINFO); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "MODINFO", OPER_MODULE_INFO_SYNTAX); + } +}; class OSModInfo : public Module { public: OSModInfo(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("MODINFO", do_modinfo, NULL, -1, -1, -1, -1, OPER_HELP_MODINFO); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSModInfo(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } @@ -41,64 +86,25 @@ class OSModInfo : public Module * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { notice_lang(s_OperServ, u, OPER_HELP_CMD_MODINFO); } -/** - * The /os command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_modinfo(User * u) -{ - char *file; - struct tm tm; - char timebuf[64]; - Module *m; - int idx = 0; - - file = strtok(NULL, ""); - if (!file) { - syntax_error(s_OperServ, u, "MODINFO", OPER_MODULE_INFO_SYNTAX); - return MOD_CONT; - } - m = findModule(file); - if (m) { - tm = *localtime(&m->created); - strftime_lang(timebuf, sizeof(timebuf), u, - STRFTIME_DATE_TIME_FORMAT, &tm); - notice_lang(s_OperServ, u, OPER_MODULE_INFO_LIST, m->name.c_str(), - !m->version.empty() ? m->version.c_str() : "?", - !m->author.empty() ? m->author.c_str() : "?", timebuf); - for (idx = 0; idx < MAX_CMD_HASH; idx++) { - showModuleCmdLoaded(HOSTSERV[idx], m->name.c_str(), u); - showModuleCmdLoaded(OPERSERV[idx], m->name.c_str(), u); - showModuleCmdLoaded(NICKSERV[idx], m->name.c_str(), u); - showModuleCmdLoaded(CHANSERV[idx], m->name.c_str(), u); - showModuleCmdLoaded(BOTSERV[idx], m->name.c_str(), u); - showModuleCmdLoaded(MEMOSERV[idx], m->name.c_str(), u); - showModuleCmdLoaded(HELPSERV[idx], m->name.c_str(), u); - } - } else { - notice_lang(s_OperServ, u, OPER_MODULE_NO_INFO, file); - } - return MOD_CONT; -} - -int showModuleCmdLoaded(CommandHash * cmdList, const char *mod_name, User * u) +int showModuleCmdLoaded(CommandHash *cmdList, const char *mod_name, User *u) { Command *c; CommandHash *current; int display = 0; - for (current = cmdList; current; current = current->next) { - for (c = current->c; c; c = c->next) { - if ((c->mod_name) && (stricmp(c->mod_name, mod_name) == 0)) { - notice_lang(s_OperServ, u, OPER_MODULE_CMD_LIST, - c->service, c->name); - display++; + for (current = cmdList; current; current = current->next) + { + for (c = current->c; c; c = c->next) + { + if (c->mod_name && !stricmp(c->mod_name, mod_name)) + { + notice_lang(s_OperServ, u, OPER_MODULE_CMD_LIST, c->service, c->name); + ++display; } } } diff --git a/src/core/os_modlist.c b/src/core/os_modlist.c index 312b29e1c..21a2a1f30 100644 --- a/src/core/os_modlist.c +++ b/src/core/os_modlist.c @@ -15,22 +15,171 @@ #include "module.h" -int do_modlist(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSModList : public Command +{ + public: + CommandOSModList() : Command("MODLIST", 0, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + int idx; + int count = 0; + int showCore = 0; + int showThird = 1; + int showProto = 1; + int showEnc = 1; + int showSupported = 1; + int showQA = 1; + + const char *param = params.size() ? params[0].c_str() : NULL; + ModuleHash *current = NULL; + + char core[] = "Core"; + char third[] = "3rd"; + char proto[] = "Protocol"; + char enc[] = "Encryption"; + char supported[] = "Supported"; + char qa[] = "QATested"; + + if (param) + { + if (!stricmp(param, core)) + { + showCore = 1; + showThird = 0; + showProto = 0; + showEnc = 0; + showSupported = 0; + showQA = 0; + } + else if (!stricmp(param, third)) + { + showCore = 0; + showThird = 1; + showSupported = 0; + showQA = 0; + showProto = 0; + showEnc = 0; + } + else if (!stricmp(param, proto)) + { + showCore = 0; + showThird = 0; + showProto = 1; + showEnc = 0; + showSupported = 0; + showQA = 0; + } + else if (!stricmp(param, supported)) + { + showCore = 0; + showThird = 0; + showProto = 0; + showSupported = 1; + showEnc = 0; + showQA = 0; + } + else if (!stricmp(param, qa)) + { + showCore = 0; + showThird = 0; + showProto = 0; + showSupported = 0; + showEnc = 0; + showQA = 1; + } + else if (!stricmp(param, enc)) + { + showCore = 0; + showThird = 0; + showProto = 0; + showSupported = 0; + showEnc = 1; + showQA = 0; + } + } + + notice_lang(s_OperServ, u, OPER_MODULE_LIST_HEADER); + + for (idx = 0; idx != MAX_CMD_HASH; ++idx) + { + for (current = MODULE_HASH[idx]; current; current = current->next) + { + switch (current->m->type) + { + case CORE: + if (showCore) + { + notice_lang(s_OperServ, u, OPER_MODULE_LIST, current->name, current->m->version.c_str(), core); + ++count; + } + break; + case THIRD: + if (showThird) + { + notice_lang(s_OperServ, u, OPER_MODULE_LIST, current->name, current->m->version.c_str(), third); + ++count; + } + break; + case PROTOCOL: + if (showProto) + { + notice_lang(s_OperServ, u, OPER_MODULE_LIST, current->name, current->m->version.c_str(), proto); + ++count; + } + break; + case SUPPORTED: + if (showSupported) + { + notice_lang(s_OperServ, u, OPER_MODULE_LIST, current->name, current->m->version.c_str(), supported); + ++count; + } + break; + case QATESTED: + if (showQA) + { + notice_lang(s_OperServ, u, OPER_MODULE_LIST, current->name, current->m->version.c_str(), qa); + ++count; + } + break; + case ENCRYPTION: + if (showEnc) + { + notice_lang(s_OperServ, u, OPER_MODULE_LIST, current->name, current->m->version.c_str(), enc); + ++count; + } + } + } + } + if (!count) + notice_lang(s_OperServ, u, OPER_MODULE_NO_LIST); + else + notice_lang(s_OperServ, u, OPER_MODULE_LIST_FOOTER, count); + + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_OperServ, u, OPER_HELP_MODLIST); + return true; + } +}; class OSModList : public Module { public: OSModList(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("MODLIST", do_modlist, NULL, -1, -1, -1, -1, OPER_HELP_MODLIST); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSModList(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } @@ -41,144 +190,9 @@ class OSModList : public Module * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { notice_lang(s_OperServ, u, OPER_HELP_CMD_MODLIST); } -/** - * The /os modlist command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_modlist(User * u) -{ - int idx; - int count = 0; - int showCore = 0; - int showThird = 1; - int showProto = 1; - int showEnc = 1; - int showSupported = 1; - int showQA = 1; - - char *param; - ModuleHash *current = NULL; - - char core[] = "Core"; - char third[] = "3rd"; - char proto[] = "Protocol"; - char enc[] = "Encryption"; - char supported[] = "Supported"; - char qa[] = "QATested"; - - param = strtok(NULL, ""); - if (param) { - if (stricmp(param, core) == 0) { - showCore = 1; - showThird = 0; - showProto = 0; - showEnc = 0; - showSupported = 0; - showQA = 0; - } else if (stricmp(param, third) == 0) { - showCore = 0; - showThird = 1; - showSupported = 0; - showQA = 0; - showProto = 0; - showEnc = 0; - } else if (stricmp(param, proto) == 0) { - showCore = 0; - showThird = 0; - showProto = 1; - showEnc = 0; - showSupported = 0; - showQA = 0; - } else if (stricmp(param, supported) == 0) { - showCore = 0; - showThird = 0; - showProto = 0; - showSupported = 1; - showEnc = 0; - showQA = 0; - } else if (stricmp(param, qa) == 0) { - showCore = 0; - showThird = 0; - showProto = 0; - showSupported = 0; - showEnc = 0; - showQA = 1; - } else if (stricmp(param, enc) == 0) { - showCore = 0; - showThird = 0; - showProto = 0; - showSupported = 0; - showEnc = 1; - showQA = 0; - } - } - - notice_lang(s_OperServ, u, OPER_MODULE_LIST_HEADER); - - for (idx = 0; idx != MAX_CMD_HASH; idx++) { - for (current = MODULE_HASH[idx]; current; current = current->next) { - switch (current->m->type) { - case CORE: - if (showCore) { - notice_lang(s_OperServ, u, OPER_MODULE_LIST, - current->name, current->m->version.c_str(), core); - count++; - } - break; - case THIRD: - if (showThird) { - notice_lang(s_OperServ, u, OPER_MODULE_LIST, - current->name, current->m->version.c_str(), third); - count++; - } - break; - case PROTOCOL: - if (showProto) { - notice_lang(s_OperServ, u, OPER_MODULE_LIST, - current->name, current->m->version.c_str(), proto); - count++; - } - break; - case SUPPORTED: - if (showSupported) { - notice_lang(s_OperServ, u, OPER_MODULE_LIST, - current->name, current->m->version.c_str(), - supported); - count++; - } - break; - case QATESTED: - if (showQA) { - notice_lang(s_OperServ, u, OPER_MODULE_LIST, - current->name, current->m->version.c_str(), qa); - count++; - } - break; - case ENCRYPTION: - if (showEnc) { - notice_lang(s_OperServ, u, OPER_MODULE_LIST, - current->name, current->m->version.c_str(), enc); - count++; - } - break; - - } - - } - } - if (count == 0) { - notice_lang(s_OperServ, u, OPER_MODULE_NO_LIST); - } else { - notice_lang(s_OperServ, u, OPER_MODULE_LIST_FOOTER, count); - } - - return MOD_CONT; -} - MODULE_INIT("os_modlist", OSModList) diff --git a/src/core/os_modload.c b/src/core/os_modload.c index 0f03b090c..c1cb1be86 100644 --- a/src/core/os_modload.c +++ b/src/core/os_modload.c @@ -15,22 +15,67 @@ #include "module.h" -int do_modload(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSModLoad : public Command +{ + public: + CommandOSModLoad() : Command("MODLOAD", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + char *name; + + name = strtok(NULL, ""); + if (!name) + { + syntax_error(s_OperServ, u, "MODLOAD", OPER_MODULE_LOAD_SYNTAX); + return MOD_CONT; + } + + Module *m = findModule(name); + if (m) + { + notice_lang(s_OperServ, u, OPER_MODULE_LOAD_FAIL, name); + return MOD_CONT; + } + + int status = ModuleManager::LoadModule(name, u); + if (status != MOD_ERR_OK) + { + notice_lang(s_OperServ, u, OPER_MODULE_LOAD_FAIL, name); + } + + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_root(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_MODLOAD); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "MODLOAD", OPER_MODULE_LOAD_SYNTAX); + } +}; class OSModLoad : public Module { public: OSModLoad(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("MODLOAD", do_modload, is_services_root, -1, -1, -1, -1, OPER_HELP_MODLOAD); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSModLoad(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } @@ -41,43 +86,10 @@ class OSModLoad : public Module * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_root(u)) { + if (is_services_root(u)) notice_lang(s_OperServ, u, OPER_HELP_CMD_MODLOAD); - } -} - -/** - * The /os modload command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_modload(User * u) -{ - char *name; - - name = strtok(NULL, ""); - if (!name) - { - syntax_error(s_OperServ, u, "MODLOAD", OPER_MODULE_LOAD_SYNTAX); - return MOD_CONT; - } - - Module *m = findModule(name); - if (m) - { - notice_lang(s_OperServ, u, OPER_MODULE_LOAD_FAIL, name); - return MOD_CONT; - } - - int status = ModuleManager::LoadModule(name, u); - if (status != MOD_ERR_OK) - { - notice_lang(s_OperServ, u, OPER_MODULE_LOAD_FAIL, name); - } - - return MOD_CONT; } MODULE_INIT("os_modload", OSModLoad) diff --git a/src/core/os_modunload.c b/src/core/os_modunload.c index 70751e0a4..e9bef9f04 100644 --- a/src/core/os_modunload.c +++ b/src/core/os_modunload.c @@ -15,24 +15,63 @@ #include "module.h" -int do_modunload(User * u); +void myOperServHelp(User *u); -void myOperServHelp(User * u); +class CommandOSModUnLoad : public Command +{ + public: + CommandOSModUnLoad() : Command("MODUNLOAD", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *name = params[0].c_str(); + int status; + + Module *m = findModule(name); + if (!m) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + alog("Trying to unload module [%s]", name); + + status = ModuleManager::UnloadModule(m, u); + + if (status != MOD_ERR_OK) + notice_lang(s_OperServ, u, OPER_MODULE_REMOVE_FAIL, name); + + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_root(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_MODUNLOAD); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "MODUNLOAD", OPER_MODULE_UNLOAD_SYNTAX); + } +}; class OSModUnLoad : public Module { public: OSModUnLoad(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); this->SetPermanent(true); - c = createCommand("MODUNLOAD", do_modunload, is_services_root, -1, -1, -1, -1, OPER_HELP_MODUNLOAD); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSModUnLoad(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } @@ -43,47 +82,10 @@ class OSModUnLoad : public Module * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_root(u)) { + if (is_services_root(u)) notice_lang(s_OperServ, u, OPER_HELP_CMD_MODUNLOAD); - } -} - -/** - * The /os modunload command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_modunload(User *u) -{ - char *name; - int status; - - name = strtok(NULL, ""); - if (!name) - { - syntax_error(s_OperServ, u, "MODUNLOAD", OPER_MODULE_UNLOAD_SYNTAX); - return MOD_CONT; - } - - Module *m = findModule(name); - if (!m) - { - syntax_error(s_OperServ, u, "MODUNLOAD", OPER_MODULE_UNLOAD_SYNTAX); - return MOD_CONT; - } - - alog("Trying to unload module [%s]", name); - - status = ModuleManager::UnloadModule(m, u); - - if (status != MOD_ERR_OK) - { - notice_lang(s_OperServ, u, OPER_MODULE_REMOVE_FAIL, name); - } - - return MOD_CONT; } MODULE_INIT("os_modunload", OSModUnLoad) diff --git a/src/core/os_news.c b/src/core/os_news.c new file mode 100644 index 000000000..bbf1018c1 --- /dev/null +++ b/src/core/os_news.c @@ -0,0 +1,336 @@ +/* OperServ core functions + * + * (C) 2003-2008 Anope Team + * Contact us at info@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + * + * $Id$ + * + */ +/*************************************************************************/ + +#include "module.h" + +void myOperServHelp(User *u); +int reload_config(int argc, char **argv); + +class NewsBase : public Command +{ + private: + CommandResult DoList(User *u, std::vector<std::string> ¶ms, short type, int *msgs) + { + int i, count = 0; + char timebuf[64]; + struct tm *tm; + + for (i = 0; i < nnews; ++i) + { + if (news[i].type == type) + { + if (!count) + notice_lang(s_OperServ, u, msgs[MSG_LIST_HEADER]); + tm = localtime(&news[i].time); + strftime_lang(timebuf, sizeof(timebuf), u, STRFTIME_DATE_TIME_FORMAT, tm); + notice_lang(s_OperServ, u, msgs[MSG_LIST_ENTRY], news[i].num, timebuf, *news[i].who ? news[i].who : "<unknown>", news[i].text); + ++count; + } + } + if (!count) + notice_lang(s_OperServ, u, msgs[MSG_LIST_NONE]); + else + notice_lang(s_OperServ, u, END_OF_ANY_LIST, "News"); + + return MOD_CONT; + } + + CommandResult DoAdd(User *u, std::vector<std::string> ¶ms, short type, int *msgs) + { + const char *text = params.size() > 1 ? params[1].c_str() : NULL; + int n; + + if (!text) + this->OnSyntaxError(u); + else + { + if (readonly) + { + notice_lang(s_OperServ, u, READ_ONLY_MODE); + return MOD_CONT; + } + n = add_newsitem(u, text, type); + if (n < 0) + notice_lang(s_OperServ, u, msgs[MSG_ADD_FULL]); + else + notice_lang(s_OperServ, u, msgs[MSG_ADDED], n); + } + + return MOD_CONT; + } + + CommandResult DoDel(User *u, std::vector<std::string> ¶ms, short type, int *msgs) + { + const char *text = params.size() > 1 ? params[1].c_str() : NULL; + int i, num; + + if (!text) + this->OnSyntaxError(u); + else + { + if (readonly) + { + notice_lang(s_OperServ, u, READ_ONLY_MODE); + return MOD_CONT; + } + if (stricmp(text, "ALL")) + { + num = atoi(text); + if (num > 0 && del_newsitem(num, type)) + { + notice_lang(s_OperServ, u, msgs[MSG_DELETED], num); + /* Reset the order - #0000397 */ + for (i = 0; i < nnews; ++i) + { + if (news[i].type == type && news[i].num > num) + --news[i].num; + } + } + else + notice_lang(s_OperServ, u, msgs[MSG_DEL_NOT_FOUND], num); + } + else + { + if (del_newsitem(0, type)) + notice_lang(s_OperServ, u, msgs[MSG_DELETED_ALL]); + else + notice_lang(s_OperServ, u, msgs[MSG_DEL_NONE]); + } + } + + return MOD_CONT; + } + + CommandResult DoNews(User *u, std::vector<std::string> ¶ms, short type) + { + int is_servadmin = is_services_admin(u); + const char *cmd = params[0].c_str(); + const char *type_name; + int *msgs; + + msgs = findmsgs(type, &type_name); + if (!msgs) + { + alog("news: Invalid type to do_news()"); + return; + } + + if (!stricmp(cmd, "LIST")) + return this->DoList(u, params, type, msgs); + else if (!stricmp(cmd, "ADD")) + { + if (is_servadmin) + return this->DoAdd(u, params, type, msgs); + else + notice_lang(s_OperServ, u, PERMISSION_DENIED); + } + else if (!stricmp(cmd, "DEL")) + { + if (is_servadmin) + return this->DoDel(u, params, type, msgs); + else + notice_lang(s_OperServ, u, PERMISSION_DENIED); + } + else + this->OnSyntaxError(u); + } + public: + NewsBase(const std::string &newstype) : Command(newstype, 1, 2) + { + } + + virtual ~NewsBase() + { + } + + virtual CommandResult Execute(User *u, std::vector<std::string> ¶ms) = 0; + + virtual bool OnHelp(User *u, const std::string &subcommand) = 0; + + virtual void OnSyntaxError(User *u) = 0; +}; + +class CommandOSLogonNews : public NewsBase +{ + public: + CommandOSLogonNews() : NewsBase("LOGONNEWS") + { + this->help_param1 = NULL; + + this->UpdateHelpParam(); + } + + ~CommandOSLogonNews() + { + delete [] this->help_param1; + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + return this->DoNews(u, params, NEWS_LOGON); + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_admin(u)) + return false; + + notice_lang(s_OperServ, u, NEWS_HELP_LOGON); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "LOGONNEWS", NEWS_LOGON_SYNTAX); + } + + void UpdateHelpParam() + { + if (this->help_param1) + delete [] this->help_param1; + + char buf[BUFSIZE]; + + snprintf(buf, BUFSIZE, "%d", NewsCount), + this->help_param1 = sstrdup(buf); + } +} *OSLogonNews = NULL; + +class CommandOSOperNews : public NewsBase +{ + public: + CommandOSOperNews() : NewsBase("OPERNEWS") + { + this->help_param1 = NULL; + + this->UpdateHelpParam(); + } + + ~CommandOSOperNews() + { + delete [] this->help_param1; + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + return this->DoNews(u, params, NEWS_OPER); + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_admin(u)) + return false; + + notice_lang(s_OperServ, u, NEWS_HELP_OPER); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "OPERNEWS", NEWS_OPER_SYNTAX); + } + + void UpdateHelpParam() + { + if (this->help_param1) + delete [] this->help_param1; + + char buf[BUFSIZE]; + + snprintf(buf, BUFSIZE, "%d", NewsCount), + this->help_param1 = sstrdup(buf); + } +} *OSOperNews = NULL; + +class CommandOSRandomNews : public NewsBase +{ + public: + CommandOSRandomNews() : NewsBase("RANDOMNEWS") + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + return this->DoNews(u, params, NEWS_RANDOM); + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_admin(u)) + return false; + + notice_lang(s_OperServ, u, NEWS_HELP_RANDOM); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "RANDOMNEWS", NEWS_RANDOM_SYNTAX); + } +}; + +class OSNews : public Module +{ + public: + OSNews(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + + OSLogonNews = new CommandOSLogonNews(); + this->AddCommand(OPERSERV, OSLogonNews, MOD_UNIQUE); + OSOperNews = new CommandOSOperNews(); + this->AddCommand(OPERSERV, OSOperNews, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSRandomNews(), MOD_UNIQUE); + + this->SetOperHelp(myOperServHelp); + + EvtHook *hook = createEventHook(EVENT_RELOAD, reload_config); + if (this->AddEventHook(hook) != MOD_ERR_OK) + throw ModuleException("os_news: Can't hook to EVENT_RELOAD event"); + } +}; + + +/** + * Add the help response to anopes /os help output. + * @param u The user who is requesting help + **/ +void myOperServHelp(User *u) +{ + if (is_services_admin(u)) + { + notice_lang(s_OperServ, u, OPER_HELP_CMD_LOGONNEWS); + notice_lang(s_OperServ, u, OPER_HELP_CMD_OPERNEWS); + notice_lang(s_OperServ, u, OPER_HELP_CMD_RANDOMNEWS); + } +} + +/** + * Upon /os reload refresh the count + **/ +int reload_config(int argc, char **argv) +{ + if (argc >= 1 && !stricmp(argv[0], EVENT_START)) + { + OSLogonNews->UpdateHelpParam(); + OSOperNews->UpdateHelpParam(); + } + + return MOD_CONT; +} + +MODULE_INIT("os_news", OSNews) diff --git a/src/core/os_noop.c b/src/core/os_noop.c index 9f3f3df7e..98186c7dc 100644 --- a/src/core/os_noop.c +++ b/src/core/os_noop.c @@ -15,22 +15,77 @@ #include "module.h" -int do_noop(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSNOOP : public Command +{ + public: + CommandOSNOOP() : Command("NOOP", 2, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + const char *server = params[1].c_str(); + + if (!stricmp(cmd, "SET")) + { + User *u2; + User *u3 = NULL; + char reason[NICKMAX + 32]; + + /* Remove the O:lines */ + ircdproto->SendSVSNOOP(server, 1); + + snprintf(reason, sizeof(reason), "NOOP command used by %s", u->nick); + if (WallOSNoOp) + ircdproto->SendGlobops(s_OperServ, "\2%s\2 used NOOP on \2%s\2", u->nick, server); + notice_lang(s_OperServ, u, OPER_NOOP_SET, server); + + /* Kill all the IRCops of the server */ + for (u2 = firstuser(); u2; u2 = u3) + { + u3 = nextuser(); + if (u2 && is_oper(u2) && u2->server->name && match_wild(server, u2->server->name)) + kill_user(s_OperServ, u2->nick, reason); + } + } + else if (!stricmp(cmd, "REVOKE")) + { + ircdproto->SendSVSNOOP(server, 0); + notice_lang(s_OperServ, u, OPER_NOOP_REVOKE, server); + } + else + this->OnSyntaxError(u); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_admin(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_NOOP); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "NOOP", OPER_NOOP_SYNTAX); + } +} class OSNOOP : public Module { public: OSNOOP(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("NOOP", do_noop, is_services_admin, OPER_HELP_NOOP, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSNOOP(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } @@ -42,55 +97,10 @@ class OSNOOP : public Module * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_admin(u)) { + if (is_services_admin(u)) notice_lang(s_OperServ, u, OPER_HELP_CMD_NOOP); - } -} - -/** - * The /os noop command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_noop(User * u) -{ - char *cmd = strtok(NULL, " "); - char *server = strtok(NULL, " "); - - if (!cmd || !server) { - syntax_error(s_OperServ, u, "NOOP", OPER_NOOP_SYNTAX); - } else if (!stricmp(cmd, "SET")) { - User *u2; - User *u3 = NULL; - char reason[NICKMAX + 32]; - - /* Remove the O:lines */ - ircdproto->SendSVSNOOP(server, 1); - - snprintf(reason, sizeof(reason), "NOOP command used by %s", - u->nick); - if (WallOSNoOp) - ircdproto->SendGlobops(s_OperServ, "\2%s\2 used NOOP on \2%s\2", - u->nick, server); - notice_lang(s_OperServ, u, OPER_NOOP_SET, server); - - /* Kill all the IRCops of the server */ - for (u2 = firstuser(); u2; u2 = u3) { - u3 = nextuser(); - if ((u2) && is_oper(u2) && (u2->server->name) - && match_wild(server, u2->server->name)) { - kill_user(s_OperServ, u2->nick, reason); - } - } - } else if (!stricmp(cmd, "REVOKE")) { - ircdproto->SendSVSNOOP(server, 0); - notice_lang(s_OperServ, u, OPER_NOOP_REVOKE, server); - } else { - syntax_error(s_OperServ, u, "NOOP", OPER_NOOP_SYNTAX); - } - return MOD_CONT; } MODULE_INIT("os_noop", OSNOOP) diff --git a/src/core/os_oline.c b/src/core/os_oline.c index 1764e401c..66f811b2c 100644 --- a/src/core/os_oline.c +++ b/src/core/os_oline.c @@ -14,23 +14,77 @@ /*************************************************************************/ #include "module.h" -int do_operoline(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSOLine : public Command +{ + public: + CommandOSOLine() : Command("OLINE", 2, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[0].c_str(); + const char *flags = params[1].c_str(); + User *u2 = NULL; + + /* Only allow this if SuperAdmin is enabled */ + if (!u->isSuperAdmin) + { + notice_lang(s_OperServ, u, OPER_SUPER_ADMIN_ONLY); + return MOD_CONT; + } + + /* let's check whether the user is online */ + if (!(u2 = finduser(nick))) + notice_lang(s_OperServ, u, NICK_X_NOT_IN_USE, nick); + else if (u2 && flags[0] == '+') + { + ircdproto->SendSVSO(s_OperServ, nick, flags); + ircdproto->SendMode(findbot(s_OperServ), nick, "+o"); + common_svsmode(u2, "+o", NULL); + notice_lang(s_OperServ, u2, OPER_OLINE_IRCOP); + notice_lang(s_OperServ, u, OPER_OLINE_SUCCESS, flags, nick); + ircdproto->SendGlobops(s_OperServ, "\2%s\2 used OLINE for %s", u->nick, nick); + } + else if (u2 && flags[0] == '-') + { + ircdproto->SendSVSO(s_OperServ, nick, flags); + notice_lang(s_OperServ, u, OPER_OLINE_SUCCESS, flags, nick); + ircdproto->SendGlobops(s_OperServ, "\2%s\2 used OLINE for %s", u->nick, nick); + } + else + this->OnSyntaxError(u); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_root(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_OLINE); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "OLINE", OPER_OLINE_SYNTAX); + } +}; class OSOLine : public Module { public: OSOLine(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("OLINE", do_operoline, is_services_root, OPER_HELP_OLINE, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSOLine(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); @@ -45,54 +99,10 @@ class OSOLine : public Module * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_admin(u) && u->isSuperAdmin) { + if (is_services_admin(u) && u->isSuperAdmin) notice_lang(s_OperServ, u, OPER_HELP_CMD_OLINE); - } -} - -/** - * The /os oline command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_operoline(User * u) -{ - char *nick = strtok(NULL, " "); - char *flags = strtok(NULL, ""); - User *u2 = NULL; - - /* Only allow this if SuperAdmin is enabled */ - if (!u->isSuperAdmin) { - notice_lang(s_OperServ, u, OPER_SUPER_ADMIN_ONLY); - return MOD_CONT; - } - - if (!nick || !flags) { - syntax_error(s_OperServ, u, "OLINE", OPER_OLINE_SYNTAX); - return MOD_CONT; - } else { - /* let's check whether the user is online */ - if (!(u2 = finduser(nick))) { - notice_lang(s_OperServ, u, NICK_X_NOT_IN_USE, nick); - } else if (u2 && flags[0] == '+') { - ircdproto->SendSVSO(s_OperServ, nick, flags); - ircdproto->SendMode(findbot(s_OperServ), nick, "+o"); - common_svsmode(u2, "+o", NULL); - notice_lang(s_OperServ, u2, OPER_OLINE_IRCOP); - notice_lang(s_OperServ, u, OPER_OLINE_SUCCESS, flags, nick); - ircdproto->SendGlobops(s_OperServ, "\2%s\2 used OLINE for %s", - u->nick, nick); - } else if (u2 && flags[0] == '-') { - ircdproto->SendSVSO(s_OperServ, nick, flags); - notice_lang(s_OperServ, u, OPER_OLINE_SUCCESS, flags, nick); - ircdproto->SendGlobops(s_OperServ, "\2%s\2 used OLINE for %s", - u->nick, nick); - } else - syntax_error(s_OperServ, u, "OLINE", OPER_OLINE_SYNTAX); - } - return MOD_CONT; } MODULE_INIT("os_oline", OSOLine) diff --git a/src/core/os_oper.c b/src/core/os_oper.c index 077c586bb..be02265e4 100644 --- a/src/core/os_oper.c +++ b/src/core/os_oper.c @@ -15,91 +15,70 @@ #include "module.h" -int do_oper(User * u); -int oper_list_callback(SList * slist, int number, void *item, - va_list args); -int oper_list(int number, NickCore * nc, User * u, int *sent_header); -void myOperServHelp(User * u); +int oper_list_callback(SList *slist, int number, void *item, va_list args); +int oper_list(int number, NickCore *nc, User *u, int *sent_header); +void myOperServHelp(User *u); -class OSOper : public Module +class CommandOSOper : public Command { - public: - OSOper(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + CommandResult DoAdd(User *u, std::vector<std::string> ¶ms) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - c = createCommand("OPER", do_oper, NULL, OPER_HELP_OPER, -1, -1, -1, -1); - c->help_param1 = s_NickServ; - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - - this->SetOperHelp(myOperServHelp); - } -}; - + const char *nick = param.size() > 1 ? params[1].c_str() : NULL; + NickAlias *na; + int res = 0; -/** - * Add the help response to anopes /os help output. - * @param u The user who is requesting help - **/ -void myOperServHelp(User * u) -{ - notice_lang(s_OperServ, u, OPER_HELP_CMD_OPER); -} - -/** - * The /os oper command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_oper(User * u) -{ - char *cmd = strtok(NULL, " "); - char *nick = strtok(NULL, " "); - NickAlias *na; - int res = 0; + if (!nick) + { + this->OnSyntaxError(u); + return MOD_CONT; + } - if (!cmd || (!nick && stricmp(cmd, "LIST") && stricmp(cmd, "CLEAR"))) { - syntax_error(s_OperServ, u, "OPER", OPER_OPER_SYNTAX); - } else if (!stricmp(cmd, "ADD")) { - if (!is_services_root(u)) { + if (!is_services_root(u)) + { notice_lang(s_OperServ, u, PERMISSION_DENIED); return MOD_CONT; } - if (!(na = findnick(nick))) { + if (!(na = findnick(nick))) + { notice_lang(s_OperServ, u, NICK_X_NOT_REGISTERED, nick); return MOD_CONT; } - if (na->status & NS_VERBOTEN) { + if (na->status & NS_VERBOTEN) + { notice_lang(s_OperServ, u, NICK_X_FORBIDDEN, nick); return MOD_CONT; } - if (na->nc->flags & NI_SERVICES_OPER - || slist_indexof(&servopers, na->nc) != -1) { + if (na->nc->flags & NI_SERVICES_OPER || slist_indexof(&servopers, na->nc) != -1) + { notice_lang(s_OperServ, u, OPER_OPER_EXISTS, nick); return MOD_CONT; } res = slist_add(&servopers, na->nc); - if (res == -2) { + if (res == -2) + { notice_lang(s_OperServ, u, OPER_OPER_REACHED_LIMIT, nick); return MOD_CONT; - } else { - if (na->nc->flags & NI_SERVICES_ADMIN - && (res = slist_indexof(&servadmins, na->nc)) != -1) { - if (!is_services_root(u)) { + } + else + { + if (na->nc->flags & NI_SERVICES_ADMIN && (res = slist_indexof(&servadmins, na->nc)) != -1) + { + if (!is_services_root(u)) + { notice_lang(s_OperServ, u, PERMISSION_DENIED); return MOD_CONT; } slist_delete(&servadmins, res); na->nc->flags |= NI_SERVICES_OPER; notice_lang(s_OperServ, u, OPER_OPER_MOVED, nick); - } else { + } + else + { na->nc->flags |= NI_SERVICES_OPER; notice_lang(s_OperServ, u, OPER_OPER_ADDED, nick); } @@ -107,36 +86,58 @@ int do_oper(User * u) if (readonly) notice_lang(s_OperServ, u, READ_ONLY_MODE); - } else if (!stricmp(cmd, "DEL")) { - if (!is_services_root(u)) { + + return MOD_CONT; + } + + CommandResult DoDel(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params.size() > 1 ? params[1].c_str() : NULL; + NickAlias *na; + int res = 0; + + if (!nick) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + if (!is_services_root(u)) + { notice_lang(s_OperServ, u, PERMISSION_DENIED); return MOD_CONT; } - if (isdigit(*nick) && strspn(nick, "1234567890,-") == strlen(nick)) { + if (isdigit(*nick) && strspn(nick, "1234567890,-") == strlen(nick)) + { /* Deleting a range */ res = slist_delete_range(&servopers, nick, NULL); - if (res == 0) { + if (res == 0) + { notice_lang(s_OperServ, u, OPER_OPER_NO_MATCH); return MOD_CONT; - } else if (res == 1) { + } + else if (res == 1) notice_lang(s_OperServ, u, OPER_OPER_DELETED_ONE); - } else { + else notice_lang(s_OperServ, u, OPER_OPER_DELETED_SEVERAL, res); - } - } else { - if (!(na = findnick(nick))) { + } + else + { + if (!(na = findnick(nick))) + { notice_lang(s_OperServ, u, NICK_X_NOT_REGISTERED, nick); return MOD_CONT; } - if (na->status & NS_VERBOTEN) { + if (na->status & NS_VERBOTEN) + { notice_lang(s_OperServ, u, NICK_X_FORBIDDEN, nick); return MOD_CONT; } - if (!(na->nc->flags & NI_SERVICES_OPER) - || (res = slist_indexof(&servopers, na->nc)) == -1) { + if (!(na->nc->flags & NI_SERVICES_OPER) || (res = slist_indexof(&servopers, na->nc)) == -1) + { notice_lang(s_OperServ, u, OPER_OPER_NOT_FOUND, nick); return MOD_CONT; } @@ -147,74 +148,143 @@ int do_oper(User * u) if (readonly) notice_lang(s_OperServ, u, READ_ONLY_MODE); - } else if (!stricmp(cmd, "LIST")) { + + return MOD_CONT; + } + + CommandResult DoList(User *u, std::vector<std::string> ¶ms) + { int sent_header = 0; + const char *nick = params.size() > 1 ? params[1].c_str() : NULL; - if (!is_oper(u)) { + if (!is_oper(u)) + { notice_lang(s_OperServ, u, PERMISSION_DENIED); return MOD_CONT; } - if (servopers.count == 0) { + if (!servopers.count) + { notice_lang(s_OperServ, u, OPER_OPER_LIST_EMPTY); return MOD_CONT; } - if (!nick || (isdigit(*nick) - && strspn(nick, "1234567890,-") == strlen(nick))) { - res = - slist_enum(&servopers, nick, &oper_list_callback, u, - &sent_header); - if (res == 0) { + if (!nick || (isdigit(*nick) && strspn(nick, "1234567890,-") == strlen(nick))) + { + res = slist_enum(&servopers, nick, &oper_list_callback, u, &sent_header); + if (!res) + { notice_lang(s_OperServ, u, OPER_OPER_NO_MATCH); return MOD_CONT; - } else { - notice_lang(s_OperServ, u, END_OF_ANY_LIST, "Oper"); } - } else { + else + notice_lang(s_OperServ, u, END_OF_ANY_LIST, "Oper"); + } + else + { int i; - for (i = 0; i < servopers.count; i++) - if (!stricmp - (nick, (static_cast<NickCore *>(servopers.list[i]))->display) - || match_wild_nocase(nick, - (static_cast<NickCore *>(servopers.list[i]))-> - display)) + for (i = 0; i < servopers.count; ++i) + { + if (!stricmp(nick, (static_cast<NickCore *>(servopers.list[i]))->display) || match_wild_nocase(nick, (static_cast<NickCore *>(servopers.list[i]))->display)) oper_list(i + 1, static_cast<NickCore *>(servopers.list[i]), u, &sent_header); + } if (!sent_header) notice_lang(s_OperServ, u, OPER_OPER_NO_MATCH); - else { + else notice_lang(s_OperServ, u, END_OF_ANY_LIST, "Oper"); - } } - } else if (!stricmp(cmd, "CLEAR")) { - if (!is_services_root(u)) { + + return MOD_CONT; + } + + CommandResult DoClear(User *u, std::vector<std::string> ¶ms) + { + if (!is_services_root(u)) + { notice_lang(s_OperServ, u, PERMISSION_DENIED); return MOD_CONT; } - if (servopers.count == 0) { + if (!servopers.count) + { notice_lang(s_OperServ, u, OPER_OPER_LIST_EMPTY); return MOD_CONT; } slist_clear(&servopers, 1); notice_lang(s_OperServ, u, OPER_OPER_CLEAR); - } else { + + return MOD_CONT; + } + public: + CommandOSOper() : Command("OPER", 1, 2) + { + this->help_param1 = s_NickServ; + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + + if (!stricmp(cmd, "ADD")) + return this->DoAdd(u, params); + else if (!stricmp(cmd, "DEL")) + return this->DoDel(u, params); + else if (!stricmp(cmd, "LIST")) + return this->DoList(u, params); + else if (!stricmp(cmd, "CLEAR")) + return this->DoClear(u, params); + else + this->OnSyntaxError(u); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_OperServ, u, OPER_HELP_OPER); + return true; + } + + void OnSyntaxError(User *u) + { syntax_error(s_OperServ, u, "OPER", OPER_OPER_SYNTAX); } - return MOD_CONT; +}; + +class OSOper : public Module +{ + public: + OSOper(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(OPERSERV, new CommandOSOper(), MOD_UNIQUE); + + this->SetOperHelp(myOperServHelp); + } +}; + + +/** + * Add the help response to anopes /os help output. + * @param u The user who is requesting help + **/ +void myOperServHelp(User *u) +{ + notice_lang(s_OperServ, u, OPER_HELP_CMD_OPER); } /* Lists an oper entry, prefixing it with the header if needed */ - -int oper_list(int number, NickCore * nc, User * u, int *sent_header) +int oper_list(int number, NickCore *nc, User *u, int *sent_header) { if (!nc) return 0; - if (!*sent_header) { + if (!*sent_header) + { notice_lang(s_OperServ, u, OPER_OPER_LIST_HEADER); *sent_header = 1; } @@ -224,8 +294,7 @@ int oper_list(int number, NickCore * nc, User * u, int *sent_header) } /* Callback for enumeration purposes */ - -int oper_list_callback(SList * slist, int number, void *item, va_list args) +int oper_list_callback(SList *slist, int number, void *item, va_list args) { User *u = va_arg(args, User *); int *sent_header = va_arg(args, int *); diff --git a/src/core/os_opernews.c b/src/core/os_opernews.c deleted file mode 100644 index e04e63e1c..000000000 --- a/src/core/os_opernews.c +++ /dev/null @@ -1,87 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2009 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * - * $Id$ - * - */ -/*************************************************************************/ - -#include "module.h" - -Command *c; - -void myOperServHelp(User * u); -int load_config(); -int reload_config(int argc, char **argv); - -class OSOperNews : public Module -{ - public: - OSOperNews(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - EvtHook *hook; - char buf[BUFSIZE]; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - /** XXX: For some unknown reason, do_opernews is actaully defined in news.c - * we can look at moving it here later - **/ - c = createCommand("OPERNEWS", do_opernews, is_services_admin, NEWS_HELP_OPER, -1, -1, -1, -1); - snprintf(buf, BUFSIZE, "%d", NewsCount), - c->help_param1 = sstrdup(buf); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - - this->SetOperHelp(myOperServHelp); - - hook = createEventHook(EVENT_RELOAD, reload_config); - if (this->AddEventHook(hook) != MOD_ERR_OK) - throw ModuleException("os_opernews: Can't hook to EVENT_RELOAD event"); - } - - ~OSOperNews() - { - delete [] c->help_param1; - } -}; - - -/** - * Add the help response to anopes /os help output. - * @param u The user who is requesting help - **/ -void myOperServHelp(User * u) -{ - if (is_services_admin(u)) { - notice_lang(s_OperServ, u, OPER_HELP_CMD_OPERNEWS); - } -} - -/** - * Upon /os reload refresh the count - **/ -int reload_config(int argc, char **argv) { - char buf[BUFSIZE]; - - if (argc >= 1) { - if (!stricmp(argv[0], EVENT_START)) { - delete [] c->help_param1; - snprintf(buf, BUFSIZE, "%d", NewsCount), - c->help_param1 = sstrdup(buf); - } - } - - return MOD_CONT; -} - - -MODULE_INIT("os_opernews", OSOperNews) diff --git a/src/core/os_quit.c b/src/core/os_quit.c index f295c173b..60e045d3e 100644 --- a/src/core/os_quit.c +++ b/src/core/os_quit.c @@ -15,22 +15,49 @@ #include "module.h" -int do_os_quit(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSQuit : public Command +{ + public: + CommandOSQuit() : Command("QUIT", 0, 0) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + quitmsg = new char[28 + strlen(u->nick)]; + if (!quitmsg) + quitmsg = "QUIT command received, but out of memory!"; + else + sprintf(const_cast<char *>(quitmsg), "QUIT command received from %s", u->nick); // XXX we know this is safe, but.. + + if (GlobalOnCycle) + oper_global(NULL, "%s", GlobalOnCycleMessage); + quitting = 1; + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_root(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_QUIT); + return true; + } +}; class OSQuit : public Module { public: OSQuit(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("QUIT", do_os_quit, is_services_root, OPER_HELP_QUIT, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSQuit(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } @@ -41,31 +68,10 @@ class OSQuit : public Module * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_root(u)) { + if (is_services_root(u)) notice_lang(s_OperServ, u, OPER_HELP_CMD_QUIT); - } -} - -/** - * The /os quit command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_os_quit(User * u) -{ - quitmsg = new char[28 + strlen(u->nick)]; - if (!quitmsg) - quitmsg = "QUIT command received, but out of memory!"; - else - sprintf(const_cast<char *>(quitmsg), "QUIT command received from %s", u->nick); // XXX we know this is safe, but.. - - if (GlobalOnCycle) { - oper_global(NULL, "%s", GlobalOnCycleMessage); - } - quitting = 1; - return MOD_CONT; } MODULE_INIT("os_quit", OSQuit) diff --git a/src/core/os_randomnews.c b/src/core/os_randomnews.c deleted file mode 100644 index b68d483bf..000000000 --- a/src/core/os_randomnews.c +++ /dev/null @@ -1,54 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2009 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * - * $Id$ - * - */ -/*************************************************************************/ - -#include "module.h" - -void myOperServHelp(User * u); - -class OSRandomNews : public Module -{ - public: - OSRandomNews(const std::string &modname, const std::string &creator) : Module(modname, creator) - { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion - ("$Id$"); - this->SetType(CORE); - - /** XXX: For some unknown reason, do_randomnews is actaully defined in news.c - * we can look at moving it here later - **/ - c = createCommand("RANDOMNEWS", do_randomnews, is_services_admin, NEWS_HELP_RANDOM, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - - this->SetOperHelp(myOperServHelp); - } -}; - - -/** - * Add the help response to anopes /os help output. - * @param u The user who is requesting help - **/ -void myOperServHelp(User * u) -{ - if (is_services_admin(u)) { - notice_lang(s_OperServ, u, OPER_HELP_CMD_RANDOMNEWS); - } -} - -MODULE_INIT("os_randomnews", OSRandomNews) diff --git a/src/core/os_raw.c b/src/core/os_raw.c index b3f31dbb6..142fbb73b 100644 --- a/src/core/os_raw.c +++ b/src/core/os_raw.c @@ -15,7 +15,42 @@ #include "module.h" -int do_raw(User * u); +class CommandOSRaw : public Command +{ + public: + CommandOSRaw() : Command("RAW", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *text = params[0].c_str(); + send_cmd(NULL, "%s", text); + if (WallOSRaw) + { + std::string kw; + spacesepstream textsep(text); + while (textsep.GetString(kw) && kw[0] == ':'); + ircdproto->SendGlobops(s_OperServ, "\2%s\2 used RAW command for \2%s\2", u->nick, !kw.empty() ? kw.c_str() : "\2non RFC compliant message\2"); + } + alog("%s used RAW command for %s", u->nick, text); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_root(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_RAW); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "RAW", OPER_RAW_SYNTAX); + } +}; class OSRaw : public Module { @@ -36,31 +71,4 @@ class OSRaw : public Module } }; - -/** - * The /os raw command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_raw(User * u) -{ - char *text = strtok(NULL, ""); - if (!text) - syntax_error(s_OperServ, u, "RAW", OPER_RAW_SYNTAX); - else { - send_cmd(NULL, "%s", text); - if (WallOSRaw) { - char *kw = strtok(text, " "); - while (kw && *kw == ':') - kw = strtok(NULL, " "); - ircdproto->SendGlobops(s_OperServ, - "\2%s\2 used RAW command for \2%s\2", - u->nick, - (kw ? kw : "\2non RFC compliant message\2")); - } - alog("%s used RAW command for %s", u->nick, text); - } - return MOD_CONT; -} - MODULE_INIT("os_raw", OSRaw) diff --git a/src/core/os_reload.c b/src/core/os_reload.c index 225305b94..1e0cf7223 100644 --- a/src/core/os_reload.c +++ b/src/core/os_reload.c @@ -15,22 +15,51 @@ #include "module.h" -int do_reload(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSReload : public Command +{ + public: + CommandOSReload() : Command("RELOAD", 0, 0) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + if (!read_config(1)) + { + quitmsg = new char[28 + strlen(u->nick)]; + if (!quitmsg) + quitmsg = "Error during the reload of the configuration file, but out of memory!"; + else + sprintf(const_cast<char *>(quitmsg), /* XXX */ "Error during the reload of the configuration file!"); + quitting = 1; + } + send_event(EVENT_RELOAD, 1, EVENT_START); + notice_lang(s_OperServ, u, OPER_RELOAD); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_root(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_RELOAD); + return true; + } +}; class OSReload : public Module { public: OSReload(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("RELOAD", do_reload, is_services_root, OPER_HELP_RELOAD, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSReload(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } @@ -41,33 +70,10 @@ class OSReload : public Module * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_root(u)) { + if (is_services_root(u)) notice_lang(s_OperServ, u, OPER_HELP_CMD_RELOAD); - } -} - -/** - * The /os relaod command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_reload(User * u) -{ - if (!read_config(1)) { - quitmsg = new char[28 + strlen(u->nick)]; - if (!quitmsg) - quitmsg = - "Error during the reload of the configuration file, but out of memory!"; - else - sprintf(const_cast<char *>(quitmsg), /* XXX */ - "Error during the reload of the configuration file!"); - quitting = 1; - } - send_event(EVENT_RELOAD, 1, EVENT_START); - notice_lang(s_OperServ, u, OPER_RELOAD); - return MOD_CONT; } MODULE_INIT("os_reload", OSReload) diff --git a/src/core/os_restart.c b/src/core/os_restart.c index 70ff49fc3..9c9e9b227 100644 --- a/src/core/os_restart.c +++ b/src/core/os_restart.c @@ -15,66 +15,66 @@ #include "module.h" -#ifdef _WIN32 -/* OperServ restart needs access to this if were gonna avoid sending ourself a signal */ -extern MDE void do_restart_services(); +void myOperServHelp(User *u); + +class CommandOSRestart : public Command +{ + public: + CommandOSRestart() : Command("RESTART", 0, 0) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { +#ifdef SERVICES_BIN + quitmsg = new char[31 + strlen(u->nick)]; + if (!quitmsg) + quitmsg = "RESTART command received, but out of memory!"; + else + sprintf(const_cast<char *>(quitmsg), /* XXX */ "RESTART command received from %s", u->nick); + + if (GlobalOnCycle) + oper_global(NULL, "%s", GlobalOnCycleMessage); + /* raise(SIGHUP); */ + do_restart_services(); +#else + notice_lang(s_OperServ, u, OPER_CANNOT_RESTART); #endif + return MOD_CONT; + } -int do_restart(User * u); -void myOperServHelp(User * u); + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_root(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_RESTART); + return true; + } +}; class OSRestart : public Module { public: OSRestart(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("RESTART", do_restart, is_services_root, OPER_HELP_RESTART, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSRestart(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } }; - /** * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_root(u)) { + if (is_services_root(u)) notice_lang(s_OperServ, u, OPER_HELP_CMD_RESTART); - } -} - -/** - * The /os restart command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_restart(User * u) -{ -#ifdef SERVICES_BIN - quitmsg = new char[31 + strlen(u->nick)]; - if (!quitmsg) - quitmsg = "RESTART command received, but out of memory!"; - else - sprintf(const_cast<char *>(quitmsg), /* XXX */ "RESTART command received from %s", u->nick); - - if (GlobalOnCycle) { - oper_global(NULL, "%s", GlobalOnCycleMessage); - } - /* raise(SIGHUP); */ - do_restart_services(); -#else - notice_lang(s_OperServ, u, OPER_CANNOT_RESTART); -#endif - return MOD_CONT; } MODULE_INIT("os_restart", OSRestart) diff --git a/src/core/os_session.c b/src/core/os_session.c index 2d79ccc76..955d3f2aa 100644 --- a/src/core/os_session.c +++ b/src/core/os_session.c @@ -15,39 +15,393 @@ #include "module.h" -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSSession : public Command +{ + private: + CommandResult DoList(User *u, std::vector<std::string> ¶ms) + { + Session *session; + int mincount; + const char *param = params[1].c_str(); + + if ((mincount = atoi(param)) <= 1) + notice_lang(s_OperServ, u, OPER_SESSION_INVALID_THRESHOLD); + else + { + notice_lang(s_OperServ, u, OPER_SESSION_LIST_HEADER, mincount); + notice_lang(s_OperServ, u, OPER_SESSION_LIST_COLHEAD); + for (i = 0; i < 1024; ++i) + { + for (session = sessionlist[i]; session; session = session->next) + { + if (session->count >= mincount) + notice_lang(s_OperServ, u, OPER_SESSION_LIST_FORMAT, session->count, session->host); + } + } + } + + return MOD_CONT; + } + + CommandResult DoView(User *u, std::vector<std::string> ¶ms) + { + const char *param = params[1].c_str(); + Session *session = findsession(param); + + if (!session) + notice_lang(s_OperServ, u, OPER_SESSION_NOT_FOUND, param); + else { + Exception *exception = find_host_exception(param); + notice_lang(s_OperServ, u, OPER_SESSION_VIEW_FORMAT, param, session->count, exception ? exception-> limit : DefSessionLimit); + } + + return MOD_CONT; + } + public: + CommandOSSession() : Command("SESSION", 2, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + + if (!LimitSessions) + { + notice_lang(s_OperServ, u, OPER_SESSION_DISABLED); + return MOD_CONT; + } + + if (!stricmp(cmd, "LIST")) + return this->DoList(u); + else if (!stricmp(cmd, "VIEW")) + return this->DoView(u); + else + this->OnSyntaxError(u); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_oper(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_SESSION); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "SESSION", OPER_SESSION_LIST_SYNTAX); + } +}; + +class CommandOSException : public Command +{ + private: + CommandResult DoAdd(User *u, std::vector<std::string> ¶ms) + { + const char *mask, *expiry, *limitstr; + char reason[BUFSIZE]; + int last_param = 3, x; + + if (nexceptions >= 32767) + { + notice_lang(s_OperServ, u, OPER_EXCEPTION_TOO_MANY); + return MOD_CONT; + } + + mask = params.size() > 1 ? params[1].c_str() : NULL; + if (mask && *mask == '+') + { + expiry = mask; + mask = params.size() > 2 ? params[2].c_str() : NULL; + last_param = 4; + } + else + expiry = NULL; + + limitstr = params.size() > last_param - 1 ? params[last_param - 1].c_str() : NULL; + + if (params.size() < last_param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + snprintf(reason, sizeof(reason), "%s%s%s", params[last_param].c_str(), last_param == 3 ? " " : "", last_param == 3 ? param[4].c_str() : ""); + + if (!*reason) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + expires = expiry ? dotime(expiry) : ExceptionExpiry; + if (expires < 0) + { + notice_lang(s_OperServ, u, BAD_EXPIRY_TIME); + return MOD_CONT; + } + else if (expires > 0) + expires += time(NULL); + + limit = limitstr && isdigit(*limitstr) ? atoi(limitstr) : -1; + + if (limit < 0 || limit > MaxSessionLimit) + { + notice_lang(s_OperServ, u, OPER_EXCEPTION_INVALID_LIMIT, MaxSessionLimit); + return MOD_CONT; + } + else + { + if (strchr(mask, '!') || strchr(mask, '@')) + { + notice_lang(s_OperServ, u, OPER_EXCEPTION_INVALID_HOSTMASK); + return MOD_CONT; + } + + x = exception_add(u, mask, limit, reason, u->nick, expires); + + if (x == 1) + notice_lang(s_OperServ, u, OPER_EXCEPTION_ADDED, mask, limit); + + if (readonly) + notice_lang(s_OperServ, u, READ_ONLY_MODE); + } + + return MOD_CONT; + } + + CommandResult DoDel(User *u, std::vector<std::string> ¶ms) + { + const char *mask = params.size() > 1 ? params[1].c_str() : NULL; + int i; + + if (!mask) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + if (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask)) + { + int count, deleted, last = -1; + deleted = process_numlist(mask, &count, exception_del_callback, u, &last); + if (!deleted) + { + if (count == 1) + notice_lang(s_OperServ, u, OPER_EXCEPTION_NO_SUCH_ENTRY, last); + else + notice_lang(s_OperServ, u, OPER_EXCEPTION_NO_MATCH); + } + else if (deleted == 1) + notice_lang(s_OperServ, u, OPER_EXCEPTION_DELETED_ONE); + else + notice_lang(s_OperServ, u, OPER_EXCEPTION_DELETED_SEVERAL, deleted); + } + else + { + int deleted = 0; + + for (i = 0; i < nexceptions; ++i) + { + if (!stricmp(mask, exceptions[i].mask)) + { + exception_del(i); + notice_lang(s_OperServ, u, OPER_EXCEPTION_DELETED, mask); + deleted = 1; + break; + } + } + if (!deleted && i == nexceptions) + notice_lang(s_OperServ, u, OPER_EXCEPTION_NOT_FOUND, mask); + } + + /* Renumber the exception list. I don't believe in having holes in + * lists - it makes code more complex, harder to debug and we end up + * with huge index numbers. Imho, fixed numbering is only beneficial + * when one doesn't have range capable manipulation. -TheShadow */ + + for (i = 0; i < nexceptions; ++i) + exceptions[i].num = i; + + if (readonly) + notice_lang(s_OperServ, u, READ_ONLY_MODE); + + return MOD_CONT; + } + + CommandResult DoMove(User *u, std::vector<std::string> ¶ms) + { + Exception *exception; + const char *n1str = params.size() > 1 ? params[1].c_str() : NULL; /* From position */ + const char *n2str = params.size() > 2 ? params[2].c_str() : NULL; /* To position */ + int n1, n2; + + if (!n2str) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + n1 = atoi(n1str) - 1; + n2 = atoi(n2str) - 1; + + if (n1 >= 0 && n1 < nexceptions && n2 >= 0 && n2 < nexceptions && n1 != n2) + { + exception = static_cast<Exception *>(smalloc(sizeof(Exception))); + memcpy(exception, &exceptions[n1], sizeof(Exception)); + + if (n1 < n2) + { + /* Shift upwards */ + memmove(&exceptions[n1], &exceptions[n1 + 1], sizeof(Exception) * (n2 - n1)); + memmove(&exceptions[n2], exception, sizeof(Exception)); + } + else + { + /* Shift downwards */ + memmove(&exceptions[n2 + 1], &exceptions[n2], sizeof(Exception) * (n1 - n2)); + memmove(&exceptions[n2], exception, sizeof(Exception)); + } + + free(exception); + + notice_lang(s_OperServ, u, OPER_EXCEPTION_MOVED, exceptions[n1].mask, n1 + 1, n2 + 1); + + /* Renumber the exception list. See DoDel() above for why. */ + for (i = 0; i < nexceptions; ++i) + exceptions[i].num = i; + + if (readonly) + notice_lang(s_OperServ, u, READ_ONLY_MODE); + } + else + this->OnSyntaxError(u); + + return MOD_CONT; + } + + CommandResult DoList(User *u, std::vector<std::string> ¶ms) + { + int sent_header = 0; + expire_exceptions(); + const char *mask = params.size() > 1 ? params[1].c_str() : NULL; + + if (mask && strspn(mask, "1234567890,-") == strlen(mask)) + process_numlist(mask, NULL, exception_list_callback, u, &sent_header); + else + { + for (i = 0; i < nexceptions; ++i) + { + if (!mask || match_wild_nocase(mask, exceptions[i].mask)) + exception_list(u, i, &sent_header); + } + } + if (!sent_header) + notice_lang(s_OperServ, u, OPER_EXCEPTION_NO_MATCH); + + return MOD_CONT; + } + + CommandResult DoView(User *u, std::vector<std::string> ¶ms) + { + int sent_header = 0; + expire_exceptions(); + const char *mask = params.size() > 1 ? params[1].c_str() : NULL; + + if (mask && strspn(mask, "1234567890,-") == strlen(mask)) + process_numlist(mask, NULL, exception_view_callback, u, + &sent_header); + else + { + for (i = 0; i < nexceptions; ++i) + { + if (!mask || match_wild_nocase(mask, exceptions[i].mask)) + exception_view(u, i, &sent_header); + } + } + if (!sent_header) + notice_lang(s_OperServ, u, OPER_EXCEPTION_NO_MATCH); + + return MOD_CONT; + } + public: + CommandOSException() : Command("EXCEPTION", 1, 5) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + char *mask, *reason, *expiry, *limitstr; + int limit, expires; + int i; + int x; + + if (!LimitSessions) + { + notice_lang(s_OperServ, u, OPER_EXCEPTION_DISABLED); + return MOD_CONT; + } + + if (!stricmp(cmd, "ADD")) + return this->DoAdd(u, params); + else if (!stricmp(cmd, "DEL")) + return this->DoDel(u, params); + else if (!stricmp(cmd, "MOVE")) + return this->DoMove(u, params); + else if (!stricmp(cmd, "LIST")) + return this->DoList(u, params); + else if (!stricmp(cmd, "VIEW")) + return this->DoView(u, params); + else { + this->OnSyntaxError(u); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_oper(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_EXCEPTION); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "EXCEPTION", OPER_EXCEPTION_SYNTAX); + } +}; class OSSession : public Module { public: OSSession(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - /** - * do_session/do_exception are exported from sessions.c - we just want to provide an interface. - **/ - c = createCommand("SESSION", do_session, is_services_oper, OPER_HELP_SESSION, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - c = createCommand("EXCEPTION", do_exception, is_services_oper, OPER_HELP_EXCEPTION, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSSession(), MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSException(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } }; - /** * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_oper(u)) { + if (is_services_oper(u)) + { notice_lang(s_OperServ, u, OPER_HELP_CMD_SESSION); notice_lang(s_OperServ, u, OPER_HELP_CMD_EXCEPTION); } diff --git a/src/core/os_set.c b/src/core/os_set.c index 7dc469aee..769dfbd6a 100644 --- a/src/core/os_set.c +++ b/src/core/os_set.c @@ -15,197 +15,303 @@ #include "module.h" -int do_set(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); -class OSSet : public Module +class CommandOSSet : public Command { - public: - OSSet(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + CommandResult DoList(User *u, std::vector<std::string> ¶ms) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("SET", do_set, is_services_root, OPER_HELP_SET, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - c = createCommand("SET LIST", NULL, NULL, OPER_HELP_SET_LIST, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - c = createCommand("SET READONLY", NULL, NULL, OPER_HELP_SET_READONLY, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - c = createCommand("SET LOGCHAN", NULL, NULL, OPER_HELP_SET_LOGCHAN, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - c = createCommand("SET DEBUG", NULL, NULL, OPER_HELP_SET_DEBUG, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - c = createCommand("SET NOEXPIRE", NULL, NULL, OPER_HELP_SET_NOEXPIRE, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - c = createCommand("SET IGNORE", NULL, NULL, OPER_HELP_SET_IGNORE, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - c = createCommand("SET SUPERADMIN", NULL, NULL, OPER_HELP_SET_SUPERADMIN, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - - this->SetOperHelp(myOperServHelp); - } -}; - - -/** - * Add the help response to anopes /os help output. - * @param u The user who is requesting help - **/ -void myOperServHelp(User * u) -{ - if (is_services_root(u)) { - notice_lang(s_OperServ, u, OPER_HELP_CMD_SET); - } -} + int index; -/** - * The /os set command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_set(User * u) -{ - char *option = strtok(NULL, " "); - char *setting = strtok(NULL, " "); - int index; - Channel *c; - - if (!option) { - syntax_error(s_OperServ, u, "SET", OPER_SET_SYNTAX); - } else if (stricmp(option, "LIST") == 0) { - index = - (allow_ignore ? OPER_SET_LIST_OPTION_ON : - OPER_SET_LIST_OPTION_OFF); + index = allow_ignore ? OPER_SET_LIST_OPTION_ON : OPER_SET_LIST_OPTION_OFF; notice_lang(s_OperServ, u, index, "IGNORE"); - index = - (readonly ? OPER_SET_LIST_OPTION_ON : - OPER_SET_LIST_OPTION_OFF); + index = readonly ? OPER_SET_LIST_OPTION_ON : OPER_SET_LIST_OPTION_OFF; notice_lang(s_OperServ, u, index, "READONLY"); - index = - (logchan ? OPER_SET_LIST_OPTION_ON : OPER_SET_LIST_OPTION_OFF); + index = logchan ? OPER_SET_LIST_OPTION_ON : OPER_SET_LIST_OPTION_OFF; notice_lang(s_OperServ, u, index, "LOGCHAN"); - index = - (debug ? OPER_SET_LIST_OPTION_ON : OPER_SET_LIST_OPTION_OFF); + index = debug ? OPER_SET_LIST_OPTION_ON : OPER_SET_LIST_OPTION_OFF; notice_lang(s_OperServ, u, index, "DEBUG"); - index = - (noexpire ? OPER_SET_LIST_OPTION_ON : - OPER_SET_LIST_OPTION_OFF); + index = noexpire ? OPER_SET_LIST_OPTION_ON : OPER_SET_LIST_OPTION_OFF; notice_lang(s_OperServ, u, index, "NOEXPIRE"); - } else if (!setting) { - syntax_error(s_OperServ, u, "SET", OPER_SET_SYNTAX); - } else if (stricmp(option, "IGNORE") == 0) { - if (stricmp(setting, "on") == 0) { + + return MOD_CONT; + } + + CommandResult DoSetIgnore(User *u, std::vector<std::string> ¶ms) + { + const char *setting = params.size() > 1 ? params[1].c_str() : NULL; + + if (!setting) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + if (!stricmp(setting, "ON")) + { allow_ignore = 1; notice_lang(s_OperServ, u, OPER_SET_IGNORE_ON); - } else if (stricmp(setting, "off") == 0) { + } + else if (!stricmp(setting, "OFF")) + { allow_ignore = 0; notice_lang(s_OperServ, u, OPER_SET_IGNORE_OFF); - } else { + } + else notice_lang(s_OperServ, u, OPER_SET_IGNORE_ERROR); + + return MOD_CONT; + } + + CommandResult DoSetReadOnly(User *u, std::vector<std::string> ¶ms) + { + const char *setting = params.size() > 1 ? params[1].c_str() : NULL; + + if (!setting) + { + this->OnSyntaxError(u); + return MOD_CONT; } - } else if (stricmp(option, "READONLY") == 0) { - if (stricmp(setting, "on") == 0) { + + if (!stricmp(setting, "ON")) + { readonly = 1; alog("Read-only mode activated"); close_log(); notice_lang(s_OperServ, u, OPER_SET_READONLY_ON); - } else if (stricmp(setting, "off") == 0) { + } + else if (!stricmp(setting, "OFF")) + { readonly = 0; open_log(); alog("Read-only mode deactivated"); notice_lang(s_OperServ, u, OPER_SET_READONLY_OFF); - } else { + } + else notice_lang(s_OperServ, u, OPER_SET_READONLY_ERROR); + + return MOD_CONT; + } + + CommandResult DoSetLogChan(User *u, std::vector<std::string> ¶ms) + { + const char *setting = params.size() > 1 ? params[1].c_str() : NULL; + Channel *c; + + if (!setting) + { + this->OnSyntaxError(u); + return MOD_CONT; } - } else if (stricmp(option, "LOGCHAN") == 0) { /* Unlike the other SET commands where only stricmp is necessary, * we also have to ensure that LogChannel is defined or we can't * send to it. * * -jester */ - if (LogChannel && (stricmp(setting, "on") == 0)) { - if (ircd->join2msg) { + if (LogChannel && !stricmp(setting, "ON")) + { + if (ircd->join2msg) + { c = findchan(LogChannel); ircdproto->SendJoin(findbot(s_GlobalNoticer), LogChannel, c ? c->creation_time : time(NULL)); } logchan = 1; alog("Now sending log messages to %s", LogChannel); notice_lang(s_OperServ, u, OPER_SET_LOGCHAN_ON, LogChannel); - } else if (LogChannel && (stricmp(setting, "off") == 0)) { + } + else if (LogChannel && !stricmp(setting, "OFF")) + { alog("No longer sending log messages to a channel"); - if (ircd->join2msg) { + if (ircd->join2msg) ircdproto->SendPart(findbot(s_GlobalNoticer), LogChannel, NULL); - } logchan = 0; notice_lang(s_OperServ, u, OPER_SET_LOGCHAN_OFF); - } else { + } + else notice_lang(s_OperServ, u, OPER_SET_LOGCHAN_ERROR); + + return MOD_CONT; + } + + CommandResult DoSetSuperAdmin(User *u, std::vector<std::string> ¶ms) + { + const char *setting = params.size() > 1 ? params[1].c_str() : NULL; + + if (!setting) + { + this->OnSyntaxError(u); + return MOD_CONT; } + /** * Allow the user to turn super admin on/off - * - * Rob + * + * Rob **/ - } else if (stricmp(option, "SUPERADMIN") == 0) { - if (!SuperAdmin) { + if (!SuperAdmin) notice_lang(s_OperServ, u, OPER_SUPER_ADMIN_NOT_ENABLED); - } else if (stricmp(setting, "on") == 0) { + else if (!stricmp(setting, "ON")) + { u->isSuperAdmin = 1; notice_lang(s_OperServ, u, OPER_SUPER_ADMIN_ON); alog("%s: %s is a SuperAdmin ", s_OperServ, u->nick); - ircdproto->SendGlobops(s_OperServ, - getstring2(NULL, OPER_SUPER_ADMIN_WALL_ON), - u->nick); - } else if (stricmp(setting, "off") == 0) { + ircdproto->SendGlobops(s_OperServ, getstring2(NULL, OPER_SUPER_ADMIN_WALL_ON), u->nick); + } + else if (!stricmp(setting, "OFF")) + { u->isSuperAdmin = 0; notice_lang(s_OperServ, u, OPER_SUPER_ADMIN_OFF); alog("%s: %s is no longer a SuperAdmin", s_OperServ, u->nick); - ircdproto->SendGlobops(s_OperServ, - getstring2(NULL, OPER_SUPER_ADMIN_WALL_OFF), - u->nick); - } else { + ircdproto->SendGlobops(s_OperServ, getstring2(NULL, OPER_SUPER_ADMIN_WALL_OFF), u->nick); + } + else notice_lang(s_OperServ, u, OPER_SUPER_ADMIN_SYNTAX); + + return MOD_CONT; + } + + CommandResult DoSetDebug(User *u, std::vector<std::string> ¶ms) + { + const char *setting = params.size() > 1 ? params[1].c_str() : NULL; + + if (!setting) + { + this->OnSyntaxError(u); + return MOD_CONT; } - } else if (stricmp(option, "DEBUG") == 0) { - if (stricmp(setting, "on") == 0) { + + if (!stricmp(setting, "ON")) + { debug = 1; alog("Debug mode activated"); notice_lang(s_OperServ, u, OPER_SET_DEBUG_ON); - } else if (stricmp(setting, "off") == 0 || - (*setting == '0' && atoi(setting) == 0)) { + } + else if (!stricmp(setting, "OFF") || (*setting == '0' && !atoi(setting))) + { alog("Debug mode deactivated"); debug = 0; notice_lang(s_OperServ, u, OPER_SET_DEBUG_OFF); - } else if (isdigit(*setting) && atoi(setting) > 0) { + } + else if (isdigit(*setting) && atoi(setting) > 0) + { debug = atoi(setting); alog("Debug mode activated (level %d)", debug); notice_lang(s_OperServ, u, OPER_SET_DEBUG_LEVEL, debug); - } else { + } + else notice_lang(s_OperServ, u, OPER_SET_DEBUG_ERROR); + + return MOD_CONT; + } + + CommandResult DoSetNoExpire(User *u, std::vector<std::string> ¶ms) + { + const char *setting = params.size() > 1 ? params[1].c_str() : NULL; + + if (!setting) + { + this->OnSyntaxError(u); + return MOD_CONT; } - } else if (stricmp(option, "NOEXPIRE") == 0) { - if (stricmp(setting, "ON") == 0) { + if (!stricmp(setting, "ON")) + { noexpire = 1; alog("No expire mode activated"); notice_lang(s_OperServ, u, OPER_SET_NOEXPIRE_ON); - } else if (stricmp(setting, "OFF") == 0) { + } + else if (!stricmp(setting, "OFF")) + { noexpire = 0; alog("No expire mode deactivated"); notice_lang(s_OperServ, u, OPER_SET_NOEXPIRE_OFF); - } else { - notice_lang(s_OperServ, u, OPER_SET_NOEXPIRE_ERROR); } - } else { - notice_lang(s_OperServ, u, OPER_SET_UNKNOWN_OPTION, option); + else + notice_lang(s_OperServ, u, OPER_SET_NOEXPIRE_ERROR); + + return MOD_CONT; } - return MOD_CONT; + public: + CommandOSSet() : Command("SET", 1, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + char *option = params[0].c_str(); + char *setting = strtok(NULL, " "); + int index; + Channel *c; + + if (!stricmp(option, "LIST")) + return this->DoList(u, params); + else if (!stricmp(option, "IGNORE")) + return this->DoSetIgnore(u, params); + else if (!stricmp(option, "READONLY")) + return this->DoSetReadOnly(u, params); + else if (!stricmp(option, "LOGCHAN")) + return this->DoSetLogChan(u, params); + else if (!stricmp(option, "SUPERADMIN")) + return this->DoSetSuperAdmin(u, params); + else if (!stricmp(option, "DEBUG")) + return this->DoSetDebug(u, params); + else if (!stricmp(option, "NOEXPIRE")) + return this->DoSetNoExpire(u, params); + else + notice_lang(s_OperServ, u, OPER_SET_UNKNOWN_OPTION, option); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_root(u)) + return false; + + // This needs to change XXX + notice_lang(s_OperServ, u, OPER_HELP_SET); + notice_lang(s_OperServ, u, OPER_HELP_SET_LIST); + notice_lang(s_OperServ, u, OPER_HELP_SET_READONLY); + notice_lang(s_OperServ, u, OPER_HELP_SET_LOGCHAN); + notice_lang(s_OperServ, u, OPER_HELP_SET_DEBUG); + notice_lang(s_OperServ, u, OPER_HELP_SET_NOEXPIRE); + notice_lang(s_OperServ, u, OPER_HELP_SET_IGNORE); + notice_lang(s_OperServ, u, OPER_HELP_SET_SUPERADMIN); + + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "SET", OPER_SET_SYNTAX); + } +}; + +class OSSet : public Module +{ + public: + OSSet(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + + this->AddCommand(OPERSERV, new CommandOSSet(), MOD_UNIQUE); + + this->SetOperHelp(myOperServHelp); + } +}; + +/** + * Add the help response to anopes /os help output. + * @param u The user who is requesting help + **/ +void myOperServHelp(User *u) +{ + if (is_services_root(u)) + notice_lang(s_OperServ, u, OPER_HELP_CMD_SET); } MODULE_INIT("os_set", OSSet) diff --git a/src/core/os_shutdown.c b/src/core/os_shutdown.c index 703119674..1d8c874d6 100644 --- a/src/core/os_shutdown.c +++ b/src/core/os_shutdown.c @@ -15,21 +15,49 @@ #include "module.h" -int do_shutdown(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSShutdown : public Command +{ + public: + CommandOSShutdown() : Command("SHUTDOWN", 0, 0) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + quitmsg = new char[32 + strlen(u->nick)]; + if (!quitmsg) + quitmsg = "SHUTDOWN command received, but out of memory!"; + else + sprintf(const_cast<char *>(quitmsg), /* XXX */ "SHUTDOWN command received from %s", u->nick); + + if (GlobalOnCycle) + oper_global(NULL, "%s", GlobalOnCycleMessage); + save_data = 1; + delayed_quit = 1; + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_root(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_SHUTDOWN); + return true; + } +}; class OSShutdown : public Module { public: OSShutdown(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("SHUTDOWN", do_shutdown, is_services_root, OPER_HELP_SHUTDOWN, -1, -1, -1, -1); this->AddCommand(OPERSERV, c, MOD_UNIQUE); this->SetOperHelp(myOperServHelp); @@ -41,32 +69,10 @@ class OSShutdown : public Module * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_root(u)) { + if (is_services_root(u)) notice_lang(s_OperServ, u, OPER_HELP_CMD_SHUTDOWN); - } -} - -/** - * The /os shutdown command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_shutdown(User * u) -{ - quitmsg = new char[32 + strlen(u->nick)]; - if (!quitmsg) - quitmsg = "SHUTDOWN command received, but out of memory!"; - else - sprintf(const_cast<char *>(quitmsg), /* XXX */ "SHUTDOWN command received from %s", u->nick); - - if (GlobalOnCycle) { - oper_global(NULL, "%s", GlobalOnCycleMessage); - } - save_data = 1; - delayed_quit = 1; - return MOD_CONT; } MODULE_INIT("os_shutdown", OSShutdown) diff --git a/src/core/os_sqline.c b/src/core/os_sqline.c index 6c24ef263..2de07f9c2 100644 --- a/src/core/os_sqline.c +++ b/src/core/os_sqline.c @@ -15,73 +15,31 @@ #include "module.h" -int do_sqline(User * u); -int sqline_view_callback(SList * slist, int number, void *item, - va_list args); -int sqline_view(int number, SXLine * sx, User * u, int *sent_header); -int sqline_list_callback(SList * slist, int number, void *item, - va_list args); -int sqline_list(int number, SXLine * sx, User * u, int *sent_header); +void myOperServHelp(User *u); +int sqline_view_callback(SList *slist, int number, void *item, va_list args); +int sqline_list_callback(SList *slist, int number, void *item, va_list args); +int sqline_view(int number, SXLine *sx, User *u, int *sent_header); +int sqline_list(int number, SXLine *sx, User *u, int *sent_header); -void myOperServHelp(User * u); - -class OSSQLine : public Module +class CommandOSSQLine : public Command { - public: - OSSQLine(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + CommandResult DoAdd(User *u, std::vector<std::string> ¶ms) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("SQLINE", do_sqline, is_services_oper, - OPER_HELP_SQLINE, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - - this->SetOperHelp(myOperServHelp); - if (!ircd->sqline) - throw ModuleException("Your IRCd does not support QLines."); - } -}; - - -/** - * Add the help response to anopes /os help output. - * @param u The user who is requesting help - **/ -void myOperServHelp(User * u) -{ - if (is_services_oper(u)) { - notice_lang(s_OperServ, u, OPER_HELP_CMD_SQLINE); - } -} - -/** - * The /os sqline command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_sqline(User * u) -{ - char *cmd = strtok(NULL, " "); - - if (!cmd) - cmd = ""; - - if (!stricmp(cmd, "ADD")) { - int deleted = 0; - char *expiry, *mask, *reason; + int deleted = 0, last_param = 2; + const char *expiry, *mask; + char reason[BUFSIZE]; time_t expires; - mask = strtok(NULL, " "); - if (mask && *mask == '+') { + mask = params.size() > 1 ? params[1].c_str() : NULL; + if (mask && *mask == '+') + { expiry = mask; - mask = strtok(NULL, " "); - } else { - expiry = NULL; + mask = params.size() > 2 ? params[2].c_str() : NULL; + last_param = 3; } + else + expiry = NULL; expires = expiry ? dotime(expiry) : SQLineExpiry; /* If the expiry given does not contain a final letter, it's in days, @@ -90,25 +48,33 @@ int do_sqline(User * u) if (expiry && isdigit(expiry[strlen(expiry) - 1])) expires *= 86400; /* Do not allow less than a minute expiry time */ - if (expires != 0 && expires < 60) { + if (expires != 0 && expires < 60) + { notice_lang(s_OperServ, u, BAD_EXPIRY_TIME); return MOD_CONT; - } else if (expires > 0) { - expires += time(NULL); } + else if (expires > 0) + expires += time(NULL); - if (mask && (reason = strtok(NULL, ""))) { - + if (params.size() < last_param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + snprintf(reason, sizeof(reason), "%s%s%s", params[last_param].c_str(), last_param == 2 ? " " : "", last_param == 2 ? param[3].c_str() : ""); + if (mask && *reason) + { /* We first do some sanity check on the proposed mask. */ - if (strspn(mask, "*") == strlen(mask)) { + if (strspn(mask, "*") == strlen(mask)) + { notice_lang(s_OperServ, u, USERHOST_MASK_TOO_WIDE, mask); return MOD_CONT; } /* Channel SQLINEs are only supported on Bahamut servers */ - if (*mask == '#' && !ircd->chansqline) { - notice_lang(s_OperServ, u, - OPER_SQLINE_CHANNELS_UNSUPPORTED); + if (*mask == '#' && !ircd->chansqline) + { + notice_lang(s_OperServ, u, OPER_SQLINE_CHANNELS_UNSUPPORTED); return MOD_CONT; } @@ -116,78 +82,88 @@ int do_sqline(User * u) if (deleted < 0) return MOD_CONT; else if (deleted) - notice_lang(s_OperServ, u, OPER_SQLINE_DELETED_SEVERAL, - deleted); + notice_lang(s_OperServ, u, OPER_SQLINE_DELETED_SEVERAL, deleted); notice_lang(s_OperServ, u, OPER_SQLINE_ADDED, mask); - if (WallOSSQLine) { + if (WallOSSQLine) + { char buf[128]; - if (!expires) { + if (!expires) strcpy(buf, "does not expire"); - } else { + else + { int wall_expiry = expires - time(NULL); char *s = NULL; - if (wall_expiry >= 86400) { + if (wall_expiry >= 86400) + { wall_expiry /= 86400; s = "day"; - } else if (wall_expiry >= 3600) { + } + else if (wall_expiry >= 3600) + { wall_expiry /= 3600; s = "hour"; - } else if (wall_expiry >= 60) { + } + else if (wall_expiry >= 60) + { wall_expiry /= 60; s = "minute"; } - snprintf(buf, sizeof(buf), "expires in %d %s%s", - wall_expiry, s, - (wall_expiry == 1) ? "" : "s"); + snprintf(buf, sizeof(buf), "expires in %d %s%s", wall_expiry, s, wall_expiry == 1 ? "" : "s"); } - ircdproto->SendGlobops(s_OperServ, - "%s added an SQLINE for %s (%s)", u->nick, - mask, buf); + ircdproto->SendGlobops(s_OperServ, "%s added an SQLINE for %s (%s)", u->nick, mask, buf); } if (readonly) notice_lang(s_OperServ, u, READ_ONLY_MODE); - } else { - syntax_error(s_OperServ, u, "SQLINE", OPER_SQLINE_SYNTAX); } + else + this->OnSyntaxError(u); - } else if (!stricmp(cmd, "DEL")) { + return MOD_CONT; + } - char *mask; + CommandResult DoDel(User *u, std::vector<std::string> ¶ms) + { + const char *mask; int res = 0; - mask = strtok(NULL, ""); + mask = params.size() > 1 ? params[1].c_str() : NULL; - if (!mask) { - syntax_error(s_OperServ, u, "SQLINE", OPER_SQLINE_SYNTAX); + if (!mask) + { + this->OnSyntaxError(u); return MOD_CONT; } - if (sqlines.count == 0) { + if (!sqlines.count) + { notice_lang(s_OperServ, u, OPER_SQLINE_LIST_EMPTY); return MOD_CONT; } - if (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask)) { + if (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask)) + { /* Deleting a range */ res = slist_delete_range(&sqlines, mask, NULL); - if (res == 0) { + if (!res) + { notice_lang(s_OperServ, u, OPER_SQLINE_NO_MATCH); return MOD_CONT; - } else if (res == 1) { - notice_lang(s_OperServ, u, OPER_SQLINE_DELETED_ONE); - } else { - notice_lang(s_OperServ, u, OPER_SQLINE_DELETED_SEVERAL, - res); } - } else { - if ((res = slist_indexof(&sqlines, mask)) == -1) { + else if (res == 1) + notice_lang(s_OperServ, u, OPER_SQLINE_DELETED_ONE); + else + notice_lang(s_OperServ, u, OPER_SQLINE_DELETED_SEVERAL, res); + } + else { + if ((res = slist_indexof(&sqlines, mask)) == -1) + { notice_lang(s_OperServ, u, OPER_SQLINE_NOT_FOUND, mask); return MOD_CONT; } @@ -199,87 +175,172 @@ int do_sqline(User * u) if (readonly) notice_lang(s_OperServ, u, READ_ONLY_MODE); - } else if (!stricmp(cmd, "LIST")) { - char *mask; + return MOD_CONT; + } + + CommandResult DoList(User *u, std::vector<std::string> ¶ms) + { + const char *mask; int res, sent_header = 0; - if (sqlines.count == 0) { + if (!sqlines.count) + { notice_lang(s_OperServ, u, OPER_SQLINE_LIST_EMPTY); return MOD_CONT; } - mask = strtok(NULL, ""); + mask = params.size() > 1 ? params[1].c_str() : NULL; - if (!mask || (isdigit(*mask) - && strspn(mask, "1234567890,-") == strlen(mask))) { - res = - slist_enum(&sqlines, mask, &sqline_list_callback, u, - &sent_header); - if (res == 0) { + if (!mask || (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask))) + { + res = slist_enum(&sqlines, mask, &sqline_list_callback, u, &sent_header); + if (!res) + { notice_lang(s_OperServ, u, OPER_SQLINE_NO_MATCH); return MOD_CONT; } - } else { + } + else + { int i; char *amask; - for (i = 0; i < sqlines.count; i++) { + for (i = 0; i < sqlines.count; ++i) + { amask = (static_cast<SXLine *>(sqlines.list[i]))->mask; - if (!stricmp(mask, amask) - || match_wild_nocase(mask, amask)) + if (!stricmp(mask, amask) || match_wild_nocase(mask, amask)) sqline_list(i + 1, static_cast<SXLine *>(sqlines.list[i]), u, &sent_header); } if (!sent_header) notice_lang(s_OperServ, u, OPER_SQLINE_NO_MATCH); - else { + else notice_lang(s_OperServ, u, END_OF_ANY_LIST, "SQLine"); - } } - } else if (!stricmp(cmd, "VIEW")) { - char *mask; + + return MOD_CONT; + } + + CommandResult DoView(User *u, std::vector<std::string> ¶ms) + { + const char *mask; int res, sent_header = 0; - if (sqlines.count == 0) { + if (!sqlines.count) + { notice_lang(s_OperServ, u, OPER_SQLINE_LIST_EMPTY); return MOD_CONT; } - mask = strtok(NULL, ""); + mask = params.size() > 1 ? params[1].c_str() : NULL; - if (!mask || (isdigit(*mask) - && strspn(mask, "1234567890,-") == strlen(mask))) { - res = - slist_enum(&sqlines, mask, &sqline_view_callback, u, - &sent_header); - if (res == 0) { + if (!mask || (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask))) + { + res = slist_enum(&sqlines, mask, &sqline_view_callback, u, &sent_header); + if (!res) + { notice_lang(s_OperServ, u, OPER_SQLINE_NO_MATCH); return MOD_CONT; } - } else { + } + else + { int i; char *amask; - for (i = 0; i < sqlines.count; i++) { + for (i = 0; i < sqlines.count; ++i) + { amask = (static_cast<SXLine *>(sqlines.list[i]))->mask; - if (!stricmp(mask, amask) - || match_wild_nocase(mask, amask)) + if (!stricmp(mask, amask) || match_wild_nocase(mask, amask)) sqline_view(i + 1, static_cast<SXLine *>(sqlines.list[i]), u, &sent_header); } if (!sent_header) notice_lang(s_OperServ, u, OPER_SQLINE_NO_MATCH); } - } else if (!stricmp(cmd, "CLEAR")) { + + return MOD_CONT; + } + + CommandResult DoClear(User *u, std::vector<std::string> ¶ms) + { slist_clear(&sqlines, 1); notice_lang(s_OperServ, u, OPER_SQLINE_CLEAR); - } else { + + return MOD_CONT; + } + public: + CommandOSSQLine() : Command("SQLINE", 1, 4) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + + if (!stricmp(cmd, "ADD")) + return this->DoAdd(u, params); + else if (!stricmp(cmd, "DEL")) + return this->DoDel(u, params); + else if (!stricmp(cmd, "LIST")) + return this->DoList(u, params); + else if (!stricmp(cmd, "VIEW")) + return this->DoView(u, params); + else if (!stricmp(cmd, "CLEAR")) + return this->DoClear(u, params); + else + this->OnSyntaxError(u); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_oper(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_SQLINE); + return true; + } + + void OnSyntaxError(User *u) + { syntax_error(s_OperServ, u, "SQLINE", OPER_SQLINE_SYNTAX); } - return MOD_CONT; +}; + +class OSSQLine : public Module +{ + public: + OSSQLine(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + Command *c; + + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + + c = createCommand("SQLINE", do_sqline, is_services_oper, + OPER_HELP_SQLINE, -1, -1, -1, -1); + this->AddCommand(OPERSERV, c, MOD_UNIQUE); + + this->SetOperHelp(myOperServHelp); + if (!ircd->sqline) + throw ModuleException("Your IRCd does not support QLines."); + } +}; + + +/** + * Add the help response to anopes /os help output. + * @param u The user who is requesting help + **/ +void myOperServHelp(User *u) +{ + if (is_services_oper(u)) + notice_lang(s_OperServ, u, OPER_HELP_CMD_SQLINE); } -int sqline_view(int number, SXLine * sx, User * u, int *sent_header) +int sqline_view(int number, SXLine *sx, User *u, int *sent_header) { char timebuf[32], expirebuf[256]; struct tm tm; @@ -287,25 +348,22 @@ int sqline_view(int number, SXLine * sx, User * u, int *sent_header) if (!sx) return 0; - if (!*sent_header) { + if (!*sent_header) + { notice_lang(s_OperServ, u, OPER_SQLINE_VIEW_HEADER); *sent_header = 1; } tm = *localtime(&sx->seton); - strftime_lang(timebuf, sizeof(timebuf), u, STRFTIME_SHORT_DATE_FORMAT, - &tm); + strftime_lang(timebuf, sizeof(timebuf), u, STRFTIME_SHORT_DATE_FORMAT, &tm); expire_left(u->na, expirebuf, sizeof(expirebuf), sx->expires); - notice_lang(s_OperServ, u, OPER_SQLINE_VIEW_FORMAT, number, sx->mask, - sx->by, timebuf, expirebuf, sx->reason); + notice_lang(s_OperServ, u, OPER_SQLINE_VIEW_FORMAT, number, sx->mask, sx->by, timebuf, expirebuf, sx->reason); return 1; } /* Callback for enumeration purposes */ - -int sqline_view_callback(SList * slist, int number, void *item, - va_list args) +int sqline_view_callback(SList *slist, int number, void *item, va_list args) { User *u = va_arg(args, User *); int *sent_header = va_arg(args, int *); @@ -314,27 +372,24 @@ int sqline_view_callback(SList * slist, int number, void *item, } /* Lists an SQLINE entry, prefixing it with the header if needed */ - -int sqline_list(int number, SXLine * sx, User * u, int *sent_header) +int sqline_list(int number, SXLine *sx, User *u, int *sent_header) { if (!sx) return 0; - if (!*sent_header) { + if (!*sent_header) + { notice_lang(s_OperServ, u, OPER_SQLINE_LIST_HEADER); *sent_header = 1; } - notice_lang(s_OperServ, u, OPER_SQLINE_LIST_FORMAT, number, sx->mask, - sx->reason); + notice_lang(s_OperServ, u, OPER_SQLINE_LIST_FORMAT, number, sx->mask, sx->reason); return 1; } /* Callback for enumeration purposes */ - -int sqline_list_callback(SList * slist, int number, void *item, - va_list args) +int sqline_list_callback(SList *slist, int number, void *item, va_list args) { User *u = va_arg(args, User *); int *sent_header = va_arg(args, int *); diff --git a/src/core/os_staff.c b/src/core/os_staff.c index d136cecbc..54bfafec8 100644 --- a/src/core/os_staff.c +++ b/src/core/os_staff.c @@ -15,25 +15,76 @@ #include "module.h" -int do_staff(User * u); -void myOperServHelp(User * u); -int opers_list_callback(SList * slist, int number, void *item, - va_list args); -int opers_list(int number, NickCore * nc, User * u, char *level); +void myOperServHelp(User *u); +int opers_list_callback(SList *slist, int number, void *item, va_list args); +int opers_list(int number, NickCore *nc, User *u, char *level); + +class CommandOSStaff : public Command +{ + public: + CommandOSStaff() : Command("STAFF", 0, 0) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + int idx = 0; + User *au = NULL; + NickCore *nc; + NickAlias *na; + int found; + int i; + + notice_lang(s_OperServ, u, OPER_STAFF_LIST_HEADER); + slist_enum(&servopers, NULL, &opers_list_callback, u, "OPER"); + slist_enum(&servadmins, NULL, &opers_list_callback, u, "ADMN"); + + for (idx = 0; idx < RootNumber; ++idx) + { + found = 0; + if ((au = finduser(ServicesRoots[idx]))) /* see if user is online */ + { + found = 1; + notice_lang(s_OperServ, u, OPER_STAFF_FORMAT, '*', "ROOT", ServicesRoots[idx]); + } + else if ((nc = findcore(ServicesRoots[idx]))) + { + for (i = 0; i < nc->aliases.count; ++i) /* check all aliases */ + { + na = static_cast<NickAlias *>(nc->aliases.list[i]); + if ((au = finduser(na->nick))) /* see if user is online */ + { + found = 1; + notice_lang(s_OperServ, u, OPER_STAFF_AFORMAT, '*', "ROOT", ServicesRoots[idx], na->nick); + } + } + } + + if (!found) + notice_lang(s_OperServ, u, OPER_STAFF_FORMAT, ' ', "ROOT", ServicesRoots[idx]); + + } + notice_lang(s_OperServ, u, END_OF_ANY_LIST, "Staff"); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_OperServ, u, OPER_HELP_STAFF); + return true; + } +}; class OSStaff : public Module { public: OSStaff(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("STAFF", do_staff, NULL, OPER_HELP_STAFF, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSStaff(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } @@ -44,60 +95,15 @@ class OSStaff : public Module * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { notice_lang(s_OperServ, u, OPER_HELP_CMD_STAFF); } /** - * The /os staff command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_staff(User * u) -{ - int idx = 0; - User *au = NULL; - NickCore *nc; - NickAlias *na; - int found; - int i; - - notice_lang(s_OperServ, u, OPER_STAFF_LIST_HEADER); - slist_enum(&servopers, NULL, &opers_list_callback, u, "OPER"); - slist_enum(&servadmins, NULL, &opers_list_callback, u, "ADMN"); - - for (idx = 0; idx < RootNumber; idx++) { - found = 0; - if ((au = finduser(ServicesRoots[idx]))) { /* see if user is online */ - found = 1; - notice_lang(s_OperServ, u, OPER_STAFF_FORMAT, '*', "ROOT", - ServicesRoots[idx]); - } else if ((nc = findcore(ServicesRoots[idx]))) { - for (i = 0; i < nc->aliases.count; i++) { /* check all aliases */ - na = static_cast<NickAlias *>(nc->aliases.list[i]); - if ((au = finduser(na->nick))) { /* see if user is online */ - found = 1; - notice_lang(s_OperServ, u, OPER_STAFF_AFORMAT, - '*', "ROOT", ServicesRoots[idx], na->nick); - } - } - } - - if (!found) - notice_lang(s_OperServ, u, OPER_STAFF_FORMAT, ' ', "ROOT", - ServicesRoots[idx]); - - } - notice_lang(s_OperServ, u, END_OF_ANY_LIST, "Staff"); - return MOD_CONT; -} - -/** * Function for the enumerator to call **/ -int opers_list_callback(SList * slist, int number, void *item, - va_list args) +int opers_list_callback(SList *slist, int number, void *item, va_list args) { User *u = va_arg(args, User *); char *level = va_arg(args, char *); @@ -109,7 +115,7 @@ int opers_list_callback(SList * slist, int number, void *item, /** * Display an Opers list Entry **/ -int opers_list(int number, NickCore * nc, User * u, char *level) +int opers_list(int number, NickCore *nc, User *u, char *level) { User *au = NULL; NickAlias *na; @@ -120,24 +126,26 @@ int opers_list(int number, NickCore * nc, User * u, char *level) return 0; found = 0; - if ((au = finduser(nc->display))) { /* see if user is online */ + if ((au = finduser(nc->display))) /* see if user is online */ + { found = 1; - notice_lang(s_OperServ, u, OPER_STAFF_FORMAT, '*', level, - nc->display); - } else { - for (i = 0; i < nc->aliases.count; i++) { /* check all aliases */ + notice_lang(s_OperServ, u, OPER_STAFF_FORMAT, '*', level, nc->display); + } + else + { + for (i = 0; i < nc->aliases.count; ++i) /* check all aliases */ + { na = static_cast<NickAlias *>(nc->aliases.list[i]); - if ((au = finduser(na->nick))) { /* see if user is online */ + if ((au = finduser(na->nick))) /* see if user is online */ + { found = 1; - notice_lang(s_OperServ, u, OPER_STAFF_AFORMAT, '*', level, - nc->display, na->nick); + notice_lang(s_OperServ, u, OPER_STAFF_AFORMAT, '*', level, nc->display, na->nick); } } } if (!found) - notice_lang(s_OperServ, u, OPER_STAFF_FORMAT, ' ', level, - nc->display); + notice_lang(s_OperServ, u, OPER_STAFF_FORMAT, ' ', level, nc->display); return 1; } diff --git a/src/core/os_stats.c b/src/core/os_stats.c index 056ae7aa5..aeaa02615 100644 --- a/src/core/os_stats.c +++ b/src/core/os_stats.c @@ -15,359 +15,330 @@ #include "module.h" - - -int do_stats(User * u); void get_operserv_stats(long *nrec, long *memuse); -void myOperServHelp(User * u); +void myOperServHelp(User *u); -class OSStats : public Module +class CommandOSStats : public Command { - public: - OSStats(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + CommandResult DoStatsAkill(User *u, std::vector<std::string> ¶ms) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("STATS", do_stats, NULL, OPER_HELP_STATS, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - c = createCommand("UPTIME", do_stats, NULL, OPER_HELP_STATS, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - - this->SetOperHelp(myOperServHelp); - } -}; - - -/** - * Add the help response to anopes /os help output. - * @param u The user who is requesting help - **/ -void myOperServHelp(User * u) -{ - notice_lang(s_OperServ, u, OPER_HELP_CMD_STATS); -} - -/** - * Count servers connected to server s - * @param s The server to start counting from - * @return Amount of servers connected to server s - **/ -int stats_count_servers(Server * s) -{ - int count = 0; - - while (s) { - count++; - if (s->links) - count += stats_count_servers(s->links); - s = s->next; - } - - return count; -} - -/** - * The /os stats command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_stats(User * u) -{ - time_t uptime = time(NULL) - start_time; - char *extra = strtok(NULL, ""); - int days = uptime / 86400, hours = (uptime / 3600) % 24, - mins = (uptime / 60) % 60, secs = uptime % 60; - struct tm *tm; - char timebuf[64]; - char buf[512]; - int buflen; - int i; - - if (extra && stricmp(extra, "ALL") != 0) { - if (stricmp(extra, "AKILL") == 0) { - int timeout; - /* AKILLs */ - notice_lang(s_OperServ, u, OPER_STATS_AKILL_COUNT, - akills.count); - timeout = AutokillExpiry + 59; + int timeout; + /* AKILLs */ + notice_lang(s_OperServ, u, OPER_STATS_AKILL_COUNT, akills.count); + timeout = AutokillExpiry + 59; + if (timeout >= 172800) + notice_lang(s_OperServ, u, OPER_STATS_AKILL_EXPIRE_DAYS, timeout / 86400); + else if (timeout >= 86400) + notice_lang(s_OperServ, u, OPER_STATS_AKILL_EXPIRE_DAY); + else if (timeout >= 7200) + notice_lang(s_OperServ, u, OPER_STATS_AKILL_EXPIRE_HOURS, timeout / 3600); + else if (timeout >= 3600) + notice_lang(s_OperServ, u, OPER_STATS_AKILL_EXPIRE_HOUR); + else if (timeout >= 120) + notice_lang(s_OperServ, u, OPER_STATS_AKILL_EXPIRE_MINS, timeout / 60); + else if (timeout >= 60) + notice_lang(s_OperServ, u, OPER_STATS_AKILL_EXPIRE_MIN); + else + notice_lang(s_OperServ, u, OPER_STATS_AKILL_EXPIRE_NONE); + if (ircd->sgline) + { + /* SGLINEs */ + notice_lang(s_OperServ, u, OPER_STATS_SGLINE_COUNT, sglines.count); + timeout = SGLineExpiry + 59; if (timeout >= 172800) - notice_lang(s_OperServ, u, OPER_STATS_AKILL_EXPIRE_DAYS, - timeout / 86400); + notice_lang(s_OperServ, u, OPER_STATS_SGLINE_EXPIRE_DAYS, timeout / 86400); else if (timeout >= 86400) - notice_lang(s_OperServ, u, OPER_STATS_AKILL_EXPIRE_DAY); + notice_lang(s_OperServ, u, OPER_STATS_SGLINE_EXPIRE_DAY); else if (timeout >= 7200) - notice_lang(s_OperServ, u, OPER_STATS_AKILL_EXPIRE_HOURS, - timeout / 3600); + notice_lang(s_OperServ, u, OPER_STATS_SGLINE_EXPIRE_HOURS, timeout / 3600); else if (timeout >= 3600) - notice_lang(s_OperServ, u, OPER_STATS_AKILL_EXPIRE_HOUR); + notice_lang(s_OperServ, u, OPER_STATS_SGLINE_EXPIRE_HOUR); else if (timeout >= 120) - notice_lang(s_OperServ, u, OPER_STATS_AKILL_EXPIRE_MINS, - timeout / 60); + notice_lang(s_OperServ, u, OPER_STATS_SGLINE_EXPIRE_MINS, timeout / 60); else if (timeout >= 60) - notice_lang(s_OperServ, u, OPER_STATS_AKILL_EXPIRE_MIN); + notice_lang(s_OperServ, u, OPER_STATS_SGLINE_EXPIRE_MIN); else - notice_lang(s_OperServ, u, OPER_STATS_AKILL_EXPIRE_NONE); - if (ircd->sgline) { - /* SGLINEs */ - notice_lang(s_OperServ, u, OPER_STATS_SGLINE_COUNT, - sglines.count); - timeout = SGLineExpiry + 59; - if (timeout >= 172800) - notice_lang(s_OperServ, u, - OPER_STATS_SGLINE_EXPIRE_DAYS, - timeout / 86400); - else if (timeout >= 86400) - notice_lang(s_OperServ, u, - OPER_STATS_SGLINE_EXPIRE_DAY); - else if (timeout >= 7200) - notice_lang(s_OperServ, u, - OPER_STATS_SGLINE_EXPIRE_HOURS, - timeout / 3600); - else if (timeout >= 3600) - notice_lang(s_OperServ, u, - OPER_STATS_SGLINE_EXPIRE_HOUR); - else if (timeout >= 120) - notice_lang(s_OperServ, u, - OPER_STATS_SGLINE_EXPIRE_MINS, - timeout / 60); - else if (timeout >= 60) - notice_lang(s_OperServ, u, - OPER_STATS_SGLINE_EXPIRE_MIN); - else - notice_lang(s_OperServ, u, - OPER_STATS_SGLINE_EXPIRE_NONE); - } - if (ircd->sqline) { - /* SQLINEs */ - notice_lang(s_OperServ, u, OPER_STATS_SQLINE_COUNT, - sqlines.count); - timeout = SQLineExpiry + 59; - if (timeout >= 172800) - notice_lang(s_OperServ, u, - OPER_STATS_SQLINE_EXPIRE_DAYS, - timeout / 86400); - else if (timeout >= 86400) - notice_lang(s_OperServ, u, - OPER_STATS_SQLINE_EXPIRE_DAY); - else if (timeout >= 7200) - notice_lang(s_OperServ, u, - OPER_STATS_SQLINE_EXPIRE_HOURS, - timeout / 3600); - else if (timeout >= 3600) - notice_lang(s_OperServ, u, - OPER_STATS_SQLINE_EXPIRE_HOUR); - else if (timeout >= 120) - notice_lang(s_OperServ, u, - OPER_STATS_SQLINE_EXPIRE_MINS, - timeout / 60); - else if (timeout >= 60) - notice_lang(s_OperServ, u, - OPER_STATS_SQLINE_EXPIRE_MIN); - else - notice_lang(s_OperServ, u, - OPER_STATS_SQLINE_EXPIRE_NONE); - } - if (ircd->szline) { - /* SZLINEs */ - notice_lang(s_OperServ, u, OPER_STATS_SZLINE_COUNT, - szlines.count); - timeout = SZLineExpiry + 59; - if (timeout >= 172800) - notice_lang(s_OperServ, u, - OPER_STATS_SZLINE_EXPIRE_DAYS, - timeout / 86400); - else if (timeout >= 86400) - notice_lang(s_OperServ, u, - OPER_STATS_SZLINE_EXPIRE_DAY); - else if (timeout >= 7200) - notice_lang(s_OperServ, u, - OPER_STATS_SZLINE_EXPIRE_HOURS, - timeout / 3600); - else if (timeout >= 3600) - notice_lang(s_OperServ, u, - OPER_STATS_SZLINE_EXPIRE_HOUR); - else if (timeout >= 120) - notice_lang(s_OperServ, u, - OPER_STATS_SZLINE_EXPIRE_MINS, - timeout / 60); - else if (timeout >= 60) - notice_lang(s_OperServ, u, - OPER_STATS_SZLINE_EXPIRE_MIN); - else - notice_lang(s_OperServ, u, - OPER_STATS_SZLINE_EXPIRE_NONE); - } - return MOD_CONT; - } else if (!stricmp(extra, "RESET")) { - if (is_services_admin(u)) { - maxusercnt = usercnt; - notice_lang(s_OperServ, u, OPER_STATS_RESET); - } else { - notice_lang(s_OperServ, u, PERMISSION_DENIED); - } - return MOD_CONT; - } else if (stricmp(extra, "MEMORY") && stricmp(extra, "UPLINK")) { - notice_lang(s_OperServ, u, OPER_STATS_UNKNOWN_OPTION, extra); + notice_lang(s_OperServ, u, OPER_STATS_SGLINE_EXPIRE_NONE); + } + if (ircd->sqline) + { + /* SQLINEs */ + notice_lang(s_OperServ, u, OPER_STATS_SQLINE_COUNT, sqlines.count); + timeout = SQLineExpiry + 59; + if (timeout >= 172800) + notice_lang(s_OperServ, u, OPER_STATS_SQLINE_EXPIRE_DAYS, timeout / 86400); + else if (timeout >= 86400) + notice_lang(s_OperServ, u, OPER_STATS_SQLINE_EXPIRE_DAY); + else if (timeout >= 7200) + notice_lang(s_OperServ, u, OPER_STATS_SQLINE_EXPIRE_HOURS, timeout / 3600); + else if (timeout >= 3600) + notice_lang(s_OperServ, u, OPER_STATS_SQLINE_EXPIRE_HOUR); + else if (timeout >= 120) + notice_lang(s_OperServ, u, OPER_STATS_SQLINE_EXPIRE_MINS, timeout / 60); + else if (timeout >= 60) + notice_lang(s_OperServ, u, OPER_STATS_SQLINE_EXPIRE_MIN); + else + notice_lang(s_OperServ, u, OPER_STATS_SQLINE_EXPIRE_NONE); + } + if (ircd->szline) + { + /* SZLINEs */ + notice_lang(s_OperServ, u, OPER_STATS_SZLINE_COUNT, szlines.count); + timeout = SZLineExpiry + 59; + if (timeout >= 172800) + notice_lang(s_OperServ, u, OPER_STATS_SZLINE_EXPIRE_DAYS, timeout / 86400); + else if (timeout >= 86400) + notice_lang(s_OperServ, u, OPER_STATS_SZLINE_EXPIRE_DAY); + else if (timeout >= 7200) + notice_lang(s_OperServ, u, OPER_STATS_SZLINE_EXPIRE_HOURS, timeout / 3600); + else if (timeout >= 3600) + notice_lang(s_OperServ, u, OPER_STATS_SZLINE_EXPIRE_HOUR); + else if (timeout >= 120) + notice_lang(s_OperServ, u, OPER_STATS_SZLINE_EXPIRE_MINS, timeout / 60); + else if (timeout >= 60) + notice_lang(s_OperServ, u, OPER_STATS_SZLINE_EXPIRE_MIN); + else + notice_lang(s_OperServ, u, OPER_STATS_SZLINE_EXPIRE_NONE); + } + return MOD_CONT; + } + + CommandResult DoStatsReset(User *u, std::vector<std::string> ¶ms) + { + if (is_services_admin(u)) + { + maxusercnt = usercnt; + notice_lang(s_OperServ, u, OPER_STATS_RESET); } + else + notice_lang(s_OperServ, u, PERMISSION_DENIED); + return MOD_CONT; } - if (!extra || ((stricmp(extra, "MEMORY") != 0) - && (stricmp(extra, "UPLINK") != 0))) { - notice_lang(s_OperServ, u, OPER_STATS_CURRENT_USERS, usercnt, - opcnt); + CommandResult DoStatsUptime(User *u, std::vector<std::string> ¶ms) + { + notice_lang(s_OperServ, u, OPER_STATS_CURRENT_USERS, usercnt, opcnt); tm = localtime(&maxusertime); - strftime_lang(timebuf, sizeof(timebuf), u, - STRFTIME_DATE_TIME_FORMAT, tm); - notice_lang(s_OperServ, u, OPER_STATS_MAX_USERS, maxusercnt, - timebuf); - if (days > 1) { - notice_lang(s_OperServ, u, OPER_STATS_UPTIME_DHMS, - days, hours, mins, secs); - } else if (days == 1) { - notice_lang(s_OperServ, u, OPER_STATS_UPTIME_1DHMS, - days, hours, mins, secs); - } else { + strftime_lang(timebuf, sizeof(timebuf), u, STRFTIME_DATE_TIME_FORMAT, tm); + notice_lang(s_OperServ, u, OPER_STATS_MAX_USERS, maxusercnt, timebuf); + if (days > 1) + notice_lang(s_OperServ, u, OPER_STATS_UPTIME_DHMS, days, hours, mins, secs); + else if (days == 1) + notice_lang(s_OperServ, u, OPER_STATS_UPTIME_1DHMS, days, hours, mins, secs); + else + { if (hours > 1) { - if (mins != 1) { - if (secs != 1) { - notice_lang(s_OperServ, u, OPER_STATS_UPTIME_HMS, - hours, mins, secs); - } else { - notice_lang(s_OperServ, u, OPER_STATS_UPTIME_HM1S, - hours, mins, secs); - } - } else { - if (secs != 1) { - notice_lang(s_OperServ, u, OPER_STATS_UPTIME_H1MS, - hours, mins, secs); - } else { - notice_lang(s_OperServ, u, OPER_STATS_UPTIME_H1M1S, - hours, mins, secs); - } + if (mins != 1) + { + if (secs != 1) + notice_lang(s_OperServ, u, OPER_STATS_UPTIME_HMS, hours, mins, secs); + else + notice_lang(s_OperServ, u, OPER_STATS_UPTIME_HM1S, hours, mins, secs); + } + else + { + if (secs != 1) + notice_lang(s_OperServ, u, OPER_STATS_UPTIME_H1MS, hours, mins, secs); + else + notice_lang(s_OperServ, u, OPER_STATS_UPTIME_H1M1S, hours, mins, secs); + } + } + else if (hours == 1) + { + if (mins != 1) + { + if (secs != 1) + notice_lang(s_OperServ, u, OPER_STATS_UPTIME_1HMS, hours, mins, secs); + else + notice_lang(s_OperServ, u, OPER_STATS_UPTIME_1HM1S, hours, mins, secs); } - } else if (hours == 1) { - if (mins != 1) { - if (secs != 1) { - notice_lang(s_OperServ, u, OPER_STATS_UPTIME_1HMS, - hours, mins, secs); - } else { - notice_lang(s_OperServ, u, OPER_STATS_UPTIME_1HM1S, - hours, mins, secs); - } - } else { - if (secs != 1) { - notice_lang(s_OperServ, u, OPER_STATS_UPTIME_1H1MS, - hours, mins, secs); - } else { - notice_lang(s_OperServ, u, - OPER_STATS_UPTIME_1H1M1S, hours, mins, - secs); - } + else + { + if (secs != 1) + notice_lang(s_OperServ, u, OPER_STATS_UPTIME_1H1MS, hours, mins, secs); + else + notice_lang(s_OperServ, u, OPER_STATS_UPTIME_1H1M1S, hours, mins, secs); + } + } + else + { + if (mins != 1) + { + if (secs != 1) + notice_lang(s_OperServ, u, OPER_STATS_UPTIME_MS, mins, secs); + else + notice_lang(s_OperServ, u, OPER_STATS_UPTIME_M1S, mins, secs); } - } else { - if (mins != 1) { - if (secs != 1) { - notice_lang(s_OperServ, u, OPER_STATS_UPTIME_MS, - mins, secs); - } else { - notice_lang(s_OperServ, u, OPER_STATS_UPTIME_M1S, - mins, secs); - } - } else { - if (secs != 1) { - notice_lang(s_OperServ, u, OPER_STATS_UPTIME_1MS, - mins, secs); - } else { - notice_lang(s_OperServ, u, OPER_STATS_UPTIME_1M1S, - mins, secs); - } + else + { + if (secs != 1) + notice_lang(s_OperServ, u, OPER_STATS_UPTIME_1MS, mins, secs); + else + notice_lang(s_OperServ, u, OPER_STATS_UPTIME_1M1S, mins, secs); } } } } - if (extra && ((stricmp(extra, "ALL") == 0) - || (stricmp(extra, "UPLINK") == 0)) - && is_services_admin(u)) { + CommandResult DoStatsUplink(User *u, std::vector<std::string> ¶ms) + { buf[0] = '\0'; - buflen = 511; /* How confusing, this is the amount of space left! */ - for (i = 0; capab_info[i].token; i++) { - if (uplink_capab & capab_info[i].flag) { + buflen = 511; /* How confusing, this is the amount of space left! */ + for (i = 0; capab_info[i].token; ++i) + { + if (uplink_capab & capab_info[i].flag) + { strncat(buf, " ", buflen); - buflen--; + --buflen; strncat(buf, capab_info[i].token, buflen); buflen -= strlen(capab_info[i].token); /* Special cases */ - if (capab_info[i].flag == CAPAB_CHANMODE) { + if (capab_info[i].flag == CAPAB_CHANMODE) + { strncat(buf, "=", buflen); - buflen--; + --buflen; strncat(buf, ircd->chanmodes, buflen); buflen -= strlen(ircd->chanmodes); } - if (capab_info[i].flag == CAPAB_NICKCHARS) { + if (capab_info[i].flag == CAPAB_NICKCHARS) + { strncat(buf, "=", buflen); - buflen--; - if (ircd->nickchars) { + --buflen; + if (ircd->nickchars) + { strncat(buf, ircd->nickchars, buflen); buflen -= strlen(ircd->nickchars); - } /* leave blank if it was null */ + } /* leave blank if it was null */ } } } - notice_lang(s_OperServ, u, OPER_STATS_UPLINK_SERVER, - serv_uplink->name); + notice_lang(s_OperServ, u, OPER_STATS_UPLINK_SERVER, serv_uplink->name); notice_lang(s_OperServ, u, OPER_STATS_UPLINK_CAPAB, buf); - notice_lang(s_OperServ, u, OPER_STATS_UPLINK_SERVER_COUNT, - stats_count_servers(serv_uplink)); + notice_lang(s_OperServ, u, OPER_STATS_UPLINK_SERVER_COUNT, stats_count_servers(serv_uplink)); + return MOD_CONT; } - if (extra && ((stricmp(extra, "ALL") == 0) - || (stricmp(extra, "MEMORY") == 0)) - && is_services_admin(u)) { + CommandResult DoStatsMemory(User *u, std::vector<std::string> ¶ms) + { long count, mem; - notice_lang(s_OperServ, u, OPER_STATS_BYTES_READ, - total_read / 1024); - notice_lang(s_OperServ, u, OPER_STATS_BYTES_WRITTEN, - total_written / 1024); + notice_lang(s_OperServ, u, OPER_STATS_BYTES_READ, total_read / 1024); + notice_lang(s_OperServ, u, OPER_STATS_BYTES_WRITTEN, total_written / 1024); get_user_stats(&count, &mem); - notice_lang(s_OperServ, u, OPER_STATS_USER_MEM, count, - (mem + 512) / 1024); + notice_lang(s_OperServ, u, OPER_STATS_USER_MEM, count, (mem + 512) / 1024); get_channel_stats(&count, &mem); - notice_lang(s_OperServ, u, OPER_STATS_CHANNEL_MEM, count, - (mem + 512) / 1024); + notice_lang(s_OperServ, u, OPER_STATS_CHANNEL_MEM, count, (mem + 512) / 1024); get_core_stats(&count, &mem); - notice_lang(s_OperServ, u, OPER_STATS_GROUPS_MEM, count, - (mem + 512) / 1024); + notice_lang(s_OperServ, u, OPER_STATS_GROUPS_MEM, count, (mem + 512) / 1024); get_aliases_stats(&count, &mem); - notice_lang(s_OperServ, u, OPER_STATS_ALIASES_MEM, count, - (mem + 512) / 1024); + notice_lang(s_OperServ, u, OPER_STATS_ALIASES_MEM, count, (mem + 512) / 1024); get_chanserv_stats(&count, &mem); - notice_lang(s_OperServ, u, OPER_STATS_CHANSERV_MEM, count, - (mem + 512) / 1024); - if (s_BotServ) { + notice_lang(s_OperServ, u, OPER_STATS_CHANSERV_MEM, count, (mem + 512) / 1024); + if (s_BotServ) + { get_botserv_stats(&count, &mem); - notice_lang(s_OperServ, u, OPER_STATS_BOTSERV_MEM, count, - (mem + 512) / 1024); + notice_lang(s_OperServ, u, OPER_STATS_BOTSERV_MEM, count, (mem + 512) / 1024); } - if (s_HostServ) { + if (s_HostServ) + { get_hostserv_stats(&count, &mem); - notice_lang(s_OperServ, u, OPER_STATS_HOSTSERV_MEM, count, - (mem + 512) / 1024); + notice_lang(s_OperServ, u, OPER_STATS_HOSTSERV_MEM, count, (mem + 512) / 1024); } get_operserv_stats(&count, &mem); - notice_lang(s_OperServ, u, OPER_STATS_OPERSERV_MEM, count, - (mem + 512) / 1024); + notice_lang(s_OperServ, u, OPER_STATS_OPERSERV_MEM, count, (mem + 512) / 1024); get_session_stats(&count, &mem); - notice_lang(s_OperServ, u, OPER_STATS_SESSIONS_MEM, count, - (mem + 512) / 1024); + notice_lang(s_OperServ, u, OPER_STATS_SESSIONS_MEM, count, (mem + 512) / 1024); + } + public: + CommandOSStats() : Command("STATS", 0, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + time_t uptime = time(NULL) - start_time; + const char *extra = params.size() ? params[0].c_str() : NULL; + int days = uptime / 86400, hours = (uptime / 3600) % 24, mins = (uptime / 60) % 60, secs = uptime % 60; + struct tm *tm; + char timebuf[64]; + char buf[512]; + int buflen; + int i; + + if (extra && stricmp(extra, "ALL")) + { + if (!stricmp(extra, "AKILL")) + return this->DoStatsAkill(u, params); + else if (!stricmp(extra, "RESET")) + return this->DoStatsReset(u, params); + else if (stricmp(extra, "MEMORY") && stricmp(extra, "UPLINK")) + notice_lang(s_OperServ, u, OPER_STATS_UNKNOWN_OPTION, extra); + } + + if (!extra || (stricmp(extra, "MEMORY") && stricmp(extra, "UPLINK"))) + return this->DoStatsUptime(u, params); + + if (extra && (!stricmp(extra, "ALL") || !stricmp(extra, "UPLINK")) && is_services_admin(u)) + return this->DoStatsUplink(u, params); + + if (extra && (!stricmp(extra, "ALL") || !stricmp(extra, "MEMORY")) && is_services_admin(u)) + return this->DoStatsMemory(u, params); + + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_OperServ, u, OPER_HELP_STATS); + return true; + } +}; + +class OSStats : public Module +{ + public: + OSStats(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + + this->AddCommand(OPERSERV, new CommandOSStats(), MOD_UNIQUE); + + this->SetOperHelp(myOperServHelp); + } +}; + + +/** + * Add the help response to anopes /os help output. + * @param u The user who is requesting help + **/ +void myOperServHelp(User *u) +{ + notice_lang(s_OperServ, u, OPER_HELP_CMD_STATS); +} + +/** + * Count servers connected to server s + * @param s The server to start counting from + * @return Amount of servers connected to server s + **/ +int stats_count_servers(Server *s) +{ + int count = 0; + + while (s) + { + ++count; + if (s->links) + count += stats_count_servers(s->links); + s = s->next; } - return MOD_CONT; + + return count; } void get_operserv_stats(long *nrec, long *memuse) @@ -381,7 +352,8 @@ void get_operserv_stats(long *nrec, long *memuse) mem += akills.capacity; mem += akills.count * sizeof(Akill); - for (i = 0; i < akills.count; i++) { + for (i = 0; i < akills.count; ++i) + { ak = static_cast<Akill *>(akills.list[i]); mem += strlen(ak->user) + 1; mem += strlen(ak->host) + 1; @@ -389,36 +361,42 @@ void get_operserv_stats(long *nrec, long *memuse) mem += strlen(ak->reason) + 1; } - if (ircd->sgline) { + if (ircd->sgline) + { count += sglines.count; mem += sglines.capacity; mem += sglines.count * sizeof(SXLine); - for (i = 0; i < sglines.count; i++) { + for (i = 0; i < sglines.count; ++i) + { sx = static_cast<SXLine *>(sglines.list[i]); mem += strlen(sx->mask) + 1; mem += strlen(sx->by) + 1; mem += strlen(sx->reason) + 1; } } - if (ircd->sqline) { + if (ircd->sqline) + { count += sqlines.count; mem += sqlines.capacity; mem += sqlines.count * sizeof(SXLine); - for (i = 0; i < sqlines.count; i++) { + for (i = 0; i < sqlines.count; ++i) + { sx = static_cast<SXLine *>(sqlines.list[i]); mem += strlen(sx->mask) + 1; mem += strlen(sx->by) + 1; mem += strlen(sx->reason) + 1; } } - if (ircd->szline) { + if (ircd->szline) + { count += szlines.count; mem += szlines.capacity; mem += szlines.count * sizeof(SXLine); - for (i = 0; i < szlines.count; i++) { + for (i = 0; i < szlines.count; ++i) + { sx = static_cast<SXLine *>(szlines.list[i]); mem += strlen(sx->mask) + 1; mem += strlen(sx->by) + 1; @@ -426,7 +404,6 @@ void get_operserv_stats(long *nrec, long *memuse) } } - get_news_stats(&count2, &mem2); count += count2; mem += mem2; diff --git a/src/core/os_svsnick.c b/src/core/os_svsnick.c index 64a2d2f16..bb4e67695 100644 --- a/src/core/os_svsnick.c +++ b/src/core/os_svsnick.c @@ -15,23 +15,93 @@ #include "module.h" -int do_svsnick(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSSVSNick : public Command +{ + public: + CommandOSSVSNick() : Command("SVSNICK", 2, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[0].c_str(); + const char *newnick = params[1].c_str(); + + NickAlias *na; + char *c; + + /* Only allow this if SuperAdmin is enabled */ + if (!u->isSuperAdmin) + { + notice_lang(s_OperServ, u, OPER_SUPER_ADMIN_ONLY); + return MOD_CONT; + } + + /* Truncate long nicknames to NICKMAX-2 characters */ + if (strlen(newnick) > NICKMAX - 2) + { + notice_lang(s_OperServ, u, NICK_X_TRUNCATED, newnick, NICKMAX - 2, newnick); + newnick[NICKMAX - 2] = '\0'; + } + + /* Check for valid characters */ + if (*newnick == '-' || isdigit(*newnick)) + { + notice_lang(s_OperServ, u, NICK_X_ILLEGAL, newnick); + return MOD_CONT; + } + for (c = newnick; *c && c - newnick < NICKMAX; ++c) + { + if (!isvalidnick(*c)) + { + notice_lang(s_OperServ, u, NICK_X_ILLEGAL, newnick); + return MOD_CONT; + } + } + + /* Check for a nick in use or a forbidden/suspended nick */ + if (!finduser(nick)) + notice_lang(s_OperServ, u, NICK_X_NOT_IN_USE, nick); + else if (finduser(newnick)) + notice_lang(s_OperServ, u, NICK_X_IN_USE, newnick); + else if ((na = findnick(newnick)) && (na->status & NS_VERBOTEN)) + notice_lang(s_OperServ, u, NICK_X_FORBIDDEN, newnick); + else + { + notice_lang(s_OperServ, u, OPER_SVSNICK_NEWNICK, nick, newnick); + ircdproto->SendGlobops(s_OperServ, "%s used SVSNICK to change %s to %s", u->nick, nick, newnick); + ircdproto->SendForceNickChange(nick, newnick, time(NULL)); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_root(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_SVSNICK); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "SVSNICK", OPER_SVSNICK_SYNTAX); + } +}; class OSSVSNick : public Module { public: OSSVSNick(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("SVSNICK", do_svsnick, is_services_root, - OPER_HELP_SVSNICK, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSSVSNick(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); if (!ircd->svsnick) @@ -44,72 +114,10 @@ class OSSVSNick : public Module * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_admin(u) && u->isSuperAdmin) { + if (is_services_admin(u) && u->isSuperAdmin) notice_lang(s_OperServ, u, OPER_HELP_CMD_SVSNICK); - } -} - -/** - * The /os svsnick command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -/* Forcefully change a user's nickname */ - -int do_svsnick(User * u) -{ - char *nick = strtok(NULL, " "); - char *newnick = strtok(NULL, " "); - - NickAlias *na; - char *c; - - /* Only allow this if SuperAdmin is enabled */ - if (!u->isSuperAdmin) { - notice_lang(s_OperServ, u, OPER_SUPER_ADMIN_ONLY); - return MOD_CONT; - } - - if (!nick || !newnick) { - syntax_error(s_OperServ, u, "SVSNICK", OPER_SVSNICK_SYNTAX); - return MOD_CONT; - } - - /* Truncate long nicknames to NICKMAX-2 characters */ - if (strlen(newnick) > (NICKMAX - 2)) { - notice_lang(s_OperServ, u, NICK_X_TRUNCATED, - newnick, NICKMAX - 2, newnick); - newnick[NICKMAX - 2] = '\0'; - } - - /* Check for valid characters */ - if (*newnick == '-' || isdigit(*newnick)) { - notice_lang(s_OperServ, u, NICK_X_ILLEGAL, newnick); - return MOD_CONT; - } - for (c = newnick; *c && (c - newnick) < NICKMAX; c++) { - if (!isvalidnick(*c)) { - notice_lang(s_OperServ, u, NICK_X_ILLEGAL, newnick); - return MOD_CONT; - } - } - - /* Check for a nick in use or a forbidden/suspended nick */ - if (!finduser(nick)) { - notice_lang(s_OperServ, u, NICK_X_NOT_IN_USE, nick); - } else if (finduser(newnick)) { - notice_lang(s_OperServ, u, NICK_X_IN_USE, newnick); - } else if ((na = findnick(newnick)) && (na->status & NS_VERBOTEN)) { - notice_lang(s_OperServ, u, NICK_X_FORBIDDEN, newnick); - } else { - notice_lang(s_OperServ, u, OPER_SVSNICK_NEWNICK, nick, newnick); - ircdproto->SendGlobops(s_OperServ, "%s used SVSNICK to change %s to %s", - u->nick, nick, newnick); - ircdproto->SendForceNickChange(nick, newnick, time(NULL)); - } - return MOD_CONT; } MODULE_INIT("os_svsnick", OSSVSNick) diff --git a/src/core/os_szline.c b/src/core/os_szline.c index f6403c301..22d2eabde 100644 --- a/src/core/os_szline.c +++ b/src/core/os_szline.c @@ -15,72 +15,31 @@ #include "module.h" -int do_szline(User * u); -void myOperServHelp(User * u); -int szline_view_callback(SList * slist, int number, void *item, - va_list args); -int szline_list_callback(SList * slist, int number, void *item, - va_list args); -int szline_view(int number, SXLine * sx, User * u, int *sent_header); -int szline_list(int number, SXLine * sx, User * u, int *sent_header); +void myOperServHelp(User *u); +int szline_view_callback(SList *slist, int number, void *item, va_list args); +int szline_list_callback(SList *slist, int number, void *item, va_list args); +int szline_view(int number, SXLine *sx, User *u, int *sent_header); +int szline_list(int number, SXLine *sx, User *u, int *sent_header); -class OSSZLine : public Module +class CommandOSSZLine : public Command { - public: - OSSZLine(const std::string &modname, const std::string &creator) : Module(modname, creator) + private: + CommandResult DoAdd(User *u, std::vector<std::string> ¶ms) { - Command *c; - - this->SetAuthor("Anope"); - this->SetVersion("$Id$"); - this->SetType(CORE); - - c = createCommand("SZLINE", do_szline, is_services_oper, - OPER_HELP_SZLINE, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); - - this->SetOperHelp(myOperServHelp); - if (!ircd->szline) - throw ModuleException("Your IRCd does not support ZLINEs"); - } -}; - - -/** - * Add the help response to anopes /os help output. - * @param u The user who is requesting help - **/ -void myOperServHelp(User * u) -{ - if (is_services_oper(u)) { - notice_lang(s_OperServ, u, OPER_HELP_CMD_SZLINE); - } -} - -/** - * The /os szline command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_szline(User * u) -{ - char *cmd = strtok(NULL, " "); - - if (!cmd) - cmd = ""; - - if (!stricmp(cmd, "ADD")) { - int deleted = 0; - char *expiry, *mask, *reason; + int deleted = 0, last_param = 2; + const char *expiry, *mask; + char reason[BUFSIZE]; time_t expires; - mask = strtok(NULL, " "); - if (mask && *mask == '+') { + mask = params.size() > 1 ? params[1].c_str() : NULL; + if (mask && *mask == '+') + { expiry = mask; - mask = strtok(NULL, " "); - } else { - expiry = NULL; + mask = params.size() > 2 ? params[2].c_str() : NULL; + last_param = 3; } + else + expiry = NULL; expires = expiry ? dotime(expiry) : SZLineExpiry; /* If the expiry given does not contain a final letter, it's in days, @@ -89,22 +48,32 @@ int do_szline(User * u) if (expiry && isdigit(expiry[strlen(expiry) - 1])) expires *= 86400; /* Do not allow less than a minute expiry time */ - if (expires != 0 && expires < 60) { + if (expires != 0 && expires < 60) + { notice_lang(s_OperServ, u, BAD_EXPIRY_TIME); return MOD_CONT; - } else if (expires > 0) { - expires += time(NULL); } + else if (expires > 0) + expires += time(NULL); - if (mask && (reason = strtok(NULL, ""))) { + if (params.size() < last_param) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + snprintf(reason, sizeof(reason), "%s%s%s", params[last_param].c_str(), last_param == 2 ? " " : "", last_param == 2 ? param[3].c_str() : ""); + if (mask && *reason) + { /* We first do some sanity check on the proposed mask. */ - if (strchr(mask, '!') || strchr(mask, '@')) { + if (strchr(mask, '!') || strchr(mask, '@')) + { notice_lang(s_OperServ, u, OPER_SZLINE_ONLY_IPS); return MOD_CONT; } - if (strspn(mask, "*?") == strlen(mask)) { + if (strspn(mask, "*?") == strlen(mask)) + { notice_lang(s_OperServ, u, USERHOST_MASK_TOO_WIDE, mask); return MOD_CONT; } @@ -113,78 +82,89 @@ int do_szline(User * u) if (deleted < 0) return MOD_CONT; else if (deleted) - notice_lang(s_OperServ, u, OPER_SZLINE_DELETED_SEVERAL, - deleted); + notice_lang(s_OperServ, u, OPER_SZLINE_DELETED_SEVERAL, deleted); notice_lang(s_OperServ, u, OPER_SZLINE_ADDED, mask); - if (WallOSSZLine) { + if (WallOSSZLine) + { char buf[128]; - if (!expires) { + if (!expires) strcpy(buf, "does not expire"); - } else { + else + { int wall_expiry = expires - time(NULL); char *s = NULL; - if (wall_expiry >= 86400) { + if (wall_expiry >= 86400) + { wall_expiry /= 86400; s = "day"; - } else if (wall_expiry >= 3600) { + } + else if (wall_expiry >= 3600) + { wall_expiry /= 3600; s = "hour"; - } else if (wall_expiry >= 60) { + } + else if (wall_expiry >= 60) + { wall_expiry /= 60; s = "minute"; } - snprintf(buf, sizeof(buf), "expires in %d %s%s", - wall_expiry, s, - (wall_expiry == 1) ? "" : "s"); + snprintf(buf, sizeof(buf), "expires in %d %s%s", wall_expiry, s, wall_expiry == 1 ? "" : "s"); } - ircdproto->SendGlobops(s_OperServ, - "%s added an SZLINE for %s (%s)", u->nick, - mask, buf); + ircdproto->SendGlobops(s_OperServ, "%s added an SZLINE for %s (%s)", u->nick, mask, buf); } if (readonly) notice_lang(s_OperServ, u, READ_ONLY_MODE); - } else { - syntax_error(s_OperServ, u, "SZLINE", OPER_SZLINE_SYNTAX); } + else + this->OnSyntaxError(u); - } else if (!stricmp(cmd, "DEL")) { + return MOD_CONT; + } + CommandResult DoDel(User *u, std::vector<std::string> ¶ms) + { char *mask; int res = 0; - mask = strtok(NULL, " "); + mask = params.size() > 1 ? params[1].c_str() : NULL; - if (!mask) { - syntax_error(s_OperServ, u, "SZLINE", OPER_SZLINE_SYNTAX); + if (!mask) + { + this->OnSyntaxError(u); return MOD_CONT; } - if (szlines.count == 0) { + if (!szlines.count) + { notice_lang(s_OperServ, u, OPER_SZLINE_LIST_EMPTY); return MOD_CONT; } - if (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask)) { + if (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask)) + { /* Deleting a range */ res = slist_delete_range(&szlines, mask, NULL); - if (res == 0) { + if (!res) + { notice_lang(s_OperServ, u, OPER_SZLINE_NO_MATCH); return MOD_CONT; - } else if (res == 1) { - notice_lang(s_OperServ, u, OPER_SZLINE_DELETED_ONE); - } else { - notice_lang(s_OperServ, u, OPER_SZLINE_DELETED_SEVERAL, - res); } - } else { - if ((res = slist_indexof(&szlines, mask)) == -1) { + else if (res == 1) + notice_lang(s_OperServ, u, OPER_SZLINE_DELETED_ONE); + else + notice_lang(s_OperServ, u, OPER_SZLINE_DELETED_SEVERAL, res); + } + else + { + if ((res = slist_indexof(&szlines, mask)) == -1) + { notice_lang(s_OperServ, u, OPER_SZLINE_NOT_FOUND, mask); return MOD_CONT; } @@ -196,85 +176,166 @@ int do_szline(User * u) if (readonly) notice_lang(s_OperServ, u, READ_ONLY_MODE); - } else if (!stricmp(cmd, "LIST")) { + return MOD_CONT; + } + + CommandResult DoList(User *u, std::vector<std::string> ¶ms) + { char *mask; int res, sent_header = 0; - if (szlines.count == 0) { + if (!szlines.count) + { notice_lang(s_OperServ, u, OPER_SZLINE_LIST_EMPTY); return MOD_CONT; } - mask = strtok(NULL, " "); + mask = params.size() > 1 : params[1].c_str() : NULL; - if (!mask || (isdigit(*mask) - && strspn(mask, "1234567890,-") == strlen(mask))) { - res = - slist_enum(&szlines, mask, &szline_list_callback, u, - &sent_header); - if (res == 0) { + if (!mask || (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask))) + { + res = slist_enum(&szlines, mask, &szline_list_callback, u, &sent_header); + if (!res) + { notice_lang(s_OperServ, u, OPER_SZLINE_NO_MATCH); return MOD_CONT; } - } else { + } + else + { int i; char *amask; - for (i = 0; i < szlines.count; i++) { + for (i = 0; i < szlines.count; ++i) + { amask = (static_cast<SXLine *>(szlines.list[i]))->mask; - if (!stricmp(mask, amask) - || match_wild_nocase(mask, amask)) + if (!stricmp(mask, amask) || match_wild_nocase(mask, amask)) szline_list(i + 1, static_cast<SXLine *>(szlines.list[i]), u, &sent_header); } if (!sent_header) notice_lang(s_OperServ, u, OPER_SZLINE_NO_MATCH); } - } else if (!stricmp(cmd, "VIEW")) { + + return MOD_CONT; + } + + CommandResult DoView(User *u, std::vector<std::string> ¶ms) + { char *mask; int res, sent_header = 0; - if (szlines.count == 0) { + if (!szlines.count) + { notice_lang(s_OperServ, u, OPER_SZLINE_LIST_EMPTY); return MOD_CONT; } - mask = strtok(NULL, " "); + mask = params.size() > 1 ? params[1].c_str() : NULL; - if (!mask || (isdigit(*mask) - && strspn(mask, "1234567890,-") == strlen(mask))) { - res = - slist_enum(&szlines, mask, &szline_view_callback, u, - &sent_header); - if (res == 0) { + if (!mask || (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask))) + { + res = slist_enum(&szlines, mask, &szline_view_callback, u, &sent_header); + if (!res) + { notice_lang(s_OperServ, u, OPER_SZLINE_NO_MATCH); return MOD_CONT; } - } else { + } + else + { int i; char *amask; - for (i = 0; i < szlines.count; i++) { + for (i = 0; i < szlines.count; ++i) + { amask = (static_cast<SXLine *>(szlines.list[i]))->mask; - if (!stricmp(mask, amask) - || match_wild_nocase(mask, amask)) + if (!stricmp(mask, amask) || match_wild_nocase(mask, amask)) szline_view(i + 1, static_cast<SXLine *>(szlines.list[i]), u, &sent_header); } if (!sent_header) notice_lang(s_OperServ, u, OPER_SZLINE_NO_MATCH); } - } else if (!stricmp(cmd, "CLEAR")) { + + return MOD_CONT; + } + + CommandResult DoClear(User *u, std::vector<std::string> ¶ms) + { slist_clear(&szlines, 1); notice_lang(s_OperServ, u, OPER_SZLINE_CLEAR); - } else { + + return MOD_CONT; + } + public: + CommandOSSZLine() : Command("SZLINE", 1, 4) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + + if (!stricmp(cmd, "ADD")) + return this->DoAdd(u, params); + else if (!stricmp(cmd, "DEL")) + return this->DoDel(u, params); + else if (!stricmp(cmd, "LIST")) + return this->DoList(u, params); + else if (!stricmp(cmd, "VIEW")) + return this->DoView(u, params); + else if (!stricmp(cmd, "CLEAR")) + return this->DoClear(u, params); + else + this->OnSyntaxError(u); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_oper(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_SZLINE); + return true; + } + + void OnSyntaxError(User *u) + { syntax_error(s_OperServ, u, "SZLINE", OPER_SZLINE_SYNTAX); } - return MOD_CONT; -} +}; + +class OSSZLine : public Module +{ + public: + OSSZLine(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + this->SetAuthor("Anope"); + this->SetVersion("$Id$"); + this->SetType(CORE); + this->AddCommand(OPERSERV, new CommandOSSZLine(), MOD_UNIQUE); -int szline_view(int number, SXLine * sx, User * u, int *sent_header) + this->SetOperHelp(myOperServHelp); + if (!ircd->szline) + throw ModuleException("Your IRCd does not support ZLINEs"); + } +}; + + +/** + * Add the help response to anopes /os help output. + * @param u The user who is requesting help + **/ +void myOperServHelp(User *u) +{ + if (is_services_oper(u)) + notice_lang(s_OperServ, u, OPER_HELP_CMD_SZLINE); +} + +int szline_view(int number, SXLine *sx, User *u, int *sent_header) { char timebuf[32], expirebuf[256]; struct tm tm; @@ -282,25 +343,22 @@ int szline_view(int number, SXLine * sx, User * u, int *sent_header) if (!sx) return 0; - if (!*sent_header) { + if (!*sent_header) + { notice_lang(s_OperServ, u, OPER_SZLINE_VIEW_HEADER); *sent_header = 1; } tm = *localtime(&sx->seton); - strftime_lang(timebuf, sizeof(timebuf), u, STRFTIME_SHORT_DATE_FORMAT, - &tm); + strftime_lang(timebuf, sizeof(timebuf), u, STRFTIME_SHORT_DATE_FORMAT, &tm); expire_left(u->na, expirebuf, sizeof(expirebuf), sx->expires); - notice_lang(s_OperServ, u, OPER_SZLINE_VIEW_FORMAT, number, sx->mask, - sx->by, timebuf, expirebuf, sx->reason); + notice_lang(s_OperServ, u, OPER_SZLINE_VIEW_FORMAT, number, sx->mask, sx->by, timebuf, expirebuf, sx->reason); return 1; } /* Callback for enumeration purposes */ - -int szline_view_callback(SList * slist, int number, void *item, - va_list args) +int szline_view_callback(SList *slist, int number, void *item, va_list args) { User *u = va_arg(args, User *); int *sent_header = va_arg(args, int *); @@ -309,9 +367,7 @@ int szline_view_callback(SList * slist, int number, void *item, } /* Callback for enumeration purposes */ - -int szline_list_callback(SList * slist, int number, void *item, - va_list args) +int szline_list_callback(SList *slist, int number, void *item, va_list args) { User *u = va_arg(args, User *); int *sent_header = va_arg(args, int *); @@ -320,19 +376,18 @@ int szline_list_callback(SList * slist, int number, void *item, } /* Lists an SZLINE entry, prefixing it with the header if needed */ - -int szline_list(int number, SXLine * sx, User * u, int *sent_header) +int szline_list(int number, SXLine *sx, User *u, int *sent_header) { if (!sx) return 0; - if (!*sent_header) { + if (!*sent_header) + { notice_lang(s_OperServ, u, OPER_SZLINE_LIST_HEADER); *sent_header = 1; } - notice_lang(s_OperServ, u, OPER_SZLINE_LIST_FORMAT, number, sx->mask, - sx->reason); + notice_lang(s_OperServ, u, OPER_SZLINE_LIST_FORMAT, number, sx->mask, sx->reason); return 1; } diff --git a/src/core/os_umode.c b/src/core/os_umode.c index f8637c4d0..ade20bcea 100644 --- a/src/core/os_umode.c +++ b/src/core/os_umode.c @@ -15,22 +15,80 @@ #include "module.h" -int do_operumodes(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSUMode : public Command +{ + public: + CommandOSUMode() : Command("UMODE", 2, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[0].c_str(); + const char *modes = params[1].c_str(); + + User *u2; + + /* Only allow this if SuperAdmin is enabled */ + if (!u->isSuperAdmin) + { + notice_lang(s_OperServ, u, OPER_SUPER_ADMIN_ONLY); + return MOD_CONT; + } + + /** + * Only accept a +/- mode string + *-rob + **/ + if (modes[0] != '+' && modes[0] != '-') + { + this->OnSyntaxError(u); + return MOD_CONT; + } + if (!(u2 = finduser(nick))) + notice_lang(s_OperServ, u, NICK_X_NOT_IN_USE, nick); + else + { + ircdproto->SendMode(findbot(s_OperServ), nick, "%s", modes); + + common_svsmode(u2, modes, NULL); + + notice_lang(s_OperServ, u, OPER_UMODE_SUCCESS, nick); + notice_lang(s_OperServ, u2, OPER_UMODE_CHANGED, u->nick); + + if (WallOSMode) + ircdproto->SendGlobops(s_OperServ, "\2%s\2 used UMODE on %s", u->nick, nick); + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_root(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_UMODE); + return true; + } + + void OnSyntaxError(User *u) + { + syntax_error(s_OperServ, u, "UMODE", OPER_UMODE_SYNTAX); + } +}; class OSUMode : public Module { public: OSUMode(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("UMODE", do_operumodes, is_services_root, OPER_HELP_UMODE, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSUMode(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); @@ -43,62 +101,10 @@ class OSUMode : public Module * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_admin(u) && u->isSuperAdmin) { + if (is_services_admin(u) && u->isSuperAdmin) notice_lang(s_OperServ, u, OPER_HELP_CMD_UMODE); - } -} - -/** - * Change any user's UMODES - * - * modified to be part of the SuperAdmin directive -jester - * check user flag for SuperAdmin -rob - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - */ -int do_operumodes(User * u) -{ - char *nick = strtok(NULL, " "); - char *modes = strtok(NULL, ""); - - User *u2; - - /* Only allow this if SuperAdmin is enabled */ - if (!u->isSuperAdmin) { - notice_lang(s_OperServ, u, OPER_SUPER_ADMIN_ONLY); - return MOD_CONT; - } - - if (!nick || !modes) { - syntax_error(s_OperServ, u, "UMODE", OPER_UMODE_SYNTAX); - return MOD_CONT; - } - - /** - * Only accept a +/- mode string - *-rob - **/ - if ((modes[0] != '+') && (modes[0] != '-')) { - syntax_error(s_OperServ, u, "UMODE", OPER_UMODE_SYNTAX); - return MOD_CONT; - } - if (!(u2 = finduser(nick))) { - notice_lang(s_OperServ, u, NICK_X_NOT_IN_USE, nick); - } else { - ircdproto->SendMode(findbot(s_OperServ), nick, "%s", modes); - - common_svsmode(u2, modes, NULL); - - notice_lang(s_OperServ, u, OPER_UMODE_SUCCESS, nick); - notice_lang(s_OperServ, u2, OPER_UMODE_CHANGED, u->nick); - - if (WallOSMode) - ircdproto->SendGlobops(s_OperServ, "\2%s\2 used UMODE on %s", - u->nick, nick); - } - return MOD_CONT; } MODULE_INIT("os_umode", OSUMode) diff --git a/src/core/os_update.c b/src/core/os_update.c index a637a307d..a85e0c219 100644 --- a/src/core/os_update.c +++ b/src/core/os_update.c @@ -15,22 +15,42 @@ #include "module.h" -int do_update(User * u); -void myOperServHelp(User * u); +void myOperServHelp(User *u); + +class CommandOSUpdate : public Command +{ + public: + CommandOSUpdate() : Command("UPDATE", 0, 0) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + notice_lang(s_OperServ, u, OPER_UPDATING); + save_data = 1; + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_services_root(u)) + return false; + + notice_lang(s_OperServ, u, OPER_HELP_UPDATE); + return true; + } +}; class OSUpdate : public Module { public: OSUpdate(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("UPDATE", do_update, is_services_root, OPER_HELP_UPDATE, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSUpdate(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } @@ -41,23 +61,10 @@ class OSUpdate : public Module * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { - if (is_services_root(u)) { + if (is_services_root(u)) notice_lang(s_OperServ, u, OPER_HELP_CMD_UPDATE); - } -} - -/** - * The /os update command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ -int do_update(User * u) -{ - notice_lang(s_OperServ, u, OPER_UPDATING); - save_data = 1; - return MOD_CONT; } MODULE_INIT("os_update", OSUpdate) diff --git a/src/core/os_userlist.c b/src/core/os_userlist.c index d6c53ae76..a04b8f2e6 100644 --- a/src/core/os_userlist.c +++ b/src/core/os_userlist.c @@ -15,27 +15,85 @@ #include "module.h" -#ifdef _WIN32 -extern MDE int anope_get_invite_mode(); -extern MDE int anope_get_invis_mode(); -#endif +void myOperServHelp(User *u); -int do_userlist(User * u); -void myOperServHelp(User * u); +class CommandOSUserList : public Command +{ + public: + CommandOSUserList() : Command("USERLIST", 0, 2) + { + } + + CommandReturn Execute(User *u, std::vector<std::string> ¶ms) + { + const char *pattern = params.size() > 0 ? params[0].c_str() : NULL; + const char *opt = params.size() > 1 ? params[1].c_str() : NULL; + + Channel *c; + int modes = 0; + + if (opt && !stricmp(opt, "INVISIBLE")) + modes |= anope_get_invis_mode(); + + if (pattern && (c = findchan(pattern))) + { + struct c_userlist *cu; + + notice_lang(s_OperServ, u, OPER_USERLIST_HEADER_CHAN, pattern); + + for (cu = c->users; cu; cu = cu->next) + { + if (modes && !(cu->user->mode & mode)) + continue; + notice_lang(s_OperServ, u, OPER_USERLIST_RECORD, cu->user->nick, cu->user->GetIdent().c_str(), cu->user->GetDisplayedHost().c_str()); + } + } + else + { + char mask[BUFSIZE]; + int i; + User *u2; + + notice_lang(s_OperServ, u, OPER_USERLIST_HEADER); + + for (i = 0; i < 1024; ++i) + { + for (u2 = userlist[i]; u2; u2 = u2->next) + { + if (pattern) + { + snprintf(mask, sizeof(mask), "%s!%s@%s", u2->nick, u2->GetIdent().c_str(), u2->GetDisplayedHost().c_str()); + if (!match_wild_nocase(pattern, mask)) + continue; + if (modes && !(u2->mode & modes)) + continue; + } + notice_lang(s_OperServ, u, OPER_USERLIST_RECORD, u2->nick, u2->GetIdent().c_str(), u2->GetDisplayedHost().c_str()); + } + } + } + + notice_lang(s_OperServ, u, OPER_USERLIST_END); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + notice_lang(s_OperServ, u, OPER_HELP_USERLIST); + return true; + } +}; class OSUserList : public Module { public: OSUserList(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); - c = createCommand("USERLIST", do_userlist, NULL, OPER_HELP_USERLIST, -1, -1, -1, -1); - this->AddCommand(OPERSERV, c, MOD_UNIQUE); + this->AddCommand(OPERSERV, new CommandOSUserList(), MOD_UNIQUE); this->SetOperHelp(myOperServHelp); } @@ -46,65 +104,9 @@ class OSUserList : public Module * Add the help response to anopes /os help output. * @param u The user who is requesting help **/ -void myOperServHelp(User * u) +void myOperServHelp(User *u) { notice_lang(s_OperServ, u, OPER_HELP_CMD_USERLIST); } -/** - * The /os userlist command. - * @param u The user who issued the command - * @param MOD_CONT to continue processing other modules, MOD_STOP to stop processing. - **/ - -int do_userlist(User * u) -{ - char *pattern = strtok(NULL, " "); - char *opt = strtok(NULL, " "); - - Channel *c; - int modes = 0; - - if (opt && !stricmp(opt, "INVISIBLE")) - modes |= anope_get_invis_mode(); - - if (pattern && (c = findchan(pattern))) { - struct c_userlist *cu; - - notice_lang(s_OperServ, u, OPER_USERLIST_HEADER_CHAN, pattern); - - for (cu = c->users; cu; cu = cu->next) { - if (modes && !(cu->user->mode & modes)) - continue; - notice_lang(s_OperServ, u, OPER_USERLIST_RECORD, - cu->user->nick, common_get_vident(cu->user), - common_get_vhost(cu->user)); - } - } else { - char mask[BUFSIZE]; - int i; - User *u2; - - notice_lang(s_OperServ, u, OPER_USERLIST_HEADER); - - for (i = 0; i < 1024; i++) { - for (u2 = userlist[i]; u2; u2 = u2->next) { - if (pattern) { - snprintf(mask, sizeof(mask), "%s!%s@%s", u2->nick, - common_get_vident(u2), common_get_vhost(u2)); - if (!match_wild_nocase(pattern, mask)) - continue; - if (modes && !(u2->mode & modes)) - continue; - } - notice_lang(s_OperServ, u, OPER_USERLIST_RECORD, u2->nick, - common_get_vident(u2), common_get_vhost(u2)); - } - } - } - - notice_lang(s_OperServ, u, OPER_USERLIST_END); - return MOD_CONT; -} - MODULE_INIT("os_userlist", OSUserList) diff --git a/src/core/ss_main.c b/src/core/ss_main.c index 988133009..d2f2b01ea 100644 --- a/src/core/ss_main.c +++ b/src/core/ss_main.c @@ -18,27 +18,36 @@ BotInfo *statserv = NULL; CommandHash *cmdTable[MAX_CMD_HASH]; int statserv_create(int argc, char **argv); -int do_help(User *u); + +class CommandSSHelp : public Command +{ + public: + CommandSSHelp() : Command("HELP", 0, 0) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + ircdproto->SendMessage(statserv, u->nick, "This is a test of the emergency StatServ system."); + return MOD_CONT; + } +}; class SSMain : public Module { public: SSMain(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - this->SetAuthor("Anope"); this->SetVersion("$Id$"); this->SetType(CORE); this->SetPermanent(true); - c = createCommand("HELP", do_help, NULL, -1, -1, -1, -1, -1); - this->AddCommand(cmdTable, c, MOD_HEAD); + this->AddCommand(cmdTable, new CommandSSHelp(), MOD_HEAD); - if (servsock == -1) { - EvtHook *hook; - - hook = createEventHook(EVENT_SERVER_CONNECT, statserv_create); + if (servsock == -1) + { + EvtHook *hook = createEventHook(EVENT_SERVER_CONNECT, statserv_create); this->AddEventHook(hook); } else @@ -48,13 +57,16 @@ class SSMain : public Module { CommandHash *current; Command *c; - for (int i = 0; i < MAX_CMD_HASH; i++) { - for (current = cmdTable[i]; current; current = current->next) { + for (int i = 0; i < MAX_CMD_HASH; ++i) + { + for (current = cmdTable[i]; current; current = current->next) + { for (c = current->c; c; c = c->next) this->DelCommand(cmdTable, c->name); } } - if (statserv) { + if (statserv) + { ircdproto->SendQuit(statserv, "Quit due to module unload."); delete statserv; } @@ -64,7 +76,8 @@ class SSMain : public Module int statserv_create(int argc, char **argv) { statserv = findbot("StatServ"); - if (!statserv) { + if (!statserv) + { statserv = new BotInfo("StatServ", ServiceUser, ServiceHost, "Stats Service"); ircdproto->SendClientIntroduction("StatServ", ServiceUser, ServiceHost, "Stats Service", ircd->pseudoclient_mode, statserv->uid.c_str()); } @@ -72,10 +85,4 @@ int statserv_create(int argc, char **argv) return MOD_CONT; } -int do_help(User *u) -{ - ircdproto->SendMessage(statserv, u->nick, "This is a test of the emergency StatServ system."); - return MOD_CONT; -} - MODULE_INIT("ss_main", SSMain) diff --git a/src/hostserv.c b/src/hostserv.c index 314e8f4e2..07bf7c976 100644 --- a/src/hostserv.c +++ b/src/hostserv.c @@ -506,7 +506,7 @@ int do_on_id(User * u) } if (ircd->vident) { if (vIdent) - u->vident = sstrdup(vIdent); + u->SetVIdent(vIdent); } set_lastmask(u); } @@ -552,8 +552,7 @@ void set_lastmask(User * u) if (u->na->last_usermask) delete [] u->na->last_usermask; - u->na->last_usermask = new char[strlen(common_get_vident(u)) + strlen(common_get_vhost(u)) + 2]; - sprintf(u->na->last_usermask, "%s@%s", common_get_vident(u), - common_get_vhost(u)); + u->na->last_usermask = new char[u->GetIdent().length() + u->GetDisplayedHost().length() + 2]; + sprintf(u->na->last_usermask, "%s@%s", u->GetIdent().c_str(), u->GetDisplayedHost().c_str()); } diff --git a/src/init.c b/src/init.c index 52bb26558..9b062d85b 100644 --- a/src/init.c +++ b/src/init.c @@ -477,54 +477,9 @@ int init_secondary(int ac, char **av) /* Set signal handlers. Catch certain signals to let us do things or * panic as necessary, and ignore all others. */ - -#ifndef _WIN32 -#if defined(NSIG) - for (i = 1; i <= NSIG - 1; i++) { -#else - for (i = 1; i <= 31; i++) { -#endif - signal(i, SIG_IGN); - } -#else - /* work around to bug #527 */ - signal(SIGILL, SIG_IGN); - signal(SIGBREAK, SIG_IGN); - signal(SIGABRT, SIG_IGN); -#endif - - signal(SIGINT, sighandler); - signal(SIGTERM, sighandler); -#ifndef _WIN32 - signal(SIGQUIT, sighandler); -#endif - if (!DumpCore) { - signal(SIGSEGV, sighandler); -#ifndef _WIN32 - signal(SIGBUS, sighandler); - signal(SIGTRAP, sighandler); -#endif - } else { - signal(SIGSEGV, SIG_DFL); -#ifndef _WIN32 - signal(SIGBUS, sighandler); - signal(SIGTRAP, sighandler); -#endif - } -#ifndef _WIN32 - signal(SIGQUIT, sighandler); signal(SIGHUP, sighandler); - signal(SIGUSR2, sighandler); -#endif - -#ifdef SIGIOT - signal(SIGIOT, sighandler); -#endif - signal(SIGFPE, sighandler); - -#ifndef _WIN32 - signal(SIGUSR1, sighandler); /* This is our "out-of-memory" panic switch */ -#endif + signal(SIGTERM, sighandler); + signal(SIGINT, sighandler)' /* Initialize multi-language support */ lang_init(); diff --git a/src/main.c b/src/main.c index d83ad4e1b..6e1f6f655 100644 --- a/src/main.c +++ b/src/main.c @@ -88,9 +88,6 @@ extern char *mod_current_buffer; /******** Local variables! ********/ -/* Set to 1 if we are waiting for input */ -static int waiting = 0; - /* Set to 1 after we've set everything up */ static int started = 0; @@ -106,34 +103,23 @@ extern void expire_all() return; } - waiting = -30; send_event(EVENT_DB_EXPIRE, 1, EVENT_START); - waiting = -3; if (debug) alog("debug: Running expire routines"); - waiting = -21; expire_nicks(); - waiting = -22; expire_chans(); - waiting = -23; expire_requests(); - waiting = -25; expire_akills(); if (ircd->sgline) { - waiting = -26; expire_sglines(); } if (ircd->sqline) { - waiting = -28; expire_sqlines(); } if (ircd->szline) { - waiting = -27; expire_szlines(); } - waiting = -29; expire_exceptions(); - waiting = -31; send_event(EVENT_DB_EXPIRE, 1, EVENT_STOP); } @@ -141,36 +127,24 @@ extern void expire_all() void save_databases() { - waiting = -19; send_event(EVENT_DB_SAVING, 1, EVENT_START); - waiting = -2; if (debug) alog("debug: Saving FFF databases"); - waiting = -10; backup_databases(); - waiting = -11; save_ns_dbase(); - waiting = -12; if (PreNickDBName) { save_ns_req_dbase(); - waiting = -13; } save_cs_dbase(); if (s_BotServ) { - waiting = -14; save_bs_dbase(); } if (s_HostServ) { - waiting = -15; save_hs_dbase(); } - waiting = -16; save_os_dbase(); - waiting = -17; save_news(); - waiting = -18; save_exceptions(); - waiting = -20; send_event(EVENT_DB_SAVING, 1, EVENT_STOP); } @@ -262,46 +236,31 @@ void sighandler(int signum) * always set when we need it. It seems some signals slip through to the * QUIT code without having a valid quitmsg. -GD */ - quitmsg = sstrdup("Signal Received"); - if (started) { -#ifndef _WIN32 - if (signum == SIGHUP) { /* SIGHUP = save databases and restart */ - signal(SIGHUP, SIG_IGN); - signal(SIGUSR2, SIG_IGN); - alog("Received SIGHUP, restarting."); - - expire_all(); - save_databases(); - - if (!quitmsg) - quitmsg = "Restarting on SIGHUP"; - -#ifdef SERVICES_BIN - services_restart(); - exit(1); -#else - quitmsg = - "Restart attempt failed--SERVICES_BIN not defined (rerun configure)"; -#endif - } else if (signum == SIGQUIT) { - /* had to move it to here to make win32 happy */ - } else if (signum == SIGUSR2) { + snprintf(const_cast<char *>(quitmsg), BUFSIZE, "Services terminating on signal %d", signum); - alog("Received SIGUSR2: Saving Databases & Rehash Configuration"); + if (started) + { +#ifndef _WIN32 + if (signum == SIGHUP) + { + alog("Received SIGHUP: Saving Databases & Rehash Configuration"); expire_all(); save_databases(); - if (!read_config(1)) { - quitmsg = "Error Reading Configuration File (Received SIGUSR2)"; + if (!read_config(1)) + { + quitmsg = "Error Reading Configuration File (Received SIGHUP)"; quitting = 1; } + send_event(EVENT_RELOAD, 1, EVENT_START); return; } else #endif - if (signum == SIGTERM) { + if (signum == SIGTERM) + { signal(SIGTERM, SIG_IGN); #ifndef _WIN32 signal(SIGHUP, SIG_IGN); @@ -314,8 +273,11 @@ void sighandler(int signum) quitmsg = "Shutting down on SIGTERM"; services_shutdown(); exit(0); - } else if (signum == SIGINT) { - if (nofork) { + } + else if (signum == SIGINT) + { + if (nofork) + { signal(SIGINT, SIG_IGN); alog("Received SIGINT, exiting."); expire_all(); @@ -324,122 +286,29 @@ void sighandler(int signum) services_shutdown(); exit(0); } - } else if (!waiting) { - alog("PANIC! buffer = %s", inbuf); - /* Cut off if this would make IRC command >510 characters. */ - if (strlen(inbuf) > 448) { - inbuf[446] = '>'; - inbuf[447] = '>'; - inbuf[448] = 0; - } - ircdproto->SendGlobops(NULL, "PANIC! buffer = %s\r\n", inbuf); - modules_unload_all(false, true); - } else if (waiting < 0) { - /* This is static on the off-chance we run low on stack */ - static char buf[BUFSIZE]; - switch (waiting) { - case -1: - snprintf(buf, sizeof(buf), "in timed_update"); - break; - case -10: - snprintf(buf, sizeof(buf), "backing up databases"); - break; - case -11: - snprintf(buf, sizeof(buf), "saving %s", NickDBName); - break; - case -12: - snprintf(buf, sizeof(buf), "saving %s", ChanDBName); - break; - case -13: - snprintf(buf, sizeof(buf), "saving %s", PreNickDBName); - break; - case -14: - snprintf(buf, sizeof(buf), "saving %s", BotDBName); - break; - case -15: - snprintf(buf, sizeof(buf), "saving %s", HostDBName); - break; - case -16: - snprintf(buf, sizeof(buf), "saving %s", OperDBName); - break; - case -17: - snprintf(buf, sizeof(buf), "saving %s", NewsDBName); - break; - case -18: - snprintf(buf, sizeof(buf), "saving %s", ExceptionDBName); - break; - case -19: - snprintf(buf, sizeof(buf), "Sending event %s %s", - EVENT_DB_SAVING, EVENT_START); - break; - case -20: - snprintf(buf, sizeof(buf), "Sending event %s %s", - EVENT_DB_SAVING, EVENT_STOP); - break; - case -21: - snprintf(buf, sizeof(buf), "expiring nicknames"); - break; - case -22: - snprintf(buf, sizeof(buf), "expiring channels"); - break; - case -25: - snprintf(buf, sizeof(buf), "expiring autokills"); - break; - case -26: - snprintf(buf, sizeof(buf), "expiring SGLINEs"); - break; - case -27: - snprintf(buf, sizeof(buf), "expiring SZLINEs"); - break; - case -28: - snprintf(buf, sizeof(buf), "expiring SQLINEs"); - break; - case -29: - snprintf(buf, sizeof(buf), "expiring Exceptions"); - break; - case -30: - snprintf(buf, sizeof(buf), "Sending event %s %s", - EVENT_DB_EXPIRE, EVENT_START); - break; - case -31: - snprintf(buf, sizeof(buf), "Sending event %s %s", - EVENT_DB_EXPIRE, EVENT_STOP); - break; - default: - snprintf(buf, sizeof(buf), "waiting=%d", waiting); - } - ircdproto->SendGlobops(NULL, "PANIC! %s (caught signal %d)", buf, signum); - alog("PANIC! %s (caught signal %d)", buf, signum); - modules_unload_all(false, true); } } - if ( -#ifndef _WIN32 - signum == SIGUSR1 || -#endif - !(quitmsg = new char[BUFSIZE])) { - quitmsg = "Out of memory!"; - } else { - snprintf(const_cast<char *>(quitmsg), BUFSIZE, "Services terminating on signal %d", signum); - } - if (signum == SIGSEGV) { - do_backtrace(1); - modules_unload_all(false, true); /* probably cant do this, but might as well try, we have nothing left to loose */ - } /* Should we send the signum here as well? -GD */ send_event(EVENT_SIGNAL, 1, quitmsg); - if (started) { + if (started) + { services_shutdown(); exit(0); - } else { - if (isatty(2)) { + } + else + { + if (isatty(2)) + { fprintf(stderr, "%s\n", quitmsg); - } else { + } + else + { alog("%s", quitmsg); } + exit(1); } } @@ -642,38 +511,3 @@ int main(int ac, char **av, char **envp) return 0; } -/*************************************************************************/ - -void do_backtrace(int show_segheader) -{ -#ifndef _WIN32 -#ifdef HAVE_BACKTRACE - void *array[50]; - size_t size; - char **strings; - int i; - - if (show_segheader) { - alog("Backtrace: Segmentation fault detected"); - alog("Backtrace: report the following lines"); - } - alog("Backtrace: Anope version %s %s %s", version_number, - version_build, version_flags); - size = backtrace(array, 10); - strings = backtrace_symbols(array, size); - for (i = 0; i < size; i++) { - alog("Backtrace(%d): %s", i, strings[i]); - } - free(strings); - alog("Backtrace: complete"); -#else - alog("Backtrace: not available on this platform"); -#endif -#else - char *winver; - winver = GetWindowsVersion(); - alog("Backtrace: not available on Windows"); - alog("Running %s", winver); - delete [] winver; -#endif -} diff --git a/src/memory.c b/src/memory.c index 67cf167a1..804961f95 100644 --- a/src/memory.c +++ b/src/memory.c @@ -37,11 +37,7 @@ void *smalloc(long size) } buf = malloc(size); if (!buf) -#ifndef _WIN32 - raise(SIGUSR1); -#else abort(); -#endif return buf; } @@ -62,11 +58,7 @@ void *scalloc(long elsize, long els) } buf = calloc(elsize, els); if (!buf) -#ifndef _WIN32 - raise(SIGUSR1); -#else abort(); -#endif return buf; } @@ -87,11 +79,7 @@ void *srealloc(void *oldptr, long newsize) } buf = realloc(oldptr, newsize); if (!buf) -#ifndef _WIN32 - raise(SIGUSR1); -#else abort(); -#endif return buf; } @@ -109,11 +97,7 @@ char *sstrdup(const char *src) if (src) { ret = new char[strlen(src) + 1]; if (!ret) -#ifndef _WIN32 - raise(SIGUSR1); -#else abort(); -#endif strcpy(ret, src); } else { alog("sstrdup() called with NULL-arg"); diff --git a/src/messages.c b/src/messages.c index 44c8a8d5c..55b4fa283 100644 --- a/src/messages.c +++ b/src/messages.c @@ -169,7 +169,7 @@ int m_privmsg(const char *source, const char *receiver, const char *msg) if (WallBadOS) ircdproto->SendGlobops(s_OperServ, "Denied access to %s from %s!%s@%s (non-oper)", - s_OperServ, u->nick, u->username, + s_OperServ, u->nick, u->GetIdent().c_str(), u->host); } else { operserv(u, const_cast<char *>(msg)); // XXX Unsafe cast, this needs reviewing -- CyberBotX diff --git a/src/misc.c b/src/misc.c index 6f9ec7e80..0c8d8d650 100644 --- a/src/misc.c +++ b/src/misc.c @@ -835,7 +835,7 @@ void EnforceQlinedNick(const char *nick, const char *killer) User *u2; if ((u2 = finduser(nick))) { - alog("Killed Q-lined nick: %s!%s@%s", u2->nick, u2->username, + alog("Killed Q-lined nick: %s!%s@%s", u2->nick, u2->GetIdent().c_str(), u2->host); kill_user(killer, u2->nick, "This nick is reserved for Services. Please use a non Q-Lined nick."); diff --git a/src/module.cpp b/src/module.cpp index 1f61b2b54..cfec523b3 100644 --- a/src/module.cpp +++ b/src/module.cpp @@ -86,7 +86,7 @@ Module::~Module() for (current = HS_cmdTable[idx]; current; current = current->next) { for (c = current->c; c; c = c->next) { if ((c->mod_name) && (strcmp(c->mod_name, this->name.c_str()) == 0)) { - this->DelCommand(HOSTSERV, c->name); + this->DelCommand(HOSTSERV, c->name.c_str()); } } } @@ -94,7 +94,7 @@ Module::~Module() for (current = BS_cmdTable[idx]; current; current = current->next) { for (c = current->c; c; c = c->next) { if ((c->mod_name) && (strcmp(c->mod_name, this->name.c_str()) == 0)) { - this->DelCommand(BOTSERV, c->name); + this->DelCommand(BOTSERV, c->name.c_str()); } } } @@ -102,7 +102,7 @@ Module::~Module() for (current = MS_cmdTable[idx]; current; current = current->next) { for (c = current->c; c; c = c->next) { if ((c->mod_name) && (strcmp(c->mod_name, this->name.c_str()) == 0)) { - this->DelCommand(MEMOSERV, c->name); + this->DelCommand(MEMOSERV, c->name.c_str()); } } } @@ -110,7 +110,7 @@ Module::~Module() for (current = NS_cmdTable[idx]; current; current = current->next) { for (c = current->c; c; c = c->next) { if ((c->mod_name) && (strcmp(c->mod_name, this->name.c_str()) == 0)) { - this->DelCommand(NICKSERV, c->name); + this->DelCommand(NICKSERV, c->name.c_str()); } } } @@ -118,7 +118,7 @@ Module::~Module() for (current = CS_cmdTable[idx]; current; current = current->next) { for (c = current->c; c; c = c->next) { if ((c->mod_name) && (strcmp(c->mod_name, this->name.c_str()) == 0)) { - this->DelCommand(CHANSERV, c->name); + this->DelCommand(CHANSERV, c->name.c_str()); } } } @@ -126,7 +126,7 @@ Module::~Module() for (current = HE_cmdTable[idx]; current; current = current->next) { for (c = current->c; c; c = c->next) { if ((c->mod_name) && (strcmp(c->mod_name, this->name.c_str()) == 0)) { - this->DelCommand(HELPSERV, c->name); + this->DelCommand(HELPSERV, c->name.c_str()); } } } @@ -134,7 +134,7 @@ Module::~Module() for (current = OS_cmdTable[idx]; current; current = current->next) { for (c = current->c; c; c = c->next) { if ((c->mod_name) && (stricmp(c->mod_name, this->name.c_str()) == 0)) { - this->DelCommand(OPERSERV, c->name); + this->DelCommand(OPERSERV, c->name.c_str()); } } } diff --git a/src/modulemanager.cpp b/src/modulemanager.cpp index 6a995f41f..5354e4755 100644 --- a/src/modulemanager.cpp +++ b/src/modulemanager.cpp @@ -170,19 +170,19 @@ int ModuleManager::LoadModule(const std::string &modname, User * u) ano_modclearerr(); - ano_module_t handle = ano_modopen(pbuf.c_str()); - if (handle == NULL && (err = ano_moderr()) != NULL) + ano_module_t handle = dlopen(pbuf.c_str(), RTLD_LAZY); + if (handle == NULL && (err = dlerror()) != NULL) { alog("%s", err); return MOD_ERR_NOLOAD; } ano_modclearerr(); - func = function_cast<Module *(*)(const std::string &)>(ano_modsym(handle, "init_module")); - if (func == NULL && (err = ano_moderr()) != NULL) + func = function_cast<Module *(*)(const std::string &)>(dlsym(handle, "init_module")); + if (func == NULL && (err = dlerror()) != NULL) { alog("No magical init function found, not an Anope module"); - ano_modclose(handle); + dlclose(handle); return MOD_ERR_NOLOAD; } @@ -275,8 +275,8 @@ void ModuleManager::DeleteModule(Module *m) handle = m->handle; ano_modclearerr(); - destroy_func = function_cast<void (*)(Module *)>(ano_modsym(m->handle, "destroy_module")); - if (destroy_func == NULL && (err = ano_moderr()) != NULL) + destroy_func = function_cast<void (*)(Module *)>(dlsym(m->handle, "destroy_module")); + if (destroy_func == NULL && (err = dlerror()) != NULL) { alog("No magical destroy function found, chancing delete..."); delete m; /* we just have to chance they haven't overwrote the delete operator then... */ @@ -288,7 +288,7 @@ void ModuleManager::DeleteModule(Module *m) if (handle) { - if ((ano_modclose(handle)) != 0) - alog("%s", ano_moderr()); + if ((dlclose(handle)) != 0) + alog("%s", dlerror()); } } diff --git a/src/modules.c b/src/modules.c index 18e5b5d24..6ea04120b 100644 --- a/src/modules.c +++ b/src/modules.c @@ -182,88 +182,6 @@ Module *findModule(const char *name) /******************************************************************************* * Command Functions *******************************************************************************/ -/** - * Create a Command struct ready for use in anope. - * @param name the name of the command - * @param func pointer to the function to execute when command is given - * @param has_priv pointer to function to check user priv's - * @param help_all help file index for all users - * @param help_reg help file index for all regustered users - * @param help_oper help file index for all opers - * @param help_admin help file index for all admins - * @param help_root help file indenx for all services roots - * @return a "ready to use" Command struct will be returned - */ -Command *createCommand(const char *name, int (*func) (User * u), - int (*has_priv) (User * u), int help_all, - int help_reg, int help_oper, int help_admin, - int help_root) -{ - Command *c; - if (!name || !*name) { - return NULL; - } - - if (!(c = new Command)) { - fatal("Out of memory!"); - } - c->name = sstrdup(name); - c->routine = func; - c->has_priv = has_priv; - c->helpmsg_all = help_all; - c->helpmsg_reg = help_reg; - c->helpmsg_oper = help_oper; - c->helpmsg_admin = help_admin; - c->helpmsg_root = help_root; - c->help_param1 = NULL; - c->help_param2 = NULL; - c->help_param3 = NULL; - c->help_param4 = NULL; - c->core = 0; - c->next = NULL; - c->mod_name = NULL; - c->service = NULL; - c->all_help = NULL; - c->regular_help = NULL; - c->oper_help = NULL; - c->admin_help = NULL; - c->root_help = NULL; - return c; -} - -/** - * Destroy a command struct freeing any memory. - * @param c Command to destroy - * @return MOD_ERR_OK on success, anything else on fail - */ -int destroyCommand(Command * c) -{ - if (!c) { - return MOD_ERR_PARAMS; - } - if (c->core == 1) { - return MOD_ERR_UNKNOWN; - } - if (c->name) { - delete [] c->name; - } - c->routine = NULL; - c->has_priv = NULL; - c->helpmsg_all = -1; - c->helpmsg_reg = -1; - c->helpmsg_oper = -1; - c->helpmsg_admin = -1; - c->helpmsg_root = -1; - if (c->mod_name) { - delete [] c->mod_name; - } - if (c->service) { - delete [] c->service; - } - c->next = NULL; - delete c; - return MOD_ERR_OK; -} /** Add a command to a command table. Only for internal use. * only add if were unique, pos = 0; @@ -294,7 +212,7 @@ static int internal_addCommand(Module *m, CommandHash * cmdTable[], Command * c, && (!strcmp(c->service, current->c->service) == 0)) { continue; } - if ((stricmp(c->name, current->name) == 0)) { /* the cmd exist's we are a addHead */ + if ((stricmp(c->name.c_str(), current->name) == 0)) { /* the cmd exist's we are a addHead */ if (pos == 1) { c->next = current->c; current->c = c; @@ -324,7 +242,7 @@ static int internal_addCommand(Module *m, CommandHash * cmdTable[], Command * c, fatal("Out of memory"); } newHash->next = NULL; - newHash->name = sstrdup(c->name); + newHash->name = sstrdup(c->name.c_str()); newHash->c = c; if (lastHash == NULL) @@ -421,7 +339,7 @@ static int internal_delCommand(CommandHash * cmdTable[], Command * c, const char index = CMD_HASH(c->name); for (current = cmdTable[index]; current; current = current->next) { - if (stricmp(c->name, current->name) == 0) { + if (stricmp(c->name.c_str(), current->name) == 0) { if (!lastHash) { tail = current->c; if (tail->next) { @@ -1094,20 +1012,6 @@ bool moduleMinVersion(int major, int minor, int patch, int build) return ret; } -#ifdef _WIN32 -const char *ano_moderr() -{ - static char errbuf[513]; - DWORD err = GetLastError(); - if (err == 0) - return NULL; - FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM | - FORMAT_MESSAGE_IGNORE_INSERTS, NULL, err, 0, errbuf, 512, - NULL); - return errbuf; -} -#endif - /** * Allow ircd protocol files to update the protect level info tables. **/ diff --git a/src/modules/cs_appendtopic.c b/src/modules/cs_appendtopic.c index b84fb0e3e..6aac5a1e1 100644 --- a/src/modules/cs_appendtopic.c +++ b/src/modules/cs_appendtopic.c @@ -48,102 +48,176 @@ #define LNG_CHAN_HELP_APPENDTOPIC 1 #define LNG_APPENDTOPIC_SYNTAX 2 -int my_cs_appendtopic(User * u); -void my_cs_help(User * u); -int my_cs_help_appendtopic(User * u); -void my_add_languages(); +void my_cs_help(User *u); static Module *me; +class CommandCSAppendTopic : public Command +{ + public: + CommandCSAppendTopic() : Command("APPENDTOPIC", 2, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + const char *newtopic = params[1].c_str(); + char topic[1024]; + Channel *c; + ChannelInfo *ci; + + if (!(c = findchan(chan))) + notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); + else if (!(ci = c->ci)) + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, c->name); + else if (ci->flags & CI_VERBOTEN) + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, ci->name); + else if (!is_services_admin(u) && !check_access(u, ci, CA_TOPIC)) + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + else + { + if (ci->last_topic) + { + snprintf(topic, sizeof(topic), "%s %s", ci->last_topic, newtopic); + delete [] ci->last_topic; + } + else + strscpy(topic, newtopic, sizeof(topic)); + + ci->last_topic = *topic ? sstrdup(topic) : NULL; + strscpy(ci->last_topic_setter, u->nick, NICKMAX); + ci->last_topic_time = time(NULL); + + if (c->topic) + delete [] c->topic; + c->topic = *topic ? sstrdup(topic) : NULL; + strscpy(c->topic_setter, u->nick, NICKMAX); + if (ircd->topictsbackward) + c->topic_time = c->topic_time - 1; + else + c->topic_time = ci->last_topic_time; + + if (is_services_admin(u) && !check_access(u, ci, CA_TOPIC)) + alog("%s: %s!%s@%s changed topic of %s as services admin.", s_ChanServ, u->nick, u->GetIdent().c_str(), u->host, c->name); + if (ircd->join2set) + { + if (whosends(ci) == findbot(s_ChanServ)) + { + ircdproto->SendJoin(findbot(s_ChanServ), c->name, c->creation_time); + ircdproto->SendMode(NULL, c->name, "+o %s", s_ChanServ); + } + } + ircdproto->SendTopic(whosends(ci), c->name, u->nick, topic, c->topic_time); + if (ircd->join2set) + { + if (whosends(ci) == findbot(s_ChanServ)) + ircdproto->SendPart(findbot(s_ChanServ), c->name, NULL); + } + } + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + me->NoticeLang(s_ChanServ, u, LNG_APPENDTOPIC_SYNTAX); + ircdproto->SendMessage(findbot(s_ChanServ), u->nick, " "); + me->NoticeLang(s_ChanServ, u, LNG_CHAN_HELP_APPENDTOPIC); + + return true; + } + + void OnSyntaxError(User *u) + { + me->NoticeLang(s_ChanServ, u, LNG_APPENDTOPIC_SYNTAX); + } +}; + class CSAppendTopic : public Module { public: CSAppendTopic(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - me = this; this->SetAuthor(AUTHOR); this->SetVersion(VERSION); this->SetType(SUPPORTED); - c = createCommand("APPENDTOPIC", my_cs_appendtopic, NULL, -1, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_HEAD); - moduleAddHelp(c, my_cs_help_appendtopic); + this->AddCommand(CHANSERV, new CommandCSAppendTopic(), MOD_HEAD); this->SetChanHelp(my_cs_help); /* English (US) */ const char* langtable_en_us[] = { - /* LNG_CHAN_HELP */ - " APPENDTOPIC Add text to a channels topic", - /* LNG_CHAN_HELP_APPENDTOPIC */ - "This command allows users to append text to a currently set\n" - "channel topic. When TOPICLOCK is on, the topic is updated and\n" - "the new, updated topic is locked.", - /* LNG_APPENDTOPIC_SYNTAX */ - "Syntax: APPENDTOPIC channel text\n" + /* LNG_CHAN_HELP */ + " APPENDTOPIC Add text to a channels topic", + /* LNG_CHAN_HELP_APPENDTOPIC */ + "This command allows users to append text to a currently set\n" + "channel topic. When TOPICLOCK is on, the topic is updated and\n" + "the new, updated topic is locked.", + /* LNG_APPENDTOPIC_SYNTAX */ + "Syntax: APPENDTOPIC channel text\n" }; /* Dutch (NL) */ const char* langtable_nl[] = { - /* LNG_CHAN_HELP */ - " APPENDTOPIC Voeg tekst aan een kanaal onderwerp toe", - /* LNG_CHAN_HELP_APPENDTOPIC */ - "Dit command stelt gebruikers in staat om text toe te voegen\n" - "achter het huidige onderwerp van een kanaal. Als TOPICLOCK aan\n" - "staat, zal het onderwerp worden bijgewerkt en zal het nieuwe,\n" - "bijgewerkte topic worden geforceerd.", - /* LNG_APPENDTOPIC_SYNTAX */ - "Gebruik: APPENDTOPIC kanaal tekst\n" + /* LNG_CHAN_HELP */ + " APPENDTOPIC Voeg tekst aan een kanaal onderwerp toe", + /* LNG_CHAN_HELP_APPENDTOPIC */ + "Dit command stelt gebruikers in staat om text toe te voegen\n" + "achter het huidige onderwerp van een kanaal. Als TOPICLOCK aan\n" + "staat, zal het onderwerp worden bijgewerkt en zal het nieuwe,\n" + "bijgewerkte topic worden geforceerd.", + /* LNG_APPENDTOPIC_SYNTAX */ + "Gebruik: APPENDTOPIC kanaal tekst\n" }; /* German (DE) */ const char* langtable_de[] = { - /* LNG_CHAN_HELP */ - " APPENDTOPIC Fügt einen Text zu einem Channel-Topic hinzu.", - /* LNG_CHAN_HELP_APPENDTOPIC */ - "Dieser Befehl erlaubt Benutzern, einen Text zu dem vorhandenen Channel-Topic\n" - "hinzuzufügen. Wenn TOPICLOCK gesetzt ist, wird das Topic aktualisiert\n" - "und das neue, aktualisierte Topic wird gesperrt.", - /* LNG_APPENDTOPIC_SYNTAX */ - "Syntax: APPENDTOPIC Channel Text\n" + /* LNG_CHAN_HELP */ + " APPENDTOPIC Fügt einen Text zu einem Channel-Topic hinzu.", + /* LNG_CHAN_HELP_APPENDTOPIC */ + "Dieser Befehl erlaubt Benutzern, einen Text zu dem vorhandenen Channel-Topic\n" + "hinzuzufügen. Wenn TOPICLOCK gesetzt ist, wird das Topic aktualisiert\n" + "und das neue, aktualisierte Topic wird gesperrt.", + /* LNG_APPENDTOPIC_SYNTAX */ + "Syntax: APPENDTOPIC Channel Text\n" }; /* Portuguese (PT) */ const char* langtable_pt[] = { - /* LNG_CHAN_HELP */ - " APPENDTOPIC Adiciona texto ao tópico de um canal", - /* LNG_CHAN_HELP_APPENDTOPIC */ - "Este comando permite aos usuários anexar texto a um tópico de canal\n" - "já definido. Quando TOPICLOCK está ativado, o tópico é atualizado e\n" - "o novo tópico é travado.", - /* LNG_APPENDTOPIC_SYNTAX */ - "Sintaxe: APPENDTOPIC canal texto\n" + /* LNG_CHAN_HELP */ + " APPENDTOPIC Adiciona texto ao tópico de um canal", + /* LNG_CHAN_HELP_APPENDTOPIC */ + "Este comando permite aos usuários anexar texto a um tópico de canal\n" + "já definido. Quando TOPICLOCK está ativado, o tópico é atualizado e\n" + "o novo tópico é travado.", + /* LNG_APPENDTOPIC_SYNTAX */ + "Sintaxe: APPENDTOPIC canal texto\n" }; /* Russian (RU) */ const char* langtable_ru[] = { - /* LNG_CHAN_HELP */ - " APPENDTOPIC Äîáàâëÿåò òåêñò ê òîïèêó êàíàëà", - /* LNG_CHAN_HELP_APPENDTOPIC */ - "Äàííàÿ êîìàíäà ïîçâîëÿåò äîáàâèòü òåêñò ê òîïèêó, êîòîðûé óñòàíîâëåí íà óêàçàííîì\n" - "êàíàëå. Åñëè àêòèâèðîâàí ðåæèì TOPICLOCK, òîïèê áóäåò îáíîâëåí è çàáëîêèðîâàí.\n" - "Ïðèìå÷àíèå: òåêñò áóäåò ÄÎÁÀÂËÅÍ ê òîïèêó, òî åñòü ñòàðûé òîïèê óäàëåí ÍÅ ÁÓÄÅÒ.\n", - /* LNG_APPENDTOPIC_SYNTAX */ - "Ñèíòàêñèñ: APPENDTOPIC #êàíàë òåêñò\n" + /* LNG_CHAN_HELP */ + " APPENDTOPIC Äîáàâëÿåò òåêñò ê òîïèêó êàíàëà", + /* LNG_CHAN_HELP_APPENDTOPIC */ + "Äàííàÿ êîìàíäà ïîçâîëÿåò äîáàâèòü òåêñò ê òîïèêó, êîòîðûé óñòàíîâëåí íà óêàçàííîì\n" + "êàíàëå. Åñëè àêòèâèðîâàí ðåæèì TOPICLOCK, òîïèê áóäåò îáíîâëåí è çàáëîêèðîâàí.\n" + "Ïðèìå÷àíèå: òåêñò áóäåò ÄÎÁÀÂËÅÍ ê òîïèêó, òî åñòü ñòàðûé òîïèê óäàëåí ÍÅ ÁÓÄÅÒ.\n", + /* LNG_APPENDTOPIC_SYNTAX */ + "Ñèíòàêñèñ: APPENDTOPIC #êàíàë òåêñò\n" }; /* Italian (IT) */ const char* langtable_it[] = { - /* LNG_CHAN_HELP */ - " APPENDTOPIC Aggiunge del testo al topic di un canale", - /* LNG_CHAN_HELP_APPENDTOPIC */ - "Questo comando permette agli utenti di aggiungere del testo ad un topic di un canale\n" - "già impostato. Se TOPICLOCK è attivato, il topic viene aggiornato e il nuovo topic\n" - "viene bloccato.", - /* LNG_APPENDTOPIC_SYNTAX */ - "Sintassi: APPENDTOPIC canale testo\n" + /* LNG_CHAN_HELP */ + " APPENDTOPIC Aggiunge del testo al topic di un canale", + /* LNG_CHAN_HELP_APPENDTOPIC */ + "Questo comando permette agli utenti di aggiungere del testo ad un topic di un canale\n" + "già impostato. Se TOPICLOCK è attivato, il topic viene aggiornato e il nuovo topic\n" + "viene bloccato.", + /* LNG_APPENDTOPIC_SYNTAX */ + "Sintassi: APPENDTOPIC canale testo\n" }; this->InsertLanguage(LANG_EN_US, LNG_NUM_STRINGS, langtable_en_us); @@ -155,83 +229,9 @@ class CSAppendTopic : public Module } }; -void my_cs_help(User * u) +void my_cs_help(User *u) { me->NoticeLang(s_ChanServ, u, LNG_CHAN_HELP); } -int my_cs_help_appendtopic(User * u) -{ - me->NoticeLang(s_ChanServ, u, LNG_APPENDTOPIC_SYNTAX); - ircdproto->SendMessage(findbot(s_ChanServ), u->nick, " "); - me->NoticeLang(s_ChanServ, u, LNG_CHAN_HELP_APPENDTOPIC); - return MOD_STOP; -} - -int my_cs_appendtopic(User * u) -{ - char *cur_buffer; - char *chan; - char *newtopic; - char topic[1024]; - Channel *c; - ChannelInfo *ci; - - cur_buffer = moduleGetLastBuffer(); - chan = myStrGetToken(cur_buffer, ' ', 0); - newtopic = myStrGetTokenRemainder(cur_buffer, ' ', 1); - - if (!chan || !newtopic) { - me->NoticeLang(s_ChanServ, u, LNG_APPENDTOPIC_SYNTAX); - } else if (!(c = findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); - } else if (!(ci = c->ci)) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, c->name); - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, ci->name); - } else if (!is_services_admin(u) && !check_access(u, ci, CA_TOPIC)) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - } else { - if (ci->last_topic) { - snprintf(topic, sizeof(topic), "%s %s", ci->last_topic, - newtopic); - delete [] ci->last_topic; - } else { - strscpy(topic, newtopic, sizeof(topic)); - } - - ci->last_topic = *topic ? sstrdup(topic) : NULL; - strscpy(ci->last_topic_setter, u->nick, NICKMAX); - ci->last_topic_time = time(NULL); - - if (c->topic) - delete [] c->topic; - c->topic = *topic ? sstrdup(topic) : NULL; - strscpy(c->topic_setter, u->nick, NICKMAX); - if (ircd->topictsbackward) - c->topic_time = c->topic_time - 1; - else - c->topic_time = ci->last_topic_time; - - if (is_services_admin(u) && !check_access(u, ci, CA_TOPIC)) - alog("%s: %s!%s@%s changed topic of %s as services admin.", - s_ChanServ, u->nick, u->username, u->host, c->name); - if (ircd->join2set) { - if (whosends(ci) == findbot(s_ChanServ)) { - ircdproto->SendJoin(findbot(s_ChanServ), c->name, c->creation_time); - ircdproto->SendMode(NULL, c->name, "+o %s", s_ChanServ); - } - } - ircdproto->SendTopic(whosends(ci), c->name, u->nick, topic, c->topic_time); - if (ircd->join2set) { - if (whosends(ci) == findbot(s_ChanServ)) { - ircdproto->SendPart(findbot(s_ChanServ), c->name, NULL); - } - } - } - if (newtopic) delete [] newtopic; - if (chan) delete [] chan; - return MOD_CONT; -} - MODULE_INIT("cs_appendtopic", CSAppendTopic) diff --git a/src/modules/cs_enforce.c b/src/modules/cs_enforce.c index b85787311..19ff90b2b 100644 --- a/src/modules/cs_enforce.c +++ b/src/modules/cs_enforce.c @@ -18,10 +18,7 @@ #define AUTHOR "Anope" #define VERSION "$Id$" -int my_cs_enforce(User * u); -void my_cs_help(User * u); -int my_cs_help_enforce(User * u); -void my_add_languages(); +void my_cs_help(User *u); #define LNG_NUM_STRINGS 6 @@ -34,224 +31,430 @@ void my_add_languages(); static Module *me; +class CommandCSEnforce : public Command +{ + private: + void DoSet(Channel *c) + { + ChannelInfo *ci; + + if (!(ci = c->ci)) + return; + + if (ci->flags & CI_SECUREOPS) + this->DoSecureOps(c); + if (ci->flags & CI_RESTRICTED) + this->DoRestricted(c); + } + + void DoModes(Channel *c) + { + CBMode *cbm; + + if ((cbm = &cbmodes[static_cast<int>('R')])->flag && (c->mode & cbm->flag)) + this->DoCModeR(c); + } + + void DoSecureOps(Channel *c) + { + struct c_userlist *user; + struct c_userlist *next; + ChannelInfo *ci; + uint32 flags; + + if (!(ci = c->ci)) + return; + + if (debug) + alog("debug: cs_enforce: Enforcing SECUREOPS on %s", c->name); + + /* Dirty hack to allow chan_set_correct_modes to work ok. + * We pretend like SECUREOPS is on so it doesn't ignore that + * part of the code. This way we can enforce SECUREOPS even + * if it's off. + */ + flags = ci->flags; + ci->flags |= CI_SECUREOPS; + + user = c->users; + do + { + next = user->next; + chan_set_correct_modes(user->user, c, 0); + user = next; + } while (user); + + ci->flags = flags; + } + + void DoRestricted(Channel *c) + { + struct c_userlist *user; + struct c_userlist *next; + ChannelInfo *ci; + int16 old_nojoin_level; + char mask[BUFSIZE]; + char *reason; + const char *av[3]; + User *u; + + if (!(ci = c->ci)) + return; + + if (debug) + alog("debug: cs_enforce: Enforcing RESTRICTED on %s", c->name); + + old_nojoin_level = ci->levels[CA_NOJOIN]; + if (ci->levels[CA_NOJOIN] < 0) + ci->levels[CA_NOJOIN] = 0; + + user = c->users; + do + { + next = user->next; + u = user->user; + if (check_access(u, c->ci, CA_NOJOIN)) + { + get_idealban(ci, u, mask, sizeof(mask)); + reason = getstring(u->na, CHAN_NOT_ALLOWED_TO_JOIN); + ircdproto->SendMode(whosends(ci), ci->name, "+b %s %lu", mask, time(NULL)); + ircdproto->SendKick(whosends(ci), ci->name, u->nick, "%s", reason); + av[0] = ci->name; + av[1] = u->nick; + av[2] = reason; + do_kick(s_ChanServ, 3, av); + } + user = next; + } while (user); + + ci->levels[CA_NOJOIN] = old_nojoin_level; + } + + void DoCModeR(Channel *c) + { + struct c_userlist *user; + struct c_userlist *next; + ChannelInfo *ci; + char mask[BUFSIZE]; + char *reason; + const char *av[3]; + User *u; + CBMode *cbm; + + if (!(ci = c->ci)) + return; + + if (debug) + alog("debug: cs_enforce: Enforcing mode +R on %s", c->name); + + user = c->users; + do + { + next = user->next; + u = user->user; + if (!nick_identified(u)) + { + get_idealban(ci, u, mask, sizeof(mask)); + reason = getstring(u->na, CHAN_NOT_ALLOWED_TO_JOIN); + if (!(cbm = &cbmodes[static_cast<int>('R')])->flag || !(c->mode & cbm->flag)) + ircdproto->SendMode(whosends(ci), ci->name, "+b %s %lu", mask, time(NULL)); + ircdproto->SendKick(whosends(ci), ci->name, u->nick, "%s", reason); + av[0] = ci->name; + av[1] = u->nick; + av[2] = reason; + do_kick(s_ChanServ, 3, av); + } + user = next; + } while (user); + } + public: + CommandCSEnforce() : Command("ENFORCE", 1, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[0].c_str(); + const char *what = params.size() > 1 ? params[1].c_str() : NULL; + Channel *c; + ChannelInfo *ci; + + if (!(c = findchan(chan))) + notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); + else if (!(ci = c->ci)) + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + else if (ci->flags & CI_VERBOTEN) + notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, ci->name); + else if (!is_services_admin(u) && !check_access(u, ci, CA_AKICK)) + notice_lang(s_ChanServ, u, PERMISSION_DENIED); + else + { + if (!what || !stricmp(what, "SET")) + { + this->DoSet(c); + me->NoticeLang(s_ChanServ, u, LNG_CHAN_RESPONSE, what); + } + else if (!stricmp(what, "MODES")) + { + this->DoModes(c); + me->NoticeLang(s_ChanServ, u, LNG_CHAN_RESPONSE, what); + } + else if (!stricmp(what, "SECUREOPS")) + { + this->DoSecureOps(c); + me->NoticeLang(s_ChanServ, u, LNG_CHAN_RESPONSE, what); + } + else if (!stricmp(what, "RESTRICTED")) + { + this->DoRestricted(c); + me->NoticeLang(s_ChanServ, u, LNG_CHAN_RESPONSE, what); + } + else if (!stricmp(what, "+R")) + { + this->DoCModeR(c); + me->NoticeLang(s_ChanServ, u, LNG_CHAN_RESPONSE, what); + } + else + this->OnSyntaxError(u); + } + + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + me->NoticeLang(s_ChanServ, u, LNG_ENFORCE_SYNTAX); + ircdproto->SendMessage(findbot(s_ChanServ), u->nick, " "); + me->NoticeLang(s_ChanServ, u, LNG_CHAN_HELP_ENFORCE); + ircdproto->SendMessage(findbot(s_ChanServ), u->nick, " "); + if (cbmodes[static_cast<int>('R')].flag) + me->NoticeLang(s_ChanServ, u, LNG_CHAN_HELP_ENFORCE_R_ENABLED); + else + me->NoticeLang(s_ChanServ, u, LNG_CHAN_HELP_ENFORCE_R_DISABLED); + + return true; + } + + void OnSyntaxError(User *u) + { + me->NoticeLang(s_ChanServ, u, LNG_ENFORCE_SYNTAX); + } +}; + class CSEnforce : public Module { public: CSEnforce(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - me = this; this->SetAuthor(AUTHOR); this->SetVersion(VERSION); this->SetType(SUPPORTED); - c = createCommand("ENFORCE", my_cs_enforce, NULL, -1, -1, -1, -1, -1); - this->AddCommand(CHANSERV, c, MOD_HEAD); + this->AddCommand(CHANSERV, new CommandCSEnforce(), MOD_HEAD); - moduleAddHelp(c, my_cs_help_enforce); this->SetChanHelp(my_cs_help); /* English (US) */ const char* langtable_en_us[] = { - /* LNG_CHAN_HELP */ - " ENFORCE Enforce various channel modes and set options", - /* LNG_ENFORCE_SYNTAX */ - "Syntax: \002ENFORCE \037channel\037 [\037what\037]\002", - /* LNG_CHAN_HELP_ENFORCE */ - "Enforce various channel modes and set options. The \037channel\037\n" - "option indicates what channel to enforce the modes and options\n" - "on. The \037what\037 option indicates what modes and options to\n" - "enforce, and can be any of SET, SECUREOPS, RESTRICTED, MODES,\n" - "or +R. When left out, it defaults to SET.\n" - " \n" - "If \037what\037 is SET, it will enforce SECUREOPS and RESTRICTED\n" - "on the users currently in the channel, if they are set. Give\n" - "SECUREOPS to enforce the SECUREOPS option, even if it is not\n" - "enabled. Use RESTRICTED to enfore the RESTRICTED option, also\n" - "if it's not enabled.", - /* LNG_CHAN_HELP_ENFORCE_R_ENABLED */ - "If \037what\037 is MODES, it will enforce channelmode +R if it is\n" - "set. If +R is specified for \037what\037, the +R channelmode will\n" - "also be enforced, but even if it is not set. If it is not set,\n" - "users will be banned to ensure they don't just rejoin.", - /* LNG_CHAN_HELP_ENFORCE_R_DISABLED */ - "If \037what\037 is MODES, nothing will be enforced, since it would\n" - "enforce modes that the current ircd does not support. If +R is\n" - "specified for \037what\037, an equalivant of channelmode +R on\n" - "other ircds will be enforced. All users that are in the channel\n" - "but have not identified for their nickname will be kicked and\n" - "banned from the channel.", - /* LNG_CHAN_RESPONSE */ - "Enforced %s" + /* LNG_CHAN_HELP */ + " ENFORCE Enforce various channel modes and set options", + /* LNG_ENFORCE_SYNTAX */ + "Syntax: \002ENFORCE \037channel\037 [\037what\037]\002", + /* LNG_CHAN_HELP_ENFORCE */ + "Enforce various channel modes and set options. The \037channel\037\n" + "option indicates what channel to enforce the modes and options\n" + "on. The \037what\037 option indicates what modes and options to\n" + "enforce, and can be any of SET, SECUREOPS, RESTRICTED, MODES,\n" + "or +R. When left out, it defaults to SET.\n" + " \n" + "If \037what\037 is SET, it will enforce SECUREOPS and RESTRICTED\n" + "on the users currently in the channel, if they are set. Give\n" + "SECUREOPS to enforce the SECUREOPS option, even if it is not\n" + "enabled. Use RESTRICTED to enfore the RESTRICTED option, also\n" + "if it's not enabled.", + /* LNG_CHAN_HELP_ENFORCE_R_ENABLED */ + "If \037what\037 is MODES, it will enforce channelmode +R if it is\n" + "set. If +R is specified for \037what\037, the +R channelmode will\n" + "also be enforced, but even if it is not set. If it is not set,\n" + "users will be banned to ensure they don't just rejoin.", + /* LNG_CHAN_HELP_ENFORCE_R_DISABLED */ + "If \037what\037 is MODES, nothing will be enforced, since it would\n" + "enforce modes that the current ircd does not support. If +R is\n" + "specified for \037what\037, an equalivant of channelmode +R on\n" + "other ircds will be enforced. All users that are in the channel\n" + "but have not identified for their nickname will be kicked and\n" + "banned from the channel.", + /* LNG_CHAN_RESPONSE */ + "Enforced %s" }; /* Dutch (NL) */ const char* langtable_nl[] = { - /* LNG_CHAN_HELP */ - " ENFORCE Forceer enkele kanaalmodes en set-opties", - /* LNG_ENFORCE_SYNTAX */ - "Syntax: \002ENFORCE \037kanaal\037 [\037wat\037]\002", - /* LNG_CHAN_HELP_ENFORCE */ - "Forceer enkele kannalmodes en set-opties. De \037kanaal\037 optie\n" - "geeft aan op welk kanaal de modes en opties geforceerd moeten\n" - "worden. De \037wat\037 optie geeft aan welke modes en opties\n" - "geforceerd moeten worden; dit kan SET, SECUREOPS, RESTRICTED,\n" - "MODES, of +R zijn. Indien weggelaten is dit standaard SET.\n" - " \n" - "Als er voor \037wat\037 SET wordt ingevuld, zullen SECUREOPS en\n" - "RESTRICTED geforceerd worden op de gebruikers in het kanaal,\n" - "maar alleen als die opties aangezet zijn voor het kanaal. Als\n" - "SECUREOPS of RESTRICTED wordt gegeven voor \037wat\037 zal die optie\n" - "altijd geforceerd worden, ook als die niet is aangezet.", - /* LNG_CHAN_HELP_ENFORCE_R_ENABLED */ - "Als er voor \037wat\037 MODES wordt ingevuld, zal kanaalmode +R worden\n" - "geforceerd, als die op het kanaal aan staat. Als +R wordt ingevuld,\n" - "zal kanaalmode +R worden geforceerd, maar ook als die niet aan" - "staat voor het kanaal. Als +R niet aan staat, zullen alle ook\n" - "gebanned worden om te zorgen dat ze niet opnieuw het kanaal binnen\n" - "kunnen komen.", - /* LNG_CHAN_HELP_ENFORCE_R_DISABLED */ - "Als er voor \037wat\037 MODES wordt ingevuld, zal er niks gebeuren.\n" - "Normaal gesproken wordt er een kanaalmode geforceerd die op deze\n" - "server niet ondersteund wordt. Als +R wordt ingevuld voor \037wat\037\n" - "zullen alle gebruikers die in het kanaal zitten maar zich niet\n" - "hebben geidentificeerd voor hun nick uit het kanaal gekicked en\n" - "verbannen worden.", - /* LNG_CHAN_RESPONSE */ - "Enforced %s" + /* LNG_CHAN_HELP */ + " ENFORCE Forceer enkele kanaalmodes en set-opties", + /* LNG_ENFORCE_SYNTAX */ + "Syntax: \002ENFORCE \037kanaal\037 [\037wat\037]\002", + /* LNG_CHAN_HELP_ENFORCE */ + "Forceer enkele kannalmodes en set-opties. De \037kanaal\037 optie\n" + "geeft aan op welk kanaal de modes en opties geforceerd moeten\n" + "worden. De \037wat\037 optie geeft aan welke modes en opties\n" + "geforceerd moeten worden; dit kan SET, SECUREOPS, RESTRICTED,\n" + "MODES, of +R zijn. Indien weggelaten is dit standaard SET.\n" + " \n" + "Als er voor \037wat\037 SET wordt ingevuld, zullen SECUREOPS en\n" + "RESTRICTED geforceerd worden op de gebruikers in het kanaal,\n" + "maar alleen als die opties aangezet zijn voor het kanaal. Als\n" + "SECUREOPS of RESTRICTED wordt gegeven voor \037wat\037 zal die optie\n" + "altijd geforceerd worden, ook als die niet is aangezet.", + /* LNG_CHAN_HELP_ENFORCE_R_ENABLED */ + "Als er voor \037wat\037 MODES wordt ingevuld, zal kanaalmode +R worden\n" + "geforceerd, als die op het kanaal aan staat. Als +R wordt ingevuld,\n" + "zal kanaalmode +R worden geforceerd, maar ook als die niet aan" + "staat voor het kanaal. Als +R niet aan staat, zullen alle ook\n" + "gebanned worden om te zorgen dat ze niet opnieuw het kanaal binnen\n" + "kunnen komen.", + /* LNG_CHAN_HELP_ENFORCE_R_DISABLED */ + "Als er voor \037wat\037 MODES wordt ingevuld, zal er niks gebeuren.\n" + "Normaal gesproken wordt er een kanaalmode geforceerd die op deze\n" + "server niet ondersteund wordt. Als +R wordt ingevuld voor \037wat\037\n" + "zullen alle gebruikers die in het kanaal zitten maar zich niet\n" + "hebben geidentificeerd voor hun nick uit het kanaal gekicked en\n" + "verbannen worden.", + /* LNG_CHAN_RESPONSE */ + "Enforced %s" }; /* German (DE) */ const char* langtable_de[] = { - /* LNG_CHAN_HELP */ - " ENFORCE Erzwingt verschieden Modes und SET Optionen", - /* LNG_ENFORCE_SYNTAX */ - "Syntax: \002ENFORCE \037Channel\037 [\037was\037]\002", - /* LNG_CHAN_HELP_ENFORCE */ - "Erzwingt verschieden Modes und SET Optionen. Die \037Channel\037\n" - "Option zeigt dir den Channel an, indem Modes und Optionen\n" - "zu erzwingen sind. Die \037was\037 Option zeigt dir welche Modes\n" - "und Optionen zu erzwingen sind. Die können nur SET, SECUREOPS,\n" - "RESTRICTED, MODES oder +R sein.Default ist SET.\n" - " \n" - "Wenn \037was\037 SET ist, wird SECUREOPS und RESTRICTED\n" - "auf die User die z.Z.in Channel sind erzwungen, wenn sie AN sind.\n" - "Benutze SECUREOPS oder RESTRICTED , um die Optionen einzeln\n" - "zu erzwingen, also wenn sie nicht eingeschaltet sind.", - /* LNG_CHAN_HELP_ENFORCE_R_ENABLED */ - "Wenn \037was\037 MODES ist, wird das ChannelMode +R erzwungen\n" - "falls an. Wenn \037was\037 +R ist, wird +R erzwungen aber eben\n" - "wenn noch nicht als Channel-Mode ist. Wenn +R noch nicht als\n" - "Channel-Mode war werden alle User aus den Channel gebannt um\n" - "sicher zu sein das sie nicht rejoinen.", - /* LNG_CHAN_HELP_ENFORCE_R_DISABLED */ - "Wenn \037was\037 MODES ist, wird nichts erzwungen weil es MODES seine\n" - "können die dein IRCD nicht unterstützt. Wenn \037was\037 +R ist\n" - "oder ein Modes was auf ein anderen IRCD gleich +R ist, wird es\n" - "erzwungen. Alle User die nicht für deren Nicknamen identifiziert\n" - "sind werden aus den Channel gekickt und gebannt.", - /* LNG_CHAN_RESPONSE */ - "Erzwungen %s" + /* LNG_CHAN_HELP */ + " ENFORCE Erzwingt verschieden Modes und SET Optionen", + /* LNG_ENFORCE_SYNTAX */ + "Syntax: \002ENFORCE \037Channel\037 [\037was\037]\002", + /* LNG_CHAN_HELP_ENFORCE */ + "Erzwingt verschieden Modes und SET Optionen. Die \037Channel\037\n" + "Option zeigt dir den Channel an, indem Modes und Optionen\n" + "zu erzwingen sind. Die \037was\037 Option zeigt dir welche Modes\n" + "und Optionen zu erzwingen sind. Die können nur SET, SECUREOPS,\n" + "RESTRICTED, MODES oder +R sein.Default ist SET.\n" + " \n" + "Wenn \037was\037 SET ist, wird SECUREOPS und RESTRICTED\n" + "auf die User die z.Z.in Channel sind erzwungen, wenn sie AN sind.\n" + "Benutze SECUREOPS oder RESTRICTED , um die Optionen einzeln\n" + "zu erzwingen, also wenn sie nicht eingeschaltet sind.", + /* LNG_CHAN_HELP_ENFORCE_R_ENABLED */ + "Wenn \037was\037 MODES ist, wird das ChannelMode +R erzwungen\n" + "falls an. Wenn \037was\037 +R ist, wird +R erzwungen aber eben\n" + "wenn noch nicht als Channel-Mode ist. Wenn +R noch nicht als\n" + "Channel-Mode war werden alle User aus den Channel gebannt um\n" + "sicher zu sein das sie nicht rejoinen.", + /* LNG_CHAN_HELP_ENFORCE_R_DISABLED */ + "Wenn \037was\037 MODES ist, wird nichts erzwungen weil es MODES seine\n" + "können die dein IRCD nicht unterstützt. Wenn \037was\037 +R ist\n" + "oder ein Modes was auf ein anderen IRCD gleich +R ist, wird es\n" + "erzwungen. Alle User die nicht für deren Nicknamen identifiziert\n" + "sind werden aus den Channel gekickt und gebannt.", + /* LNG_CHAN_RESPONSE */ + "Erzwungen %s" }; /* Portuguese (PT) */ const char* langtable_pt[] = { - /* LNG_CHAN_HELP */ - " ENFORCE Verifica o cumprimento de vários modos de canal e opções ajustadas", - /* LNG_ENFORCE_SYNTAX */ - "Sintaxe: \002ENFORCE \037canal\037 [\037opção\037]\002", - /* LNG_CHAN_HELP_ENFORCE */ - "Verifica o cumprimento de vários modos de canal e opções ajustadas.\n" - "O campo \037canal\037 indica qual canal deve ter os modos e opções verificadas\n" - "O campo \037opção\037 indica quais modos e opções devem ser verificadas,\n" - "e pode ser: SET, SECUREOPS, RESTRICTED, MODES ou +R\n" - "Quando deixado em branco, o padrão é SET.\n" - " \n" - "Se \037opção\037 for SET, serão verificadas as opções SECUREOPS e RESTRICTED\n" - "para usuários que estiverem no canal, caso elas estejam ativadas. Use\n" - "SECUREOPS para verificar a opção SECUREOPS, mesmo que ela não esteja ativada\n" - "Use RESTRICTED para verificar a opção RESTRICTED, mesmo que ela não esteja\n" - "ativada.", - /* LNG_CHAN_HELP_ENFORCE_R_ENABLED */ - "Se \037opção\037 for MODES, será verificado o modo de canal +R caso ele\n" - "esteja ativado. Se +R for especificado para \037opção\037, o modo de canal\n" - "+R também será verificado, mesmo que ele não esteja ativado. Se ele não\n" - "estiver ativado, os usuários serão banidos para evitar que reentrem no canal.", - /* LNG_CHAN_HELP_ENFORCE_R_DISABLED */ - "Se \037opção\037 for MODES, nada será verificado, visto que isto poderia\n" - "verificar modos que o IRCd atual não suporta. Se +R for especificado\n" - "para \037opção\037, um equivalente ao modo de canal +R em outros IRCds\n" - "será verificado. Todos os usuários que estão no canal, mas não estejam\n" - "identificados para seus nicks serão kickados e banidos do canal.", - /* LNG_CHAN_RESPONSE */ - "Verificado %s" + /* LNG_CHAN_HELP */ + " ENFORCE Verifica o cumprimento de vários modos de canal e opções ajustadas", + /* LNG_ENFORCE_SYNTAX */ + "Sintaxe: \002ENFORCE \037canal\037 [\037opção\037]\002", + /* LNG_CHAN_HELP_ENFORCE */ + "Verifica o cumprimento de vários modos de canal e opções ajustadas.\n" + "O campo \037canal\037 indica qual canal deve ter os modos e opções verificadas\n" + "O campo \037opção\037 indica quais modos e opções devem ser verificadas,\n" + "e pode ser: SET, SECUREOPS, RESTRICTED, MODES ou +R\n" + "Quando deixado em branco, o padrão é SET.\n" + " \n" + "Se \037opção\037 for SET, serão verificadas as opções SECUREOPS e RESTRICTED\n" + "para usuários que estiverem no canal, caso elas estejam ativadas. Use\n" + "SECUREOPS para verificar a opção SECUREOPS, mesmo que ela não esteja ativada\n" + "Use RESTRICTED para verificar a opção RESTRICTED, mesmo que ela não esteja\n" + "ativada.", + /* LNG_CHAN_HELP_ENFORCE_R_ENABLED */ + "Se \037opção\037 for MODES, será verificado o modo de canal +R caso ele\n" + "esteja ativado. Se +R for especificado para \037opção\037, o modo de canal\n" + "+R também será verificado, mesmo que ele não esteja ativado. Se ele não\n" + "estiver ativado, os usuários serão banidos para evitar que reentrem no canal.", + /* LNG_CHAN_HELP_ENFORCE_R_DISABLED */ + "Se \037opção\037 for MODES, nada será verificado, visto que isto poderia\n" + "verificar modos que o IRCd atual não suporta. Se +R for especificado\n" + "para \037opção\037, um equivalente ao modo de canal +R em outros IRCds\n" + "será verificado. Todos os usuários que estão no canal, mas não estejam\n" + "identificados para seus nicks serão kickados e banidos do canal.", + /* LNG_CHAN_RESPONSE */ + "Verificado %s" }; /* Russian (RU) */ const char* langtable_ru[] = { - /* LNG_CHAN_HELP */ - " ENFORCE Ïåðåïðîâåðêà è óñòàíîâêà ðàçëè÷íûõ ðåæèìîâ è îïöèé êàíàëà", - /* LNG_ENFORCE_SYNTAX */ - "Ñèíòàêñèñ: \002ENFORCE \037#êàíàë\037 \037ïàðàìåòð\037\002", - /* LNG_CHAN_HELP_ENFORCE */ - "Ïåðåïðîâåðêà è óñòàíîâêà ðàçëè÷íûõ ðåæèìîâ è îïöèé êàíàëà.\n" - "\037Ïàðàìåòð\037 óêàçûâàåò êàêèå îïöèè èëè ðåæèìû êàíàëà äîëæíû áûòü\n" - "ïåðåïðîâåðåíû.  êà÷åñòâå ïàðàìåòðà ìîãóò áûòü óêàçàíû: SET, SECUREOPS,\n" - "RESTRICTED, MODES, èëè +R. Åñëè ïàðàìåòð íå óêàçàí, ïî-óìîë÷àíèþ áóäåò SET.\n" - " \n" - "Åñëè â êà÷åñòâå \037ïàðàìåòðà\037 óêàçàíî SET, áóäóò ïåðåïðîâåðåíû îïöèè\n" - "SECUREOPS è RESTRICTED îòíîñèòåëüíî ïîëüçîâàòåëåé íà óêàçàííîì êàíàëå\n" - "(ïðè óñëîâèè, ÷òî îïöèè âêëþ÷åíû). Îòäåëüíî óêàçàííûé ïàðàìåòð SECUREOPS\n" - "ïðèìåíèò îïöèþ SECUREOPS (äàæå åñëè îíà \037ÍÅ\037 óñòàíîâëåíà). Ïàðàìåòð\n" - "RESTRICTED ïðèìåíèò îïöèþ RESTRICTED (äàæå åñëè îíà \037ÍÅ\037 óñòàíîâëåíà)", - /* LNG_CHAN_HELP_ENFORCE_R_ENABLED */ - "Åñëè â êà÷åñòâå \037ïàðàìåòðà\037 óêàçàíî MODES, áóäåò ïåðåïðîâåðåí ðåæèì +R\n" - "(åñëè îí óñòàíîâëåí). Îòäåëüíî óêàçàííûé ïàðàìåòð \037+R\037 ïðèìåíèò\n" - "êàíàëüíûé ðåæèì +R, äàæå åñëè îí íå óñòàíîâëåí, è çàáàíèò âñåõ ïîëüçîâàòåëåé,\n" - "êîòîðûå íå èäåíòèôèöèðîâàëèñü ê ñâîåìó íèêó èëè íå èìåþò çàðåãèñòðèðîâàííîãî íèêà.", - /* LNG_CHAN_HELP_ENFORCE_R_DISABLED */ - "Åñëè â êà÷åñòâå \037ïàðàìåòðà\037 óêàçàíî MODES, ïåðåïðîâåðêà îñóùåñòâëåíà\n" - "ÍÅ ÁÓÄÅÒ, òàê êàê òåêóùèé IRCD íå ïîääåðæèâàåò íåîáõîäèìûå ðåæèìû.\n" - "Îòäåëüíî óêàçàííûé ïàðàìåòð \037+R\037 ïðèìåíèò êàíàëüíûé ðåæèì, ýêâèâàëåíòíûé\n" - "ðåæèìó +R è çàáàíèò âñåõ ïîëüçîâàòåëåé, êîòîðûå íå èäåíòèôèöèðîâàëèñü ê ñâîåìó\n" - "íèêó èëè íå èìåþò çàðåãèñòðèðîâàííîãî íèêà.", - /* LNG_CHAN_RESPONSE */ - "Ïåðåïðîâåðåíî: %s" + /* LNG_CHAN_HELP */ + " ENFORCE Ïåðåïðîâåðêà è óñòàíîâêà ðàçëè÷íûõ ðåæèìîâ è îïöèé êàíàëà", + /* LNG_ENFORCE_SYNTAX */ + "Ñèíòàêñèñ: \002ENFORCE \037#êàíàë\037 \037ïàðàìåòð\037\002", + /* LNG_CHAN_HELP_ENFORCE */ + "Ïåðåïðîâåðêà è óñòàíîâêà ðàçëè÷íûõ ðåæèìîâ è îïöèé êàíàëà.\n" + "\037Ïàðàìåòð\037 óêàçûâàåò êàêèå îïöèè èëè ðåæèìû êàíàëà äîëæíû áûòü\n" + "ïåðåïðîâåðåíû.  êà÷åñòâå ïàðàìåòðà ìîãóò áûòü óêàçàíû: SET, SECUREOPS,\n" + "RESTRICTED, MODES, èëè +R. Åñëè ïàðàìåòð íå óêàçàí, ïî-óìîë÷àíèþ áóäåò SET.\n" + " \n" + "Åñëè â êà÷åñòâå \037ïàðàìåòðà\037 óêàçàíî SET, áóäóò ïåðåïðîâåðåíû îïöèè\n" + "SECUREOPS è RESTRICTED îòíîñèòåëüíî ïîëüçîâàòåëåé íà óêàçàííîì êàíàëå\n" + "(ïðè óñëîâèè, ÷òî îïöèè âêëþ÷åíû). Îòäåëüíî óêàçàííûé ïàðàìåòð SECUREOPS\n" + "ïðèìåíèò îïöèþ SECUREOPS (äàæå åñëè îíà \037ÍÅ\037 óñòàíîâëåíà). Ïàðàìåòð\n" + "RESTRICTED ïðèìåíèò îïöèþ RESTRICTED (äàæå åñëè îíà \037ÍÅ\037 óñòàíîâëåíà)", + /* LNG_CHAN_HELP_ENFORCE_R_ENABLED */ + "Åñëè â êà÷åñòâå \037ïàðàìåòðà\037 óêàçàíî MODES, áóäåò ïåðåïðîâåðåí ðåæèì +R\n" + "(åñëè îí óñòàíîâëåí). Îòäåëüíî óêàçàííûé ïàðàìåòð \037+R\037 ïðèìåíèò\n" + "êàíàëüíûé ðåæèì +R, äàæå åñëè îí íå óñòàíîâëåí, è çàáàíèò âñåõ ïîëüçîâàòåëåé,\n" + "êîòîðûå íå èäåíòèôèöèðîâàëèñü ê ñâîåìó íèêó èëè íå èìåþò çàðåãèñòðèðîâàííîãî íèêà.", + /* LNG_CHAN_HELP_ENFORCE_R_DISABLED */ + "Åñëè â êà÷åñòâå \037ïàðàìåòðà\037 óêàçàíî MODES, ïåðåïðîâåðêà îñóùåñòâëåíà\n" + "ÍÅ ÁÓÄÅÒ, òàê êàê òåêóùèé IRCD íå ïîääåðæèâàåò íåîáõîäèìûå ðåæèìû.\n" + "Îòäåëüíî óêàçàííûé ïàðàìåòð \037+R\037 ïðèìåíèò êàíàëüíûé ðåæèì, ýêâèâàëåíòíûé\n" + "ðåæèìó +R è çàáàíèò âñåõ ïîëüçîâàòåëåé, êîòîðûå íå èäåíòèôèöèðîâàëèñü ê ñâîåìó\n" + "íèêó èëè íå èìåþò çàðåãèñòðèðîâàííîãî íèêà.", + /* LNG_CHAN_RESPONSE */ + "Ïåðåïðîâåðåíî: %s" }; /* Italian (IT) */ const char* langtable_it[] = { - /* LNG_CHAN_HELP */ - " ENFORCE Forza diversi modi di canale ed opzioni SET", - /* LNG_ENFORCE_SYNTAX */ - "Sintassi: \002ENFORCE \037canale\037 [\037cosa\037]\002", - /* LNG_CHAN_HELP_ENFORCE */ - "Forza diversi modi di canale ed opzioni SET. Il parametro \037canale\037\n" - "indica il canale sul quale forzare i modi e le opzioni. Il parametro\n" - "\037cosa\037 indica i modi e le opzioni da forzare, e possono essere\n" - "qualsiasi delle opzioni SET, SECUREOPS, RESTRICTED, MODES, o +R.\n" - "Se non specificato, viene sottointeso SET.\n" - " \n" - "Se \037cosa\037 è SET, forzerà SECUREOPS e RESTRICTED sugli utenti\n" - "attualmente nel canale, se sono impostati. Specifica SECUREOPS per\n" - "forzare l'opzione SECUREOPS, anche se non è attivata. Specifica\n" - "RESTRICTED per forzare l'opzione RESTRICTED, anche se non è\n" - "attivata.", - /* LNG_CHAN_HELP_ENFORCE_R_ENABLED */ - "Se \037cosa\037 è MODES, forzerà il modo del canale +R se è impostato.\n" - "Se +R è specificato per \037cosa\037, il modo del canale +R verrà\n" - "forzato, anche se non è impostato. Se non è impostato, gli utenti\n" - "verranno bannati per assicurare che non rientrino semplicemente.", - /* LNG_CHAN_HELP_ENFORCE_R_DISABLED */ - "Se \037cosa\037 è MODES, niente verrà forzato, siccome forzerebbe\n" - "dei modi che l'ircd in uso non supporterebbe. Se +R è specificato\n" - "per \037cosa\037, un modo equivalente a +R sui altri ircd verrà\n" - "forzato. Tutti gli utenti presenti nel canale ma non identificati\n" - "per il loro nickname verranno bannati ed espulsi dal canale.\n", - /* LNG_CHAN_RESPONSE */ - "Forzato %s" + /* LNG_CHAN_HELP */ + " ENFORCE Forza diversi modi di canale ed opzioni SET", + /* LNG_ENFORCE_SYNTAX */ + "Sintassi: \002ENFORCE \037canale\037 [\037cosa\037]\002", + /* LNG_CHAN_HELP_ENFORCE */ + "Forza diversi modi di canale ed opzioni SET. Il parametro \037canale\037\n" + "indica il canale sul quale forzare i modi e le opzioni. Il parametro\n" + "\037cosa\037 indica i modi e le opzioni da forzare, e possono essere\n" + "qualsiasi delle opzioni SET, SECUREOPS, RESTRICTED, MODES, o +R.\n" + "Se non specificato, viene sottointeso SET.\n" + " \n" + "Se \037cosa\037 è SET, forzerà SECUREOPS e RESTRICTED sugli utenti\n" + "attualmente nel canale, se sono impostati. Specifica SECUREOPS per\n" + "forzare l'opzione SECUREOPS, anche se non è attivata. Specifica\n" + "RESTRICTED per forzare l'opzione RESTRICTED, anche se non è\n" + "attivata.", + /* LNG_CHAN_HELP_ENFORCE_R_ENABLED */ + "Se \037cosa\037 è MODES, forzerà il modo del canale +R se è impostato.\n" + "Se +R è specificato per \037cosa\037, il modo del canale +R verrà\n" + "forzato, anche se non è impostato. Se non è impostato, gli utenti\n" + "verranno bannati per assicurare che non rientrino semplicemente.", + /* LNG_CHAN_HELP_ENFORCE_R_DISABLED */ + "Se \037cosa\037 è MODES, niente verrà forzato, siccome forzerebbe\n" + "dei modi che l'ircd in uso non supporterebbe. Se +R è specificato\n" + "per \037cosa\037, un modo equivalente a +R sui altri ircd verrà\n" + "forzato. Tutti gli utenti presenti nel canale ma non identificati\n" + "per il loro nickname verranno bannati ed espulsi dal canale.\n", + /* LNG_CHAN_RESPONSE */ + "Forzato %s" }; this->InsertLanguage(LANG_EN_US, LNG_NUM_STRINGS, langtable_en_us); @@ -263,211 +466,10 @@ class CSEnforce : public Module } }; - - -/* Enforcing functions */ -void do_enforce_secureops(Channel * c) -{ - struct c_userlist *user; - struct c_userlist *next; - ChannelInfo *ci; - uint32 flags; - - if (!(ci = c->ci)) - return; - - if (debug) - alog("debug: cs_enforce: Enforcing SECUREOPS on %s", c->name); - - /* Dirty hack to allow chan_set_correct_modes to work ok. - * We pretend like SECUREOPS is on so it doesn't ignore that - * part of the code. This way we can enforce SECUREOPS even - * if it's off. - */ - flags = ci->flags; - ci->flags |= CI_SECUREOPS; - - user = c->users; - do { - next = user->next; - chan_set_correct_modes(user->user, c, 0); - user = next; - } while (user); - - ci->flags = flags; -} - -void do_enforce_restricted(Channel * c) -{ - struct c_userlist *user; - struct c_userlist *next; - ChannelInfo *ci; - int16 old_nojoin_level; - char mask[BUFSIZE]; - char *reason; - const char *av[3]; - User *u; - - if (!(ci = c->ci)) - return; - - if (debug) - alog("debug: cs_enforce: Enforcing RESTRICTED on %s", c->name); - - old_nojoin_level = ci->levels[CA_NOJOIN]; - if (ci->levels[CA_NOJOIN] < 0) - ci->levels[CA_NOJOIN] = 0; - - user = c->users; - do { - next = user->next; - u = user->user; - if (check_access(u, c->ci, CA_NOJOIN)) { - get_idealban(ci, u, mask, sizeof(mask)); - reason = getstring(u->na, CHAN_NOT_ALLOWED_TO_JOIN); - ircdproto->SendMode(whosends(ci), ci->name, "+b %s %lu", mask, - time(NULL)); - ircdproto->SendKick(whosends(ci), ci->name, u->nick, "%s", reason); - av[0] = ci->name; - av[1] = u->nick; - av[2] = reason; - do_kick(s_ChanServ, 3, av); - } - user = next; - } while (user); - - ci->levels[CA_NOJOIN] = old_nojoin_level; -} - -void do_enforce_cmode_R(Channel * c) -{ - struct c_userlist *user; - struct c_userlist *next; - ChannelInfo *ci; - char mask[BUFSIZE]; - char *reason; - const char *av[3]; - User *u; - CBMode *cbm; - - if (!(ci = c->ci)) - return; - - if (debug) - alog("debug: cs_enforce: Enforcing mode +R on %s", c->name); - - user = c->users; - do { - next = user->next; - u = user->user; - if (!nick_identified(u)) { - get_idealban(ci, u, mask, sizeof(mask)); - reason = getstring(u->na, CHAN_NOT_ALLOWED_TO_JOIN); - if (((cbm = &cbmodes[static_cast<int>('R')])->flag == 0) - || !(c->mode & cbm->flag)) - ircdproto->SendMode(whosends(ci), ci->name, "+b %s %lu", mask, - time(NULL)); - ircdproto->SendKick(whosends(ci), ci->name, u->nick, "%s", reason); - av[0] = ci->name; - av[1] = u->nick; - av[2] = reason; - do_kick(s_ChanServ, 3, av); - } - user = next; - } while (user); -} - -/* Enforcing Group Functions */ -void do_enforce_set(Channel * c) -{ - ChannelInfo *ci; - - if (!(ci = c->ci)) - return; - - if (ci->flags & CI_SECUREOPS) - do_enforce_secureops(c); - if (ci->flags & CI_RESTRICTED) - do_enforce_restricted(c); -} - -void do_enforce_modes(Channel * c) -{ - CBMode *cbm; - - if (((cbm = &cbmodes[static_cast<int>('R')])->flag != 0) && (c->mode & cbm->flag)) - do_enforce_cmode_R(c); -} - -/* End of enforcing functions */ - -int my_cs_enforce(User * u) -{ - char *cur_buffer; - char *chan=NULL; - char *what=NULL; - Channel *c; - ChannelInfo *ci; - - cur_buffer = moduleGetLastBuffer(); - chan = myStrGetToken(cur_buffer, ' ', 0); - - if (!chan) { - me->NoticeLang(s_ChanServ, u, LNG_ENFORCE_SYNTAX); - } else if (!(c = findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); - } else if (!(ci = c->ci)) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); - } else if (ci->flags & CI_VERBOTEN) { - notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, ci->name); - } else if (!is_services_admin(u) && !check_access(u, ci, CA_AKICK)) { - notice_lang(s_ChanServ, u, PERMISSION_DENIED); - } else { - what = myStrGetToken(cur_buffer, ' ', 1); - if (!what || (stricmp(what, "SET") == 0)) { - do_enforce_set(c); - me->NoticeLang(s_ChanServ,u,LNG_CHAN_RESPONSE,what); - } else if (stricmp(what, "MODES") == 0) { - do_enforce_modes(c); - me->NoticeLang(s_ChanServ,u,LNG_CHAN_RESPONSE,what); - } else if (stricmp(what, "SECUREOPS") == 0) { - do_enforce_secureops(c); - me->NoticeLang(s_ChanServ,u,LNG_CHAN_RESPONSE,what); - } else if (stricmp(what, "RESTRICTED") == 0) { - do_enforce_restricted(c); - me->NoticeLang(s_ChanServ,u,LNG_CHAN_RESPONSE,what); - } else if (stricmp(what, "+R") == 0) { - do_enforce_cmode_R(c); - me->NoticeLang(s_ChanServ,u,LNG_CHAN_RESPONSE,what); - } else { - me->NoticeLang(s_ChanServ, u, LNG_ENFORCE_SYNTAX); - } - } - - if(chan) delete [] chan; - if(what) delete [] what; - - return MOD_CONT; -} - /* Language and response stuff */ -void my_cs_help(User * u) +void my_cs_help(User *u) { me->NoticeLang(s_ChanServ, u, LNG_CHAN_HELP); } -int my_cs_help_enforce(User * u) -{ - me->NoticeLang(s_ChanServ, u, LNG_ENFORCE_SYNTAX); - ircdproto->SendMessage(findbot(s_ChanServ), u->nick, " "); - me->NoticeLang(s_ChanServ, u, LNG_CHAN_HELP_ENFORCE); - ircdproto->SendMessage(findbot(s_ChanServ), u->nick, " "); - if (cbmodes[static_cast<int>('R')].flag != 0) - me->NoticeLang(s_ChanServ, u, LNG_CHAN_HELP_ENFORCE_R_ENABLED); - else - me->NoticeLang(s_ChanServ, u, LNG_CHAN_HELP_ENFORCE_R_DISABLED); - - return MOD_STOP; -} - MODULE_INIT("cs_enforce", CSEnforce) diff --git a/src/modules/cs_tban.c b/src/modules/cs_tban.c index 2432a0d92..4b7994bfc 100644 --- a/src/modules/cs_tban.c +++ b/src/modules/cs_tban.c @@ -21,15 +21,12 @@ #define AUTHOR "Rob" #define VERSION "$Id$" -void myHelp(User * u); -void myFullHelpSyntax(User * u); -int myFullHelp(User * u); -void mySendResponse(User * u, char *channel, char *mask, char *time); +void myHelp(User *u); +void mySendResponse(User *u, char *channel, char *mask, char *time); -int do_tban(User * u); -void addBan(Channel * c, time_t timeout, char *banmask); +void addBan(Channel *c, time_t timeout, char *banmask); int delBan(int argc, char **argv); -int canBanUser(Channel * c, User * u, User * u2); +int canBanUser(Channel *c, User *u, User *u2); void mAddLanguages(); @@ -41,72 +38,117 @@ static Module *me = NULL; #define TBAN_HELP_DETAIL 2 #define TBAN_RESPONSE 3 +class CommandCSTBan : public Command +{ + public: + CommandCSTBan() : Command("TBAN", 3, 3) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + char mask[BUFSIZE]; + Channel *c; + User *u2 = NULL; + + char *chan = params[0].c_str(); + char *nick = params[1].c_str(); + char *time = params[2].c_str(); + + if (!(c = findchan(chan))) + notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); + else if (!(u2 = finduser(nick))) + notice_lang(s_ChanServ, u, NICK_X_NOT_IN_USE, nick); + else + { + if (canBanUser(c, u, u2)) + { + get_idealban(c->ci, u2, mask, sizeof(mask)); + addBan(c, dotime(time), mask); + mySendResponse(u, chan, mask, time); + } + } + + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + this->OnSyntaxError(u); + ircdproto->SendMessage(findbot(s_ChanServ), u->nick, " "); + me->NoticeLang(s_ChanServ, u, TBAN_HELP_DETAIL); + + return true; + } + + void OnSyntaxError(User *u) + { + me->NoticeLang(s_ChanServ, u, TBAN_SYNTAX); + } +}; + class CSTBan : public Module { public: CSTBan(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; - me = this; this->SetChanHelp(myHelp); - c = createCommand("TBAN", do_tban, NULL, -1, -1, -1, -1, -1); - moduleAddHelp(c, myFullHelp); - this->AddCommand(CHANSERV, c, MOD_HEAD); + this->AddCommand(CHANSERV, new CommandCSTBan(), MOD_HEAD); this->SetAuthor(AUTHOR); this->SetVersion(VERSION); this->SetType(SUPPORTED); const char* langtable_en_us[] = { - " TBAN Bans the user for a given length of time", - "Syntax: TBAN channel nick time", - "Bans the given user from a channel for a specified length of\n" - "time. If the ban is removed before by hand, it will NOT be replaced.", - "%s banned from %s, will auto-expire in %s" + " TBAN Bans the user for a given length of time", + "Syntax: TBAN channel nick time", + "Bans the given user from a channel for a specified length of\n" + "time. If the ban is removed before by hand, it will NOT be replaced.", + "%s banned from %s, will auto-expire in %s" }; const char* langtable_nl[] = { - " TBAN Verban een gebruiker voor een bepaalde tijd", - "Syntax: TBAN kanaal nick tijd", - "Verbant de gegeven gebruiken van het gegeven kanaal voor de\n" - "gegeven tijdsduur. Als de verbanning eerder wordt verwijderd,\n" - "zal deze NIET worden vervangen.", - "%s verbannen van %s, zal verlopen in %s" + " TBAN Verban een gebruiker voor een bepaalde tijd", + "Syntax: TBAN kanaal nick tijd", + "Verbant de gegeven gebruiken van het gegeven kanaal voor de\n" + "gegeven tijdsduur. Als de verbanning eerder wordt verwijderd,\n" + "zal deze NIET worden vervangen.", + "%s verbannen van %s, zal verlopen in %s" }; const char* langtable_de[] = { - " TBAN Bant ein User für eine bestimmte Zeit aus ein Channel", - "Syntax: TBAN Channel Nickname Zeit", - "Bant ein User für eine bestimmte Zeit aus ein Channel\n" - "Wenn der Ban manuell entfernt wird, wird es NICHT ersetzt.", - "%s gebannt von %s, wird auto-auslaufen in %s" + " TBAN Bant ein User für eine bestimmte Zeit aus ein Channel", + "Syntax: TBAN Channel Nickname Zeit", + "Bant ein User für eine bestimmte Zeit aus ein Channel\n" + "Wenn der Ban manuell entfernt wird, wird es NICHT ersetzt.", + "%s gebannt von %s, wird auto-auslaufen in %s" }; const char* langtable_pt[] = { - " TBAN Bane o usuário por um determinado período de tempo", - "Sintaxe: TBAN canal nick tempo", - "Bane de um canal o usuário especificado por um determinado período de\n" - "tempo. Se o ban for removido manualmente antes do tempo, ele não será recolocado.", - "%s foi banido do %s, irá auto-expirar em %s" + " TBAN Bane o usuário por um determinado período de tempo", + "Sintaxe: TBAN canal nick tempo", + "Bane de um canal o usuário especificado por um determinado período de\n" + "tempo. Se o ban for removido manualmente antes do tempo, ele não será recolocado.", + "%s foi banido do %s, irá auto-expirar em %s" }; const char* langtable_ru[] = { - " TBAN Áàíèò ïîëüçîâàòåëÿ íà óêàçàííûé ïðîìåæóòîê âðåìåíè", - "Ñèíòàêñèñ: TBAN #êàíàë íèê âðåìÿ", - "Áàíèò ïîëüçîâàòåëÿ íà óêàçàííûé ïðîìåæóòîê âðåìåíè â ñåêóíäàõ\n" - "Ïðèìå÷àíèå: óäàëåííûé âðó÷íóþ (äî ñâîåãî èñòå÷åíèÿ) áàí ÍÅ ÁÓÄÅÒ\n" - "ïåðåóñòàíîâëåí ñåðâèñàìè àâòîìàòè÷åñêè!", - "Óñòàíîâëåííûé áàí %s íà êàíàëå %s èñòå÷åò ÷åðåç %s ñåêóíä" + " TBAN Áàíèò ïîëüçîâàòåëÿ íà óêàçàííûé ïðîìåæóòîê âðåìåíè", + "Ñèíòàêñèñ: TBAN #êàíàë íèê âðåìÿ", + "Áàíèò ïîëüçîâàòåëÿ íà óêàçàííûé ïðîìåæóòîê âðåìåíè â ñåêóíäàõ\n" + "Ïðèìå÷àíèå: óäàëåííûé âðó÷íóþ (äî ñâîåãî èñòå÷åíèÿ) áàí ÍÅ ÁÓÄÅÒ\n" + "ïåðåóñòàíîâëåí ñåðâèñàìè àâòîìàòè÷åñêè!", + "Óñòàíîâëåííûé áàí %s íà êàíàëå %s èñòå÷åò ÷åðåç %s ñåêóíä" }; const char* langtable_it[] = { - " TBAN Banna l'utente per un periodo di tempo specificato", - "Sintassi: TBAN canale nick tempo", - "Banna l'utente specificato da un canale per un periodo di tempo\n" - "specificato. Se il ban viene rimosso a mano prima della scadenza, NON verrà rimpiazzato.", - "%s bannato da %s, scadrà automaticamente tra %s" + " TBAN Banna l'utente per un periodo di tempo specificato", + "Sintassi: TBAN canale nick tempo", + "Banna l'utente specificato da un canale per un periodo di tempo\n" + "specificato. Se il ban viene rimosso a mano prima della scadenza, NON verrà rimpiazzato.", + "%s bannato da %s, scadrà automaticamente tra %s" }; this->InsertLanguage(LANG_EN_US, LANG_NUM_STRINGS, langtable_en_us); @@ -118,73 +160,17 @@ class CSTBan : public Module } }; - - -void myHelp(User * u) +void myHelp(User *u) { me->NoticeLang(s_ChanServ, u, TBAN_HELP); } -void myFullHelpSyntax(User * u) -{ - me->NoticeLang(s_ChanServ, u, TBAN_SYNTAX); -} - -int myFullHelp(User * u) -{ - myFullHelpSyntax(u); - ircdproto->SendMessage(findbot(s_ChanServ), u->nick, " "); - me->NoticeLang(s_ChanServ, u, TBAN_HELP_DETAIL); - return MOD_CONT; -} - -void mySendResponse(User * u, char *channel, char *mask, char *time) +void mySendResponse(User *u, char *channel, char *mask, char *time) { me->NoticeLang(s_ChanServ, u, TBAN_RESPONSE, mask, channel, time); } -int do_tban(User * u) -{ - char mask[BUFSIZE]; - Channel *c; - User *u2 = NULL; - - char *buffer = moduleGetLastBuffer(); - char *chan; - char *nick; - char *time; - - chan = myStrGetToken(buffer, ' ', 0); - nick = myStrGetToken(buffer, ' ', 1); - time = myStrGetToken(buffer, ' ', 2); - - if (time && chan && nick) { - - if (!(c = findchan(chan))) { - notice_lang(s_ChanServ, u, CHAN_X_NOT_IN_USE, chan); - } else if (!(u2 = finduser(nick))) { - notice_lang(s_ChanServ, u, NICK_X_NOT_IN_USE, nick); - } else { - if (canBanUser(c, u, u2)) { - get_idealban(c->ci, u2, mask, sizeof(mask)); - addBan(c, dotime(time), mask); - mySendResponse(u, chan, mask, time); - } - } - } else { - myFullHelpSyntax(u); - } - if (time) - delete [] time; - if (nick) - delete [] nick; - if (chan) - delete [] chan; - - return MOD_CONT; -} - -void addBan(Channel * c, time_t timeout, char *banmask) +void addBan(Channel *c, time_t timeout, char *banmask) { const char *av[3]; char *cb[2]; @@ -209,7 +195,8 @@ int delBan(int argc, char **argv) av[0] = "-b"; av[1] = argv[1]; - if ((c = findchan(argv[0])) && c->ci) { + if ((c = findchan(argv[0])) && c->ci) + { ircdproto->SendMode(whosends(c->ci), c->name, "-b %s", av[1]); chan_set_modes(s_ChanServ, c, 2, av, 1); } @@ -221,23 +208,20 @@ int canBanUser(Channel * c, User * u, User * u2) { ChannelInfo *ci; int ok = 0; - if (!(ci = c->ci)) { + if (!(ci = c->ci)) notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, c->name); - } else if (ci->flags & CI_VERBOTEN) { + else if (ci->flags & CI_VERBOTEN) notice_lang(s_ChanServ, u, CHAN_X_FORBIDDEN, c->name); - } else if (!check_access(u, ci, CA_BAN)) { + else if (!check_access(u, ci, CA_BAN)) notice_lang(s_ChanServ, u, ACCESS_DENIED); - } else if (ircd->except && is_excepted(ci, u2)) { + else if (ircd->except && is_excepted(ci, u2)) notice_lang(s_ChanServ, u, CHAN_EXCEPTED, u2->nick, ci->name); - } else if (ircd->protectedumode && is_protected(u2)) { + else if (ircd->protectedumode && is_protected(u2)) notice_lang(s_ChanServ, u, PERMISSION_DENIED); - } else { + else ok = 1; - } return ok; } - - MODULE_INIT("cs_tban", CSTBan) diff --git a/src/modules/hs_request.c b/src/modules/hs_request.c index 838d11564..a1471705a 100644 --- a/src/modules/hs_request.c +++ b/src/modules/hs_request.c @@ -53,25 +53,12 @@ char *HSRequestDBName = NULL; #define LNG_WAITING_SYNTAX 19 #define LNG_HELP_WAITING 20 -int hs_do_request(User * u); -int hs_do_activate(User * u); -int hs_do_reject(User * u); -int hs_do_list_out(User * u); - -int hs_help_request(User * u); -int hs_help_activate(User * u); -int hs_help_reject(User * u); -int hs_help_waiting(User * u); -void hs_help(User * u); - -void my_add_host_request(char *nick, char *vIdent, char *vhost, - char *creator, int32 tmp_time); +void hs_help(User *u); + +void my_add_host_request(char *nick, char *vIdent, char *vhost, char *creator, int32 tmp_time); int my_isvalidchar(const char c); -void my_memo_lang(User * u, char *name, int z, int number, ...); -void req_send_memos(User * u, char *vHost); -void show_list(User * u); -int hs_do_waiting(User * u); -int ns_do_drop(User * u); +void my_memo_lang(User *u, char *name, int z, int number, ...); +void req_send_memos(User *u, char *vHost); void hsreq_save_db(); void hsreq_load_db(); @@ -85,37 +72,377 @@ HostCore *hs_request_head; static Module *me; -class HSRequest : public Module +class CommandHSRequest : public Command { public: - HSRequest(const std::string &modname, const std::string &creator) : Module(modname, creator) + CommandHSRequest() : Command("REQUEST", 1, 1) { - Command *c; - EvtHook *hook; + } - me = this; + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + char *nick; + const char *rawhostmask = params[1].c_str(); + char hostmask[HOSTMAX]; + NickAlias *na; + int32 tmp_time; + char *s; + char *vIdent = NULL; + time_t now = time(NULL); + + nick = u->nick; + + vIdent = myStrGetOnlyToken(rawhostmask, '@', 0); /* Get the first substring, @ as delimiter */ + if (vIdent) + { + rawhostmask = myStrGetTokenRemainder(rawhostmask, '@', 1); /* get the remaining string */ + if (!rawhostmask) + { + me->NoticeLang(s_HostServ, u, LNG_REQUEST_SYNTAX); + delete [] vIdent; + return MOD_CONT; + } + if (strlen(vIdent) > USERMAX - 1) + { + notice_lang(s_HostServ, u, HOST_SET_IDENTTOOLONG, USERMAX); + delete [] vIdent; + delete [] rawhostmask; + return MOD_CONT; + } + else + { + for (s = vIdent; *s; ++s) + { + if (!my_isvalidchar(*s)) + { + notice_lang(s_HostServ, u, HOST_SET_IDENT_ERROR); + delete [] vIdent; + delete [] rawhostmask; + return MOD_CONT; + } + } + } + if (!ircd->vident) + { + notice_lang(s_HostServ, u, HOST_NO_VIDENT); + delete [] vIdent; + delete [] rawhostmask; + return MOD_CONT; + } + } + if (strlen(rawhostmask) < HOSTMAX - 1) + snprintf(hostmask, HOSTMAX, "%s", rawhostmask); + else + { + notice_lang(s_HostServ, u, HOST_SET_TOOLONG, HOSTMAX); + if (vIdent) + { + delete [] vIdent; + delete [] rawhostmask; + } + return MOD_CONT; + } + + if (!isValidHost(hostmask, 3)) + { + notice_lang(s_HostServ, u, HOST_SET_ERROR); + if (vIdent) + { + delete [] vIdent; + delete [] rawhostmask; + } + return MOD_CONT; + } + + tmp_time = time(NULL); + if ((na = findnick(nick))) + { + if (HSRequestMemoOper || HSRequestMemoSetters) + { + if (MSSendDelay > 0 && u && u->lastmemosend + MSSendDelay > now) + { + me->NoticeLang(s_HostServ, u, LNG_REQUEST_WAIT, MSSendDelay); + u->lastmemosend = now; + if (vIdent) + { + delete [] vIdent; + delete [] rawhostmask; + } + return MOD_CONT; + } + } + my_add_host_request(nick, vIdent, hostmask, u->nick, tmp_time); + + me->NoticeLang(s_HostServ, u, LNG_REQUESTED); + req_send_memos(u, hostmask); + alog("New vHost Requested by %s", nick); + } + else + notice_lang(s_HostServ, u, HOST_NOREG, nick); + + if (vIdent) + { + delete [] vIdent; + delete [] rawhostmask; + } + + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + me->NoticeLang(s_HostServ, u, LNG_REQUEST_SYNTAX); + ircdproto->SendMessage(findbot(s_HostServ), u->nick, " "); + me->NoticeLang(s_HostServ, u, LNG_HELP_REQUEST); + + return true; + } + + void OnSyntaxError(User *u) + { + me->NoticeLang(s_HostServ, u, LNG_REQUEST_SYNTAX); + } +}; + +class CommandHSActivate : public Command +{ + public: + CommandHSActivate() : Command("ACTIVATE", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[0].c_str(); + NickAlias *na; + HostCore *tmp, *hc; + bool found = false; + + if ((na = findnick(nick))) + { + tmp = findHostCore(hs_request_head, nick, &found); + if (found) + { + if (!tmp) + hc = hs_request_head; + else + hc = tmp->next; + + addHostCore(hc->nick, hc->vIdent, hc->vHost, u->nick, time(NULL)); + + if (HSRequestMemoUser) + my_memo_lang(u, hc->nick, 2, LNG_ACTIVATE_MEMO); + + hs_request_head = deleteHostCore(hs_request_head, tmp); + me->NoticeLang(s_HostServ, u, LNG_ACTIVATED, nick); + alog("Host Request for %s activated by %s", nick, u->nick); + } + else + me->NoticeLang(s_HostServ, u, LNG_NO_REQUEST, nick); + } + else + notice_lang(s_HostServ, u, NICK_X_NOT_REGISTERED, nick); + + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_host_setter(u)) + return false; + + me->NoticeLang(s_HostServ, u, LNG_ACTIVATE_SYNTAX); + ircdproto->SendMessage(findbot(s_HostServ), u->nick, " "); + me->NoticeLang(s_HostServ, u, LNG_HELP_ACTIVATE); + if (HSRequestMemoUser) + me->NoticeLang(s_HostServ, u, LNG_HELP_ACTIVATE_MEMO); + + return true; + } + + void OnSyntaxError(User *u) + { + me->NoticeLang(s_HostServ, u, LNG_ACTIVATE_SYNTAX); + } +}; + +class CommandHSReject : public Command +{ + public: + CommandHSReject() : Command("REJECT", 1, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[0].c_str(); + const char *reason = params.size() > 1 ? params[1].c_str() : NULL; + HostCore *tmp, *hc; + bool found = false; + + tmp = findHostCore(hs_request_head, nick, &found); + if (found) + { + if (!tmp) + hc = hs_request_head; + else + hc = tmp->next; + + if (HSRequestMemoUser) + { + if (reason) + my_memo_lang(u, hc->nick, 2, LNG_REJECT_MEMO_REASON, reason); + else + my_memo_lang(u, hc->nick, 2, LNG_REJECT_MEMO); + } + + hs_request_head = deleteHostCore(hs_request_head, tmp); + me->NoticeLang(s_HostServ, u, LNG_REJECTED, nick); + alog("Host Request for %s rejected by %s (%s)", nick, u->nick, reason ? reason : ""); + } + else + me->NoticeLang(s_HostServ, u, LNG_NO_REQUEST, nick); + + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_host_setter(u)) + return false; + + me->NoticeLang(s_HostServ, u, LNG_REJECT_SYNTAX); + ircdproto->SendMessage(findbot(s_HostServ), u->nick, " "); + me->NoticeLang(s_HostServ, u, LNG_HELP_REJECT); + if (HSRequestMemoUser) + me->NoticeLang(s_HostServ, u, LNG_HELP_REJECT_MEMO); - c = createCommand("request", hs_do_request, nick_identified, -1, -1, -1, -1, -1); - moduleAddHelp(c, hs_help_request); - this->AddCommand(HOSTSERV, c, MOD_HEAD); + return true; + } - c = createCommand("activate", hs_do_activate, is_host_setter, -1, -1, -1, -1, -1); - moduleAddHelp(c, hs_help_activate); - this->AddCommand(HOSTSERV, c, MOD_HEAD); + void OnSyntaxError(User *u) + { + me->NoticeLang(s_HostServ, u, LNG_REJECT_SYNTAX); + } +}; - c = createCommand("reject", hs_do_reject, is_host_setter, -1, -1, -1, -1, -1); - moduleAddHelp(c, hs_help_reject); - this->AddCommand(HOSTSERV, c, MOD_HEAD); +class CommandHSList : public Command +{ + private: + CommandResult DoList(User *u, std::vector<std::string> ¶ms) + { + struct tm *tm; + char buf[BUFSIZE]; + int counter = 1; + int from = 0, to = 0; + int display_counter = 0; + HostCore *current; + + current = hs_request_head; + while (current) + { + if (((counter >= from && counter <= to) || (!from && !to)) && display_counter < NSListMax) + { + ++display_counter; + tm = localtime(¤t->time); + strftime(buf, sizeof(buf), getstring(NULL, STRFTIME_DATE_TIME_FORMAT), tm); + if (current->vIdent) + notice_lang(s_HostServ, u, HOST_IDENT_ENTRY, counter, current->nick, current->vIdent, current->vHost, current->creator, buf); + else + notice_lang(s_HostServ, u, HOST_ENTRY, counter, current->nick, current->vHost, current->creator, buf); + } + ++counter; + current = current->next; + } + notice_lang(s_HostServ, u, HOST_LIST_FOOTER, display_counter); - c = createCommand("waiting", hs_do_waiting, is_host_setter, -1, -1, -1, -1, -1); - moduleAddHelp(c, hs_help_waiting); - this->AddCommand(HOSTSERV, c, MOD_HEAD); + return MOD_CONT; + } + public: + CommandHSList() : Command("LIST", 1, 1) + { + } - c = createCommand("list", hs_do_list_out, is_services_oper, -1, -1, -1, -1, -1); - this->AddCommand(HOSTSERV, c, MOD_HEAD); + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *key = params[0].c_str(); - c = createCommand("drop", ns_do_drop, NULL, -1, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_HEAD); + if (stricmp(key, "+req")) + return MOD_CONT; + + return this->DoList(u, params); + } + + void OnSyntaxError(User *u) + { + // no-op + } +}; + +class CommandHSWaiting : public CommandHSList +{ + public: + CommandHSWaiting() : Command("WAITING", 0, 0) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + return this->DoList(u, params); + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_host_setter(u)) + return false; + + me->NoticeLang(s_HostServ, u, LNG_WAITING_SYNTAX); + ircdproto->SendMessage(findbot(s_HostServ), u->nick, " "); + me->NoticeLang(s_HostServ, u, LNG_HELP_WAITING); + + return true; + } +}; + +class CommandNSDrop : public Command +{ + public: + CommandNSDrop() : Command("DROP", 0, 0) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + HostCore *tmp; + bool found = false; + NickAlias *na; + + na = findnick(u->nick); + tmp = findHostCore(hs_request_head, u->nick, &found); + + if (found && na) + hs_request_head = deleteHostCore(hs_request_head, tmp); + + return MOD_CONT; + } +}; + +class HSRequest : public Module +{ + public: + HSRequest(const std::string &modname, const std::string &creator) : Module(modname, creator) + { + EvtHook *hook; + + me = this; + + this->AddCommand(HOSTSERV, new CommandHSRequest(), MOD_HEAD); + this->AddCommand(HOSTSERV, new CommandHSActivate(), MOD_HEAD); + this->AddCommand(HOSTSERV, new CommandHSReject(), MOD_HEAD); + this->AddCommand(HOSTSERV, new CommandHSWaiting(), MOD_HEAD); + this->AddCommand(HOSTSERV, new CommandHSList(), MOD_HEAD); + + this->AddCommand(NICKSERV, new CommandNSDrop(), MOD_HEAD); hook = createEventHook(EVENT_DB_SAVING, hsreqevt_db_saving); this->AddEventHook(hook); @@ -134,254 +461,255 @@ class HSRequest : public Module hsreq_load_db(); const char* langtable_en_us[] = { - /* LNG_REQUEST_SYNTAX */ - "Syntax: \002REQUEST \037vhost\037\002", - /* LNG_REQUESTED */ - "Your vHost has been requested", - /* LNG_REQUEST_WAIT */ - "Please wait %d seconds before requesting a new vHost", - /* LNG_REQUEST_MEMO */ - "[auto memo] vHost \002%s\002 has been requested.", - /* LNG_ACTIVATE_SYNTAX */ - "Syntax: \002ACTIVATE \037nick\037\002", - /* LNG_ACTIVATED */ - "vHost for %s has been activated", - /* LNG_ACTIVATE_MEMO */ - "[auto memo] Your requested vHost has been approved.", - /* LNG_REJECT_SYNTAX */ - "Syntax: \002REJECT \037nick\037\002", - /* LNG_REJECTED */ - "vHost for %s has been rejected", - /* LNG_REJECT_MEMO */ - "[auto memo] Your requested vHost has been rejected.", - /* LNG_REJECT_MEMO_REASON */ - "[auto memo] Your requested vHost has been rejected. Reason: %s", - /* LNG_NO_REQUEST */ - "No request for nick %s found.", - /* LNG_HELP */ - " REQUEST Request a vHost for your nick", - /* LNG_HELP_SETTER */ - " ACTIVATE Approve the requested vHost of a user\n" - " REJECT Reject the requested vHost of a user\n" - " WAITING Convenience command for LIST +req", - /* LNG_HELP_REQUEST */ - "Request the given vHost to be actived for your nick by the\n" - "network administrators. Please be patient while your request\n" - "is being considered.", - /* LNG_HELP_ACTIVATE */ - "Activate the requested vHost for the given nick.", - /* LNG_HELP_ACTIVATE_MEMO */ - "A memo informing the user will also be sent.", - /* LNG_HELP_REJECT */ - "Reject the requested vHost for the given nick.", - /* LNG_HELP_REJECT_MEMO */ - "A memo informing the user will also be sent.", - /* LNG_WAITING_SYNTAX */ - "Syntax: \002WAITING\002", - /* LNG_HELP_WAITING */ - "This command is provided for convenience. It is essentially\n" - "the same as performing a LIST +req ." + /* LNG_REQUEST_SYNTAX */ + "Syntax: \002REQUEST \037vhost\037\002", + /* LNG_REQUESTED */ + "Your vHost has been requested", + /* LNG_REQUEST_WAIT */ + "Please wait %d seconds before requesting a new vHost", + /* LNG_REQUEST_MEMO */ + "[auto memo] vHost \002%s\002 has been requested.", + /* LNG_ACTIVATE_SYNTAX */ + "Syntax: \002ACTIVATE \037nick\037\002", + /* LNG_ACTIVATED */ + "vHost for %s has been activated", + /* LNG_ACTIVATE_MEMO */ + "[auto memo] Your requested vHost has been approved.", + /* LNG_REJECT_SYNTAX */ + "Syntax: \002REJECT \037nick\037\002", + /* LNG_REJECTED */ + "vHost for %s has been rejected", + /* LNG_REJECT_MEMO */ + "[auto memo] Your requested vHost has been rejected.", + /* LNG_REJECT_MEMO_REASON */ + "[auto memo] Your requested vHost has been rejected. Reason: %s", + /* LNG_NO_REQUEST */ + "No request for nick %s found.", + /* LNG_HELP */ + " REQUEST Request a vHost for your nick", + /* LNG_HELP_SETTER */ + " ACTIVATE Approve the requested vHost of a user\n" + " REJECT Reject the requested vHost of a user\n" + " WAITING Convenience command for LIST +req", + /* LNG_HELP_REQUEST */ + "Request the given vHost to be actived for your nick by the\n" + "network administrators. Please be patient while your request\n" + "is being considered.", + /* LNG_HELP_ACTIVATE */ + "Activate the requested vHost for the given nick.", + /* LNG_HELP_ACTIVATE_MEMO */ + "A memo informing the user will also be sent.", + /* LNG_HELP_REJECT */ + "Reject the requested vHost for the given nick.", + /* LNG_HELP_REJECT_MEMO */ + "A memo informing the user will also be sent.", + /* LNG_WAITING_SYNTAX */ + "Syntax: \002WAITING\002", + /* LNG_HELP_WAITING */ + "This command is provided for convenience. It is essentially\n" + "the same as performing a LIST +req ." }; const char* langtable_nl[] = { - /* LNG_REQUEST_SYNTAX */ - "Gebruik: \002REQUEST \037vhost\037\002", - /* LNG_REQUESTED */ - "Je vHost is aangevraagd", - /* LNG_REQUEST_WAIT */ - "Wacht %d seconden voor je een nieuwe vHost aanvraagt", - /* LNG_REQUEST_MEMO */ - "[auto memo] vHost \002%s\002 is aangevraagd.", - /* LNG_ACTIVATE_SYNTAX */ - "Gebruik: \002ACTIVATE \037nick\037\002", - /* LNG_ACTIVATED */ - "vHost voor %s is geactiveerd", - /* LNG_ACTIVATE_MEMO */ - "[auto memo] Je aangevraagde vHost is geaccepteerd.", - /* LNG_REJECT_SYNTAX */ - "Gebruik: \002REJECT \037nick\037\002", - /* LNG_REJECTED */ - "vHost voor %s is afgekeurd", - /* LNG_REJECT_MEMO */ - "[auto memo] Je aangevraagde vHost is afgekeurd.", - /* LNG_REJECT_MEMO_REASON */ - "[auto memo] Je aangevraagde vHost is afgekeurd. Reden: %s", - /* LNG_NO_REQUEST */ - "Geen aanvraag voor nick %s gevonden.", - /* LNG_HELP */ - " REQUEST Vraag een vHost aan voor je nick", - /* LNG_HELP_SETTER */ - " ACTIVATE Activeer de aangevraagde vHost voor een gebruiker\n" - " REJECT Keur de aangevraagde vHost voor een gebruiker af\n" - " WAITING Snelkoppeling naar LIST +req", - /* LNG_HELP_REQUEST */ - "Verzoek de gegeven vHost te activeren voor jouw nick bij de\n" - "netwerk beheerders. Het kan even duren voordat je aanvraag\n" - "afgehandeld wordt.", - /* LNG_HELP_ACTIVATE */ - "Activeer de aangevraagde vHost voor de gegeven nick.", - /* LNG_HELP_ACTIVATE_MEMO */ - "Een memo die de gebruiker op de hoogste stelt zal ook worden verstuurd.", - /* LNG_HELP_REJECT */ - "Keur de aangevraagde vHost voor de gegeven nick af.", - /* LNG_HELP_REJECT_MEMO */ - "Een memo die de gebruiker op de hoogste stelt zal ook worden verstuurd.", - /* LNG_WAITING_SYNTAX */ - "Gebruik: \002WAITING\002", - /* LNG_HELP_WAITING */ - "Dit commando is beschikbaar als handigheid. Het is simpelweg\n" - "hetzelfde als LIST +req ." + /* LNG_REQUEST_SYNTAX */ + "Gebruik: \002REQUEST \037vhost\037\002", + /* LNG_REQUESTED */ + "Je vHost is aangevraagd", + /* LNG_REQUEST_WAIT */ + "Wacht %d seconden voor je een nieuwe vHost aanvraagt", + /* LNG_REQUEST_MEMO */ + "[auto memo] vHost \002%s\002 is aangevraagd.", + /* LNG_ACTIVATE_SYNTAX */ + "Gebruik: \002ACTIVATE \037nick\037\002", + /* LNG_ACTIVATED */ + "vHost voor %s is geactiveerd", + /* LNG_ACTIVATE_MEMO */ + "[auto memo] Je aangevraagde vHost is geaccepteerd.", + /* LNG_REJECT_SYNTAX */ + "Gebruik: \002REJECT \037nick\037\002", + /* LNG_REJECTED */ + "vHost voor %s is afgekeurd", + /* LNG_REJECT_MEMO */ + "[auto memo] Je aangevraagde vHost is afgekeurd.", + /* LNG_REJECT_MEMO_REASON */ + "[auto memo] Je aangevraagde vHost is afgekeurd. Reden: %s", + /* LNG_NO_REQUEST */ + "Geen aanvraag voor nick %s gevonden.", + /* LNG_HELP */ + " REQUEST Vraag een vHost aan voor je nick", + /* LNG_HELP_SETTER */ + " ACTIVATE Activeer de aangevraagde vHost voor een gebruiker\n" + " REJECT Keur de aangevraagde vHost voor een gebruiker af\n" + " WAITING Snelkoppeling naar LIST +req", + /* LNG_HELP_REQUEST */ + "Verzoek de gegeven vHost te activeren voor jouw nick bij de\n" + "netwerk beheerders. Het kan even duren voordat je aanvraag\n" + "afgehandeld wordt.", + /* LNG_HELP_ACTIVATE */ + "Activeer de aangevraagde vHost voor de gegeven nick.", + /* LNG_HELP_ACTIVATE_MEMO */ + "Een memo die de gebruiker op de hoogste stelt zal ook worden verstuurd.", + /* LNG_HELP_REJECT */ + "Keur de aangevraagde vHost voor de gegeven nick af.", + /* LNG_HELP_REJECT_MEMO */ + "Een memo die de gebruiker op de hoogste stelt zal ook worden verstuurd.", + /* LNG_WAITING_SYNTAX */ + "Gebruik: \002WAITING\002", + /* LNG_HELP_WAITING */ + "Dit commando is beschikbaar als handigheid. Het is simpelweg\n" + "hetzelfde als LIST +req ." }; const char* langtable_pt[] = { - /* LNG_REQUEST_SYNTAX */ - "Sintaxe: \002REQUEST \037vhost\037\002", - /* LNG_REQUESTED */ - "Seu pedido de vHost foi encaminhado", - /* LNG_REQUEST_WAIT */ - "Por favor, espere %d segundos antes de fazer um novo pedido de vHost", - /* LNG_REQUEST_MEMO */ - "[Auto Memo] O vHost \002%s\002 foi solicitado.", - /* LNG_ACTIVATE_SYNTAX */ - "Sintaxe: \002ACTIVATE \037nick\037\002", - /* LNG_ACTIVATED */ - "O vHost para %s foi ativado", - /* LNG_ACTIVATE_MEMO */ - "[Auto Memo] Seu pedido de vHost foi aprovado.", - /* LNG_REJECT_SYNTAX */ - "Sintaxe: \002REJECT \037nick\037\002", - /* LNG_REJECTED */ - "O vHost de %s foi recusado", - /* LNG_REJECT_MEMO */ - "[Auto Memo] Seu pedido de vHost foi recusado.", - /* LNG_REJECT_MEMO_REASON */ - "[Auto Memo] Seu pedido de vHost foi recusado. Motivo: %s", - /* LNG_NO_REQUEST */ - "Nenhum pedido encontrado para o nick %s.", - /* LNG_HELP */ - " REQUEST Request a vHost for your nick", - /* LNG_HELP_SETTER */ - " ACTIVATE Aprova o pedido de vHost de um usuário\n" - " REJECT Recusa o pedido de vHost de um usuário\n" - " WAITING Comando para LISTAR +req", - /* LNG_HELP_REQUEST */ - "Solicita a ativação do vHost fornecido em seu nick pelos\n" - "administradores da rede. Por favor, tenha paciência\n" - "enquanto seu pedido é analisado.", - /* LNG_HELP_ACTIVATE */ - "Ativa o vHost solicitado para o nick fornecido.", - /* LNG_HELP_ACTIVATE_MEMO */ - "Um memo informando o usuário também será enviado.", - /* LNG_HELP_REJECT */ - "Recusa o pedido de vHost para o nick fornecido.", - /* LNG_HELP_REJECT_MEMO */ - "Um memo informando o usuário também será enviado.", - /* LNG_WAITING_SYNTAX */ - "Sintaxe: \002WAITING\002", - /* LNG_HELP_WAITING */ - "Este comando é usado por conveniência. É essencialmente\n" - "o mesmo que fazer um LIST +req" + /* LNG_REQUEST_SYNTAX */ + "Sintaxe: \002REQUEST \037vhost\037\002", + /* LNG_REQUESTED */ + "Seu pedido de vHost foi encaminhado", + /* LNG_REQUEST_WAIT */ + "Por favor, espere %d segundos antes de fazer um novo pedido de vHost", + /* LNG_REQUEST_MEMO */ + "[Auto Memo] O vHost \002%s\002 foi solicitado.", + /* LNG_ACTIVATE_SYNTAX */ + "Sintaxe: \002ACTIVATE \037nick\037\002", + /* LNG_ACTIVATED */ + "O vHost para %s foi ativado", + /* LNG_ACTIVATE_MEMO */ + "[Auto Memo] Seu pedido de vHost foi aprovado.", + /* LNG_REJECT_SYNTAX */ + "Sintaxe: \002REJECT \037nick\037\002", + /* LNG_REJECTED */ + "O vHost de %s foi recusado", + /* LNG_REJECT_MEMO */ + "[Auto Memo] Seu pedido de vHost foi recusado.", + /* LNG_REJECT_MEMO_REASON */ + "[Auto Memo] Seu pedido de vHost foi recusado. Motivo: %s", + /* LNG_NO_REQUEST */ + "Nenhum pedido encontrado para o nick %s.", + /* LNG_HELP */ + " REQUEST Request a vHost for your nick", + /* LNG_HELP_SETTER */ + " ACTIVATE Aprova o pedido de vHost de um usuário\n" + " REJECT Recusa o pedido de vHost de um usuário\n" + " WAITING Comando para LISTAR +req", + /* LNG_HELP_REQUEST */ + "Solicita a ativação do vHost fornecido em seu nick pelos\n" + "administradores da rede. Por favor, tenha paciência\n" + "enquanto seu pedido é analisado.", + /* LNG_HELP_ACTIVATE */ + "Ativa o vHost solicitado para o nick fornecido.", + /* LNG_HELP_ACTIVATE_MEMO */ + "Um memo informando o usuário também será enviado.", + /* LNG_HELP_REJECT */ + "Recusa o pedido de vHost para o nick fornecido.", + /* LNG_HELP_REJECT_MEMO */ + "Um memo informando o usuário também será enviado.", + /* LNG_WAITING_SYNTAX */ + "Sintaxe: \002WAITING\002", + /* LNG_HELP_WAITING */ + "Este comando é usado por conveniência. É essencialmente\n" + "o mesmo que fazer um LIST +req" }; const char* langtable_ru[] = { - /* LNG_REQUEST_SYNTAX */ - "Ñèíòàêñèñ: \002REQUEST \037vHost\037\002", - /* LNG_REQUESTED */ - "Âàø çàïðîñ íà vHost îòïðàâëåí.", - /* LNG_REQUEST_WAIT */ - "Ïîæàëóéñòà, ïîäîæäèòå %d ñåêóíä, ïðåæäå ÷åì çàïðàøèâàòü íîâûé vHost", - /* LNG_REQUEST_MEMO */ - "[àâòî-ñîîáùåíèå] Áûë çàïðîøåí vHost \002%s\002", - /* LNG_ACTIVATE_SYNTAX */ - "Ñèíòàêñèñ: \002ACTIVATE \037íèê\037\002", - /* LNG_ACTIVATED */ - "vHost äëÿ %s óñïåøíî àêòèâèðîâàí", - /* LNG_ACTIVATE_MEMO */ - "[àâòî-ñîîáùåíèå] Çàïðàøèâàåìûé âàìè vHost óòâåðæäåí è àêòèâèðîâàí.", - /* LNG_REJECT_SYNTAX */ - "Ñèíòàêñèñ: \002REJECT \037íèê\037\002", - /* LNG_REJECTED */ - "vHost äëÿ %s îòêëîíåí.", - /* LNG_REJECT_MEMO */ - "[àâòî-ñîîáùåíèå] Çàïðàøèâàåìûé âàìè vHost îòêëîíåí.", - /* LNG_REJECT_MEMO_REASON */ - "[àâòî-ñîîáùåíèå] Çàïðàøèâàåìûé âàìè vHost îòêëîíåí. Ïðè÷èíà: %s", - /* LNG_NO_REQUEST */ - "Çàïðîñ íà vHost äëÿ íèêà %s íå íàéäåí.", - /* LNG_HELP */ - " REQUEST Çàïðîñ íà vHost äëÿ âàøåãî òåêóùåãî íèêà", - /* LNG_HELP_SETTER */ - " ACTIVATE Óòâåðäèòü çàïðàøèâàåìûé ïîëüçîâàòåëåì vHost\n" - " REJECT Îòêëîíèòü çàïðàøèâàåìûé ïîëüçîâàòåëåì vHost\n" - " WAITING Ñïèñîê çàïðîñîâ îæèäàþùèõ îáðàáîòêè (àíàëîã LIST +req)", - /* LNG_HELP_REQUEST */ - "Îòïðàâëÿåò çàïðîñ íà àêòèâàöèþ vHost, êîòîðûé áóäåò ðàññìîòðåí îäíèì èç\n" - "àäìèíèñòðàòîðîâ ñåòè. Ïðîñüáà ïðîÿâèòü òåðïåíèå, ïîêà çàïðîñ\n" - "ðàññìàòðèâàåòñÿ àäìèíèñòðàöèåé.", - /* LNG_HELP_ACTIVATE */ - "Óòâåðäèòü çàïðàøèâàåìûé vHost äëÿ óêàçàííîãî íèêà.", - /* LNG_HELP_ACTIVATE_MEMO */ - "Ïîëüçîâàòåëþ áóäåò ïîñëàíî àâòî-óâåäîìëåíèå îá àêòèâàöèè åãî çàïðîñà.", - /* LNG_HELP_REJECT */ - "Îòêëîíèòü çàïðàøèâàåìûé vHost äëÿ óêàçàííîãî íèêà.", - /* LNG_HELP_REJECT_MEMO */ - "Ïîëüçîâàòåëþ áóäåò ïîñëàíî àâòî-óâåäîìëåíèå îá îòêëîíåíèè åãî çàïðîñà.", - /* LNG_WAITING_SYNTAX */ - "Ñèíòàêñèñ: \002WAITING\002", - /* LNG_HELP_WAITING */ - "Äàííàÿ êîìàíäà ñîçäàíà äëÿ óäîáñòâà èñïîëüçîâàíèÿ è âûâîäèò ñïèñîê çàïðîñîâ,\n" - "îæèäàþùèõ îáðàáîòêè. Àíàëîãè÷íàÿ êîìàíäà: LIST +req ." + /* LNG_REQUEST_SYNTAX */ + "Ñèíòàêñèñ: \002REQUEST \037vHost\037\002", + /* LNG_REQUESTED */ + "Âàø çàïðîñ íà vHost îòïðàâëåí.", + /* LNG_REQUEST_WAIT */ + "Ïîæàëóéñòà, ïîäîæäèòå %d ñåêóíä, ïðåæäå ÷åì çàïðàøèâàòü íîâûé vHost", + /* LNG_REQUEST_MEMO */ + "[àâòî-ñîîáùåíèå] Áûë çàïðîøåí vHost \002%s\002", + /* LNG_ACTIVATE_SYNTAX */ + "Ñèíòàêñèñ: \002ACTIVATE \037íèê\037\002", + /* LNG_ACTIVATED */ + "vHost äëÿ %s óñïåøíî àêòèâèðîâàí", + /* LNG_ACTIVATE_MEMO */ + "[àâòî-ñîîáùåíèå] Çàïðàøèâàåìûé âàìè vHost óòâåðæäåí è àêòèâèðîâàí.", + /* LNG_REJECT_SYNTAX */ + "Ñèíòàêñèñ: \002REJECT \037íèê\037\002", + /* LNG_REJECTED */ + "vHost äëÿ %s îòêëîíåí.", + /* LNG_REJECT_MEMO */ + "[àâòî-ñîîáùåíèå] Çàïðàøèâàåìûé âàìè vHost îòêëîíåí.", + /* LNG_REJECT_MEMO_REASON */ + "[àâòî-ñîîáùåíèå] Çàïðàøèâàåìûé âàìè vHost îòêëîíåí. Ïðè÷èíà: %s", + /* LNG_NO_REQUEST */ + "Çàïðîñ íà vHost äëÿ íèêà %s íå íàéäåí.", + /* LNG_HELP */ + " REQUEST Çàïðîñ íà vHost äëÿ âàøåãî òåêóùåãî íèêà", + /* LNG_HELP_SETTER */ + " ACTIVATE Óòâåðäèòü çàïðàøèâàåìûé ïîëüçîâàòåëåì vHost\n" + " REJECT Îòêëîíèòü çàïðàøèâàåìûé ïîëüçîâàòåëåì vHost\n" + " WAITING Ñïèñîê çàïðîñîâ îæèäàþùèõ îáðàáîòêè (àíàëîã LIST +req)", + /* LNG_HELP_REQUEST */ + "Îòïðàâëÿåò çàïðîñ íà àêòèâàöèþ vHost, êîòîðûé áóäåò ðàññìîòðåí îäíèì èç\n" + "àäìèíèñòðàòîðîâ ñåòè. Ïðîñüáà ïðîÿâèòü òåðïåíèå, ïîêà çàïðîñ\n" + "ðàññìàòðèâàåòñÿ àäìèíèñòðàöèåé.", + /* LNG_HELP_ACTIVATE */ + "Óòâåðäèòü çàïðàøèâàåìûé vHost äëÿ óêàçàííîãî íèêà.", + /* LNG_HELP_ACTIVATE_MEMO */ + "Ïîëüçîâàòåëþ áóäåò ïîñëàíî àâòî-óâåäîìëåíèå îá àêòèâàöèè åãî çàïðîñà.", + /* LNG_HELP_REJECT */ + "Îòêëîíèòü çàïðàøèâàåìûé vHost äëÿ óêàçàííîãî íèêà.", + /* LNG_HELP_REJECT_MEMO */ + "Ïîëüçîâàòåëþ áóäåò ïîñëàíî àâòî-óâåäîìëåíèå îá îòêëîíåíèè åãî çàïðîñà.", + /* LNG_WAITING_SYNTAX */ + "Ñèíòàêñèñ: \002WAITING\002", + /* LNG_HELP_WAITING */ + "Äàííàÿ êîìàíäà ñîçäàíà äëÿ óäîáñòâà èñïîëüçîâàíèÿ è âûâîäèò ñïèñîê çàïðîñîâ,\n" + "îæèäàþùèõ îáðàáîòêè. Àíàëîãè÷íàÿ êîìàíäà: LIST +req ." }; const char* langtable_it[] = { - /* LNG_REQUEST_SYNTAX */ - "Sintassi: \002REQUEST \037vhost\037\002", - /* LNG_REQUESTED */ - "Il tuo vHost è stato richiesto", - /* LNG_REQUEST_WAIT */ - "Prego attendere %d secondi prima di richiedere un nuovo vHost", - /* LNG_REQUEST_MEMO */ - "[auto memo] è stato richiesto il vHost \002%s\002.", - /* LNG_ACTIVATE_SYNTAX */ - "Sintassi: \002ACTIVATE \037nick\037\002", - /* LNG_ACTIVATED */ - "Il vHost per %s è stato attivato", - /* LNG_ACTIVATE_MEMO */ - "[auto memo] Il vHost da te richiesto è stato approvato.", - /* LNG_REJECT_SYNTAX */ - "Sintassi: \002REJECT \037nick\037\002", - /* LNG_REJECTED */ - "Il vHost per %s è stato rifiutato", - /* LNG_REJECT_MEMO */ - "[auto memo] Il vHost da te richiesto è stato rifiutato.", - /* LNG_REJECT_MEMO_REASON */ - "[auto memo] Il vHost da te richiesto è stato rifiutato. Motivo: %s", - /* LNG_NO_REQUEST */ - "Nessuna richiesta trovata per il nick %s.", - /* LNG_HELP */ - " REQUEST Richiede un vHost per il tuo nick", - /* LNG_HELP_SETTER */ - " ACTIVATE Approva il vHost richiesto di un utente\n" - " REJECT Rifiuta il vHost richiesto di un utente\n" - " WAITING Comando per LIST +req", - /* LNG_HELP_REQUEST */ - "Richiede l'attivazione del vHost specificato per il tuo nick da parte\n" - "degli amministratori di rete. Sei pregato di pazientare finchè la tua\n" - "richiesta viene elaborata.", - /* LNG_HELP_ACTIVATE */ - "Attiva il vHost richiesto per il nick specificato.", - /* LNG_HELP_ACTIVATE_MEMO */ - "Viene inviato un memo per informare l'utente.", - /* LNG_HELP_REJECT */ - "Rifiuta il vHost richiesto per il nick specificato.", - /* LNG_HELP_REJECT_MEMO */ - "Viene inviato un memo per informare l'utente.", - /* LNG_WAITING_SYNTAX */ - "Sintassi: \002WAITING\002", - /* LNG_HELP_WAITING */ - "Questo comando è per comodità. Praticamente è la stessa cosa che\n" - "eseguire un LIST +req ." + /* LNG_REQUEST_SYNTAX */ + "Sintassi: \002REQUEST \037vhost\037\002", + /* LNG_REQUESTED */ + "Il tuo vHost è stato richiesto", + /* LNG_REQUEST_WAIT */ + "Prego attendere %d secondi prima di richiedere un nuovo vHost", + /* LNG_REQUEST_MEMO */ + "[auto memo] è stato richiesto il vHost \002%s\002.", + /* LNG_ACTIVATE_SYNTAX */ + "Sintassi: \002ACTIVATE \037nick\037\002", + /* LNG_ACTIVATED */ + "Il vHost per %s è stato attivato", + /* LNG_ACTIVATE_MEMO */ + "[auto memo] Il vHost da te richiesto è stato approvato.", + /* LNG_REJECT_SYNTAX */ + "Sintassi: \002REJECT \037nick\037\002", + /* LNG_REJECTED */ + "Il vHost per %s è stato rifiutato", + /* LNG_REJECT_MEMO */ + "[auto memo] Il vHost da te richiesto è stato rifiutato.", + /* LNG_REJECT_MEMO_REASON */ + "[auto memo] Il vHost da te richiesto è stato rifiutato. Motivo: %s", + /* LNG_NO_REQUEST */ + "Nessuna richiesta trovata per il nick %s.", + /* LNG_HELP */ + " REQUEST Richiede un vHost per il tuo nick", + /* LNG_HELP_SETTER */ + " ACTIVATE Approva il vHost richiesto di un utente\n" + " REJECT Rifiuta il vHost richiesto di un utente\n" + " WAITING Comando per LIST +req", + /* LNG_HELP_REQUEST */ + "Richiede l'attivazione del vHost specificato per il tuo nick da parte\n" + "degli amministratori di rete. Sei pregato di pazientare finchè la tua\n" + "richiesta viene elaborata.", + /* LNG_HELP_ACTIVATE */ + "Attiva il vHost richiesto per il nick specificato.", + /* LNG_HELP_ACTIVATE_MEMO */ + "Viene inviato un memo per informare l'utente.", + /* LNG_HELP_REJECT */ + "Rifiuta il vHost richiesto per il nick specificato.", + /* LNG_HELP_REJECT_MEMO */ + "Viene inviato un memo per informare l'utente.", + /* LNG_WAITING_SYNTAX */ + "Sintassi: \002WAITING\002", + /* LNG_HELP_WAITING */ + "Questo comando è per comodità. Praticamente è la stessa cosa che\n" + "eseguire un LIST +req ." }; + this->InsertLanguage(LANG_EN_US, LNG_NUM_STRINGS, langtable_en_us); this->InsertLanguage(LANG_NL, LNG_NUM_STRINGS, langtable_nl); this->InsertLanguage(LANG_PT, LNG_NUM_STRINGS, langtable_pt); @@ -401,109 +729,7 @@ class HSRequest : public Module } }; - -int hs_do_request(User * u) -{ - char *cur_buffer; - char *nick; - char *rawhostmask; - char hostmask[HOSTMAX]; - NickAlias *na; - int32 tmp_time; - char *s; - char *vIdent = NULL; - time_t now = time(NULL); - - cur_buffer = moduleGetLastBuffer(); - nick = u->nick; - rawhostmask = myStrGetToken(cur_buffer, ' ', 0); - - if (!nick || !rawhostmask) { - if (rawhostmask) - delete [] rawhostmask; - me->NoticeLang(s_HostServ, u, LNG_REQUEST_SYNTAX); - return MOD_CONT; - } - - vIdent = myStrGetOnlyToken(rawhostmask, '@', 0); /* Get the first substring, @ as delimiter */ - if (vIdent) { - rawhostmask = myStrGetTokenRemainder(rawhostmask, '@', 1); /* get the remaining string */ - if (!rawhostmask) { - me->NoticeLang(s_HostServ, u, LNG_REQUEST_SYNTAX); - delete [] vIdent; - return MOD_CONT; - } - if (strlen(vIdent) > USERMAX - 1) { - notice_lang(s_HostServ, u, HOST_SET_IDENTTOOLONG, USERMAX); - delete [] vIdent; - delete [] rawhostmask; - return MOD_CONT; - } else { - for (s = vIdent; *s; s++) { - if (!my_isvalidchar(*s)) { - notice_lang(s_HostServ, u, HOST_SET_IDENT_ERROR); - delete [] vIdent; - delete [] rawhostmask; - return MOD_CONT; - } - } - } - if (!ircd->vident) { - notice_lang(s_HostServ, u, HOST_NO_VIDENT); - delete [] vIdent; - delete [] rawhostmask; - return MOD_CONT; - } - } - if (strlen(rawhostmask) < HOSTMAX - 1) { - snprintf(hostmask, HOSTMAX, "%s", rawhostmask); - } else { - notice_lang(s_HostServ, u, HOST_SET_TOOLONG, HOSTMAX); - if (vIdent) - delete [] vIdent; - delete [] rawhostmask; - return MOD_CONT; - } - - if (!isValidHost(hostmask, 3)) { - notice_lang(s_HostServ, u, HOST_SET_ERROR); - if (vIdent) - delete [] vIdent; - delete [] rawhostmask; - return MOD_CONT; - } - - tmp_time = time(NULL); - if ((na = findnick(nick))) { - if (HSRequestMemoOper || HSRequestMemoSetters) { - if (MSSendDelay > 0 && u - && u->lastmemosend + MSSendDelay > now) { - me->NoticeLang(s_HostServ, u, LNG_REQUEST_WAIT, - MSSendDelay); - u->lastmemosend = now; - if (vIdent) - delete [] vIdent; - delete [] rawhostmask; - return MOD_CONT; - } - } - my_add_host_request(nick, vIdent, hostmask, u->nick, tmp_time); - - me->NoticeLang(s_HostServ, u, LNG_REQUESTED); - req_send_memos(u, hostmask); - alog("New vHost Requested by %s", nick); - } else { - notice_lang(s_HostServ, u, HOST_NOREG, nick); - } - - if (vIdent) - delete [] vIdent; - delete [] rawhostmask; - - return MOD_CONT; -} - -void my_memo_lang(User * u, char *name, int z, int number, ...) +void my_memo_lang(User *u, char *name, int z, int number, ...) { va_list va; char buffer[4096], outbuf[4096]; @@ -518,16 +744,18 @@ void my_memo_lang(User * u, char *name, int z, int number, ...) lang = u2->na->nc->language; /* If the users lang isnt supported, drop back to enlgish */ - if (me->lang[lang].argc == 0) + if (!me->lang[lang].argc) lang = LANG_EN_US; /* If the requested lang string exists for the language */ - if (me->lang[lang].argc > number) { + if (me->lang[lang].argc > number) + { fmt = me->lang[lang].argv[number]; buf = sstrdup(fmt); s = buf; - while (*s) { + while (*s) + { t = s; s += strcspn(s, "\n"); if (*s) @@ -540,13 +768,12 @@ void my_memo_lang(User * u, char *name, int z, int number, ...) memo_send(u, name, buffer, z); } delete [] buf; - } else { - alog("%s: INVALID language string call, language: [%d], String [%d]", me->name.c_str(), lang, number); } + else + alog("%s: INVALID language string call, language: [%d], String [%d]", me->name.c_str(), lang, number); } - -void req_send_memos(User * u, char *vHost) +void req_send_memos(User *u, char *vHost) { int i; int z = 2; @@ -554,281 +781,56 @@ void req_send_memos(User * u, char *vHost) if (checkDefCon(DEFCON_NO_NEW_MEMOS)) return; - if (HSRequestMemoOper == 1) { - for (i = 0; i < servopers.count; i++) { - my_memo_lang(u, ((static_cast<NickCore *>(servopers.list[i]))->display), z, - LNG_REQUEST_MEMO, vHost); - } - for (i = 0; i < servadmins.count; i++) { - my_memo_lang(u, ((static_cast<NickCore *>(servadmins.list[i]))->display), - z, LNG_REQUEST_MEMO, vHost); - } - for (i = 0; i < RootNumber; i++) { + if (HSRequestMemoOper == 1) + { + for (i = 0; i < servopers.count; ++i) + my_memo_lang(u, (static_cast<NickCore *>(servopers.list[i]))->display, z, LNG_REQUEST_MEMO, vHost); + for (i = 0; i < servadmins.count; ++i) + my_memo_lang(u, (static_cast<NickCore *>(servadmins.list[i]))->display, z, LNG_REQUEST_MEMO, vHost); + for (i = 0; i < RootNumber; ++i) my_memo_lang(u, ServicesRoots[i], z, LNG_REQUEST_MEMO, vHost); - } } - if (HSRequestMemoSetters == 1) { - for (i = 0; i < HostNumber; i++) { + if (HSRequestMemoSetters == 1) + { + for (i = 0; i < HostNumber; ++i) my_memo_lang(u, HostSetters[i], z, LNG_REQUEST_MEMO, vHost); - } - } -} - -int ns_do_drop(User * u) -{ - HostCore *tmp; - bool found = false; - NickAlias *na; - - na = findnick(u->nick); - tmp = findHostCore(hs_request_head, u->nick, &found); - - if (found && na) - hs_request_head = deleteHostCore(hs_request_head, tmp); - - return MOD_CONT; -} - -int hs_do_reject(User * u) -{ - char *cur_buffer; - char *nick; - char *reason; - HostCore *tmp, *hc; - bool found = false; - - cur_buffer = moduleGetLastBuffer(); - nick = myStrGetToken(cur_buffer, ' ', 0); - reason = myStrGetTokenRemainder(cur_buffer, ' ', 1); - - if (!nick) { - me->NoticeLang(s_HostServ, u, LNG_REJECT_SYNTAX); - if (reason) - delete [] reason; - return MOD_CONT; - } - - tmp = findHostCore(hs_request_head, nick, &found); - if (found) { - if (!tmp) - hc = hs_request_head; - else - hc = tmp->next; - - if (HSRequestMemoUser) { - if (reason) - my_memo_lang(u, hc->nick, 2, LNG_REJECT_MEMO_REASON, - reason); - else - my_memo_lang(u, hc->nick, 2, LNG_REJECT_MEMO); - } - - hs_request_head = deleteHostCore(hs_request_head, tmp); - me->NoticeLang(s_HostServ, u, LNG_REJECTED, nick); - alog("Host Request for %s rejected by %s (%s)", nick, u->nick, - reason ? reason : ""); - } else { - me->NoticeLang(s_HostServ, u, LNG_NO_REQUEST, nick); - } - - delete [] nick; - if (reason) - delete [] reason; - - return MOD_CONT; -} - -int hs_do_activate(User * u) -{ - char *cur_buffer; - char *nick; - NickAlias *na; - HostCore *tmp, *hc; - bool found = false; - - cur_buffer = moduleGetLastBuffer(); - nick = myStrGetToken(cur_buffer, ' ', 0); - - if (!nick) { - me->NoticeLang(s_HostServ, u, LNG_ACTIVATE_SYNTAX); - return MOD_CONT; } - - if ((na = findnick(nick))) { - tmp = findHostCore(hs_request_head, nick, &found); - if (found) { - if (!tmp) - hc = hs_request_head; - else - hc = tmp->next; - - addHostCore(hc->nick, hc->vIdent, hc->vHost, u->nick, - time(NULL)); - - if (HSRequestMemoUser) - my_memo_lang(u, hc->nick, 2, LNG_ACTIVATE_MEMO); - - hs_request_head = deleteHostCore(hs_request_head, tmp); - me->NoticeLang(s_HostServ, u, LNG_ACTIVATED, nick); - alog("Host Request for %s activated by %s", nick, u->nick); - } else { - me->NoticeLang(s_HostServ, u, LNG_NO_REQUEST, nick); - } - } else { - notice_lang(s_HostServ, u, NICK_X_NOT_REGISTERED, nick); - } - - delete [] nick; - return MOD_CONT; } - -void my_add_host_request(char *nick, char *vIdent, char *vhost, - char *creator, int32 tmp_time) +void my_add_host_request(char *nick, char *vIdent, char *vhost, char *creator, int32 tmp_time) { HostCore *tmp; bool found = false; - if (!hs_request_head) { - hs_request_head = - createHostCorelist(hs_request_head, nick, vIdent, vhost, - creator, tmp_time); - } else { + if (!hs_request_head) + hs_request_head = createHostCorelist(hs_request_head, nick, vIdent, vhost, creator, tmp_time); + else { tmp = findHostCore(hs_request_head, nick, &found); - if (!found) { - hs_request_head = - insertHostCore(hs_request_head, tmp, nick, vIdent, vhost, - creator, tmp_time); - } else { - hs_request_head = deleteHostCore(hs_request_head, tmp); /* delete the old entry */ - my_add_host_request(nick, vIdent, vhost, creator, tmp_time); /* recursive call to add new entry */ + if (!found) + hs_request_head = insertHostCore(hs_request_head, tmp, nick, vIdent, vhost, creator, tmp_time); + else + { + hs_request_head = deleteHostCore(hs_request_head, tmp); /* delete the old entry */ + my_add_host_request(nick, vIdent, vhost, creator, tmp_time); /* recursive call to add new entry */ } } } int my_isvalidchar(const char c) { - if (((c >= 'A') && (c <= 'Z')) || ((c >= 'a') && (c <= 'z')) - || ((c >= '0') && (c <= '9')) || (c == '.') || (c == '-')) + if ((c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') || (c >= '0' && c <= '9') || c == '.' || c == '-') return 1; else return 0; } -int hs_do_list_out(User * u) -{ - char *key; - - key = moduleGetLastBuffer(); - if (!key) - return MOD_CONT; - - if (stricmp(key, "+req") != 0) - return MOD_CONT; - - show_list(u); - - return MOD_CONT; -} - -int hs_do_waiting(User * u) -{ - show_list(u); - - return MOD_CONT; -} - -void show_list(User * u) -{ - struct tm *tm; - char buf[BUFSIZE]; - int counter = 1; - int from = 0, to = 0; - int display_counter = 0; - HostCore *current; - - current = hs_request_head; - while (current) { - if ((((counter >= from) && (counter <= to)) - || ((from == 0) && (to == 0))) - && (display_counter < NSListMax)) { - display_counter++; - tm = localtime(¤t->time); - strftime(buf, sizeof(buf), - getstring(NULL, STRFTIME_DATE_TIME_FORMAT), tm); - if (current->vIdent) - notice_lang(s_HostServ, u, HOST_IDENT_ENTRY, counter, - current->nick, current->vIdent, current->vHost, - current->creator, buf); - else - notice_lang(s_HostServ, u, HOST_ENTRY, counter, - current->nick, current->vHost, - current->creator, buf); - } - counter++; - current = current->next; - } - notice_lang(s_HostServ, u, HOST_LIST_FOOTER, display_counter); -} - -int hs_help_request(User * u) -{ - me->NoticeLang(s_HostServ, u, LNG_REQUEST_SYNTAX); - ircdproto->SendMessage(findbot(s_HostServ), u->nick, " "); - me->NoticeLang(s_HostServ, u, LNG_HELP_REQUEST); - - return MOD_CONT; -} - -int hs_help_activate(User * u) -{ - if (is_host_setter(u)) { - me->NoticeLang(s_HostServ, u, LNG_ACTIVATE_SYNTAX); - ircdproto->SendMessage(findbot(s_HostServ), u->nick, " "); - me->NoticeLang(s_HostServ, u, LNG_HELP_ACTIVATE); - if (HSRequestMemoUser) - me->NoticeLang(s_HostServ, u, LNG_HELP_ACTIVATE_MEMO); - } else { - notice_lang(s_HostServ, u, NO_HELP_AVAILABLE, "ACTIVATE"); - } - - return MOD_CONT; -} - -int hs_help_reject(User * u) -{ - if (is_host_setter(u)) { - me->NoticeLang(s_HostServ, u, LNG_REJECT_SYNTAX); - ircdproto->SendMessage(findbot(s_HostServ), u->nick, " "); - me->NoticeLang(s_HostServ, u, LNG_HELP_REJECT); - if (HSRequestMemoUser) - me->NoticeLang(s_HostServ, u, LNG_HELP_REJECT_MEMO); - } else { - notice_lang(s_HostServ, u, NO_HELP_AVAILABLE, "REJECT"); - } - - return MOD_CONT; -} - -int hs_help_waiting(User * u) -{ - if (is_host_setter(u)) { - me->NoticeLang(s_HostServ, u, LNG_WAITING_SYNTAX); - ircdproto->SendMessage(findbot(s_HostServ), u->nick, " "); - me->NoticeLang(s_HostServ, u, LNG_HELP_WAITING); - } else { - notice_lang(s_HostServ, u, NO_HELP_AVAILABLE, "WAITING"); - } - - return MOD_CONT; -} - void hs_help(User * u) { me->NoticeLang(s_HostServ, u, LNG_HELP); if (is_host_setter(u)) me->NoticeLang(s_HostServ, u, LNG_HELP_SETTER); } + void hsreq_load_db() { FILE *fp; @@ -844,31 +846,36 @@ void hsreq_load_db() filename = HSREQ_DEFAULT_DBNAME; fp = fopen(filename, "r"); - if (!fp) { - alog("[hs_request] Unable to open database ('%s') for reading", - filename); + if (!fp) + { + alog("[hs_request] Unable to open database ('%s') for reading", filename); return; } - while (fgets(readbuf, 1024, fp)) { + while (fgets(readbuf, 1024, fp)) + { buf = normalizeBuffer(readbuf); - if (buf || *buf) { + if (buf || *buf) + { nick = myStrGetToken(buf, ':', 0); vident = myStrGetToken(buf, ':', 1); vhost = myStrGetToken(buf, ':', 2); tmp = myStrGetToken(buf, ':', 3); - if (tmp) { + if (tmp) + { tmp_time = strtol(tmp, NULL, 16); delete [] tmp; - } else { - tmp_time = 0; } + else + tmp_time = 0; creator = myStrGetToken(buf, ':', 4); - if (!nick || !vident || !vhost || !creator) { + if (!nick || !vident || !vhost || !creator) + { alog("[hs_request] Error while reading database, skipping record"); continue; } - if (stricmp(vident, "(null)") == 0) { + if (!stricmp(vident, "(null)")) + { delete [] vident; vident = NULL; } @@ -901,17 +908,17 @@ void hsreq_save_db() filename = HSREQ_DEFAULT_DBNAME; fp = fopen(filename, "w"); - if (!fp) { - alog("[hs_request] Unable to open database ('%s') for writing", - filename); + if (!fp) + { + alog("[hs_request] Unable to open database ('%s') for writing", filename); return; } current = hs_request_head; - while (current) { - vident = (current->vIdent ? current->vIdent : "(null)"); - fprintf(fp, "%s:%s:%s:%X:%s\n", current->nick, vident, - current->vHost, static_cast<uint32>(current->time), current->creator); + while (current) + { + vident = current->vIdent ? current->vIdent : "(null)"; + fprintf(fp, "%s:%s:%s:%X:%s\n", current->nick, vident, current->vHost, static_cast<uint32>(current->time), current->creator); current = current->next; } @@ -923,7 +930,7 @@ void hsreq_save_db() int hsreqevt_db_saving(int argc, char **argv) { - if ((argc >= 1) && (stricmp(argv[0], EVENT_START) == 0)) + if (argc >= 1 && !stricmp(argv[0], EVENT_START)) hsreq_save_db(); return MOD_CONT; @@ -931,7 +938,8 @@ int hsreqevt_db_saving(int argc, char **argv) int hsreqevt_db_backup(int argc, char **argv) { - if ((argc >= 1) && (stricmp(argv[0], EVENT_START) == 0)) { + if (argc >= 1 && !stricmp(argv[0], EVENT_START)) + { if (HSRequestDBName) ModuleDatabaseBackup(HSRequestDBName); else diff --git a/src/modules/ns_maxemail.c b/src/modules/ns_maxemail.c index df6d51cda..b2e870c88 100644 --- a/src/modules/ns_maxemail.c +++ b/src/modules/ns_maxemail.c @@ -20,8 +20,6 @@ void my_load_config(); void my_add_languages(); -int my_ns_register(User * u); -int my_ns_set(User * u); int my_event_reload(int argc, char **argv); int NSEmailMax = 0; @@ -32,12 +30,53 @@ int NSEmailMax = 0; static Module *me; +class CommandNSRegister : public Command +{ + public: + CommandNSRegister() : Command("REGISTER", 2, 2) + { + } + + CommandResult(User *u, std::vector<std::string> ¶ms) + { + return check_email_limit_reached(params[1].c_str(), u); + } + + void OnSyntaxError(User *u) + { + // no-op + } +}; + +class CommandNSSet : public Command +{ + public: + CommandNSSet() : Command("SET", 2, 2) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *set = params[0].c_str(); + const char *email = params[1].c_str(); + + if (!stricmp(set, "email")) + return MOD_CONT; + + return check_email_limit_reached(email, u); + } + + void OnSyntaxError(User *u) + { + // no-op + } +}; + class NSMaxEmail : public Module { public: NSMaxEmail(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; EvtHook *evt; int status; @@ -47,57 +86,55 @@ class NSMaxEmail : public Module this->SetVersion(VERSION); this->SetType(SUPPORTED); - c = createCommand("REGISTER", my_ns_register, NULL, -1, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_HEAD); - c = createCommand("SET", my_ns_set, NULL, -1, -1, -1, -1, -1); - this->AddCommand(NICKSERV, c, MOD_HEAD); + this->AddCommand(NICKSERV, new CommandNSRegister(), MOD_HEAD); + this->AddCommand(NICKSERV, new CommandNSSet(), MOD_HEAD); evt = createEventHook(EVENT_RELOAD, my_event_reload); if ((status = this->AddEventHook(evt))) - throw ModuleException("ns_maxemail: Unable to hook to EVENT_RELOAD"); + throw ModuleException("ns_maxemail: Unable to hook to EVENT_RELOAD"); my_load_config(); const char *langtable_en_us[] = { - /* LNG_NSEMAILMAX_REACHED */ - "The given email address has reached it's usage limit of %d users.", - /* LNG_NSEMAILMAX_REACHED_ONE */ - "The given email address has reached it's usage limit of 1 user." + /* LNG_NSEMAILMAX_REACHED */ + "The given email address has reached it's usage limit of %d users.", + /* LNG_NSEMAILMAX_REACHED_ONE */ + "The given email address has reached it's usage limit of 1 user." }; const char *langtable_nl[] = { - /* LNG_NSEMAILMAX_REACHED */ - "Het gegeven email adres heeft de limiet van %d gebruikers bereikt.", - /* LNG_NSEMAILMAX_REACHED_ONE */ - "Het gegeven email adres heeft de limiet van 1 gebruiker bereikt." + /* LNG_NSEMAILMAX_REACHED */ + "Het gegeven email adres heeft de limiet van %d gebruikers bereikt.", + /* LNG_NSEMAILMAX_REACHED_ONE */ + "Het gegeven email adres heeft de limiet van 1 gebruiker bereikt." }; const char *langtable_de[] = { - /* LNG_NSEMAILMAX_REACHED */ - "Die angegebene eMail hat die limit Begrenzung von %d User erreicht.", - /* LNG_NSEMAILMAX_REACHED_ONE */ - "Die angegebene eMail hat die limit Begrenzung von 1 User erreicht." + /* LNG_NSEMAILMAX_REACHED */ + "Die angegebene eMail hat die limit Begrenzung von %d User erreicht.", + /* LNG_NSEMAILMAX_REACHED_ONE */ + "Die angegebene eMail hat die limit Begrenzung von 1 User erreicht." }; const char *langtable_pt[] = { - /* LNG_NSEMAILMAX_REACHED */ - "O endereço de email fornecido alcançou seu limite de uso de %d usuários.", - /* LNG_NSEMAILMAX_REACHED_ONE */ - "O endereço de email fornecido alcançou seu limite de uso de 1 usuário." + /* LNG_NSEMAILMAX_REACHED */ + "O endereço de email fornecido alcançou seu limite de uso de %d usuários.", + /* LNG_NSEMAILMAX_REACHED_ONE */ + "O endereço de email fornecido alcançou seu limite de uso de 1 usuário." }; const char *langtable_ru[] = { - /* LNG_NSEMAILMAX_REACHED */ - "Óêàçàííûé âàìè email-àäðåñ èñïîëüçóåòñÿ ìàêñèìàëüíî äîïóñòèìîå êîë-âî ðàç: %d", - /* LNG_NSEMAILMAX_REACHED_ONE */ - "Óêàçàííûé âàìè email-àäðåñ óæå êåì-òî èñïîëüçóåòñÿ." + /* LNG_NSEMAILMAX_REACHED */ + "Óêàçàííûé âàìè email-àäðåñ èñïîëüçóåòñÿ ìàêñèìàëüíî äîïóñòèìîå êîë-âî ðàç: %d", + /* LNG_NSEMAILMAX_REACHED_ONE */ + "Óêàçàííûé âàìè email-àäðåñ óæå êåì-òî èñïîëüçóåòñÿ." }; const char *langtable_it[] = { - /* LNG_NSEMAILMAX_REACHED */ - "L'indirizzo email specificato ha raggiunto il suo limite d'utilizzo di %d utenti.", - /* LNG_NSEMAILMAX_REACHED_ONE */ - "L'indirizzo email specificato ha raggiunto il suo limite d'utilizzo di 1 utente." + /* LNG_NSEMAILMAX_REACHED */ + "L'indirizzo email specificato ha raggiunto il suo limite d'utilizzo di %d utenti.", + /* LNG_NSEMAILMAX_REACHED_ONE */ + "L'indirizzo email specificato ha raggiunto il suo limite d'utilizzo di 1 utente." }; this->InsertLanguage(LANG_EN_US, LNG_NUM_STRINGS, langtable_en_us); @@ -119,10 +156,12 @@ int count_email_in_use(char *email, User * u) if (!email) return 0; - for (i = 0; i < 1024; i++) { - for (nc = nclists[i]; nc; nc = nc->next) { - if (!(u->na && u->na->nc && (u->na->nc == nc)) && nc->email && (stricmp(nc->email, email) == 0)) - count++; + for (i = 0; i < 1024; ++i) + { + for (nc = nclists[i]; nc; nc = nc->next) + { + if (!(u->na && u->na->nc && u->na->nc == nc) && nc->email && !stricmp(nc->email, email)) + ++count; } } @@ -131,7 +170,7 @@ int count_email_in_use(char *email, User * u) int check_email_limit_reached(char *email, User * u) { - if ((NSEmailMax < 1) || !email || is_services_admin(u)) + if (NSEmailMax < 1 || !email || is_services_admin(u)) return MOD_CONT; if (count_email_in_use(email, u) < NSEmailMax) @@ -140,61 +179,14 @@ int check_email_limit_reached(char *email, User * u) if (NSEmailMax == 1) me->NoticeLang(s_NickServ, u, LNG_NSEMAILMAX_REACHED_ONE); else - me->NoticeLang(s_NickServ, u, LNG_NSEMAILMAX_REACHED, - NSEmailMax); + me->NoticeLang(s_NickServ, u, LNG_NSEMAILMAX_REACHED, NSEmailMax); return MOD_STOP; } -int my_ns_register(User * u) -{ - char *cur_buffer; - char *email; - int ret; - - cur_buffer = moduleGetLastBuffer(); - email = myStrGetToken(cur_buffer, ' ', 1); - if (!email) - return MOD_CONT; - - ret = check_email_limit_reached(email, u); - delete [] email; - - return ret; -} - -int my_ns_set(User * u) -{ - char *cur_buffer; - char *set; - char *email; - int ret; - - cur_buffer = moduleGetLastBuffer(); - set = myStrGetToken(cur_buffer, ' ', 0); - - if (!set) - return MOD_CONT; - - if (stricmp(set, "email") != 0) { - delete [] set; - return MOD_CONT; - } - - delete [] set; - email = myStrGetToken(cur_buffer, ' ', 1); - if (!email) - return MOD_CONT; - - ret = check_email_limit_reached(email, u); - delete [] email; - - return ret; -} - int my_event_reload(int argc, char **argv) { - if ((argc > 0) && (stricmp(argv[0], EVENT_START) == 0)) + if (argc > 0 && !stricmp(argv[0], EVENT_START)) my_load_config(); return MOD_CONT; @@ -209,6 +201,4 @@ void my_load_config() alog("debug: [ns_maxemail] NSEmailMax set to %d", NSEmailMax); } - - MODULE_INIT("ns_maxemail", NSMaxEmail) diff --git a/src/modules/os_info.c b/src/modules/os_info.c index 765935496..c7560318d 100644 --- a/src/modules/os_info.c +++ b/src/modules/os_info.c @@ -42,16 +42,8 @@ char *OSInfoDBName = NULL; -int myAddNickInfo(User * u); -int myAddChanInfo(User * u); -int myNickInfo(User * u); -int myChanInfo(User * u); - -int mNickHelp(User * u); -int mChanHelp(User * u); -void mMainChanHelp(User * u); -void mMainNickHelp(User * u); -void m_AddLanguages(); +void mMainChanHelp(User *u); +void mMainNickHelp(User *u); int mLoadData(); int mSaveData(int argc, char **argv); @@ -63,12 +55,239 @@ static Module *me; /*************************************************************************/ +class CommandNSOInfo : public Command +{ + private: + CommandResult DoAdd(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[1].c_str(); + const char *info = params.size() > 2 ? params[2].c_str() : NULL; + NickAlias *na = NULL; + + if (!info) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + if ((na = findnick(nick))) /* ok we've found the user */ + { + /* Add the module data to the user */ + na->nc->Extend("os_info", sstrdup(info)); + me->NoticeLang(s_NickServ, u, OINFO_ADD_SUCCESS, nick); + + } + else /* NickCore not found! */ + notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + + return MOD_CONT; + } + + CommandResult DoDel(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[1].c_str(); + NickAlias *na = NULL; + + if ((na = findnick(nick))) /* ok we've found the user */ + { + char *c; + if (na->nc->GetExt("os_info", c)) + { + delete [] c; + na->nc->Shrink("os_info"); + } + + me->NoticeLang(s_NickServ, u, OINFO_DEL_SUCCESS, nick); + + } + else /* NickCore not found! */ + notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, nick); + + return MOD_CONT; + } + public: + CommandNSOInfo() : Command("OINFO", 2, 3) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + + if (!strcasecmp(cmd, "ADD")) + return this->DoAdd(u, params); + else if (!strcasecmp(cmd, "DEL")) + return this->DoDel(u, params); + else + this->OnSyntaxError(u); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_oper(u)) + return false; + + me->NoticeLang(s_NickServ, u, OINFO_HELP); + return true; + } + + void OnSyntaxError(User *u) + { + me->NoticeLang(s_NickServ, u, OINFO_SYNTAX); + } +}; + +class CommandNSInfo : public Command +{ + public: + CommandNSInfo() : Command("INFO", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *nick = params[0].c_str(); + NickAlias *na = NULL; + + if (is_oper(u)) /* Only show our goodies to opers */ + { + if ((na = findnick(nick))) /* ok we've found the user */ + { + /* If we have any info on this user */ + char *c; + if (na->nc->GetExt("os_info", c)) + { + notice_user(s_NickServ, u, " OperInfo: %s", c); + } + } + } + return MOD_CONT; + } + + void OnSyntaxError(User *u) + { + // no-op + } +}; + +class CommandCSOInfo : public Command +{ + private: + CommandResult DoAdd(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[1].c_str(); + const char *info = params.size() > 2 ? params[2].c_str() : NULL; + ChannelInfo *ci = NULL; + + if (!info) + { + this->OnSyntaxError(u); + return MOD_CONT; + } + + if ((ci = cs_findchan(chan))) + { + /* Add the module data to the channel */ + ci->Extend("os_info", sstrdup(info)); + me->NoticeLang(s_ChanServ, u, OCINFO_ADD_SUCCESS, chan); + } + else + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + + return MOD_CONT; + } + + CommandResult DoDel(User *u, std::vector<std::string> ¶ms) + { + const char *chan = params[1].c_str(); + ChannelInfo *ci = NULL; + + if ((ci = cs_findchan(chan))) + { + /* Del the module data from the channel */ + char *c; + if (ci->GetExt("os_info", c)) + { + delete [] c; + ci->Shrink("os_info"); + } + me->NoticeLang(s_ChanServ, u, OCINFO_DEL_SUCCESS, chan); + } + else + notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, chan); + + return MOD_CONT; + } + public: + CommandCSOInfo : Command("OINFO", 2, 3) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + const char *cmd = params[0].c_str(); + + if (!strcasecmp(cmd, "ADD")) + return this->DoAdd(u, params); + else if (!strcasecmp(cmd, "DEL")) + return this->DoDel(u, params); + else + this->OnSyntaxError(u); + return MOD_CONT; + } + + bool OnHelp(User *u, const std::string &subcommand) + { + if (!is_oper(u)) + return false; + + me->NoticeLang(s_ChanServ, u, OCINFO_HELP); + return true; + } + + void OnSyntaxError(User *u) + { + me->NoticeLang(s_ChanServ, u, OCINFO_SYNTAX); + } +}; + +class CommandCSInfo : public Command +{ + public: + CommandCSInfo() : Command("INFO", 1, 1) + { + } + + CommandResult Execute(User *u, std::vector<std::string> ¶ms) + { + char *chan = params[0].c_str(); + ChannelInfo *ci = NULL; + + if (is_oper(u)) /* Only show our goodies to opers */ + { + if ((ci = cs_findchan(chan))) + { + /* If we have any info on this channel */ + char *c; + if (ci->GetExt("os_info", c)) + notice_user(s_ChanServ, u, " OperInfo: %s", c); + } + } + return MOD_CONT; + } + + void OnSyntaxError(User *u) + { + // no-op + } +}; + class OSInfo : public Module { public: OSInfo(const std::string &modname, const std::string &creator) : Module(modname, creator) { - Command *c; EvtHook *hook = NULL; int status; @@ -82,19 +301,11 @@ class OSInfo : public Module if (mLoadConfig()) throw ModuleException("Unable to load config"); - c = createCommand("oInfo", myAddNickInfo, is_oper, -1, -1, -1, -1, -1); - moduleAddHelp(c, mNickHelp); - status = this->AddCommand(NICKSERV, c, MOD_HEAD); + status = this->AddCommand(NICKSERV, new CommandNSOInfo(), MOD_HEAD); + status = this->AddCommand(NICKSERV, new CommandNSInfo(), MOD_TAIL); - c = createCommand("Info", myNickInfo, NULL, -1, -1, -1, -1, -1); - status = this->AddCommand(NICKSERV, c, MOD_TAIL); - - c = createCommand("oInfo", myAddChanInfo, is_oper, -1, -1, -1, -1, -1); - moduleAddHelp(c, mChanHelp); - status = this->AddCommand(CHANSERV, c, MOD_HEAD); - - c = createCommand("Info", myChanInfo, NULL, -1, -1, -1, -1, -1); - status = this->AddCommand(CHANSERV, c, MOD_TAIL); + status = this->AddCommand(CHANSERV, new CommandCSOInfo(), MOD_HEAD); + status = this->AddCommand(CHANSERV, new CommandCSInfo(), MOD_TAIL); hook = createEventHook(EVENT_DB_SAVING, mSaveData); status = this->AddEventHook(hook); @@ -111,208 +322,208 @@ class OSInfo : public Module mLoadData(); const char* langtable_en_us[] = { - /* OINFO_SYNTAX */ - "Syntax: OINFO [ADD|DEL] nick <info>", - /* OINFO_ADD_SUCCESS */ - "OperInfo line has been added to nick %s", - /* OINFO_DEL_SUCCESS */ - "OperInfo line has been removed from nick %s", - /* OCINFO_SYNTAX */ - "Syntax: OINFO [ADD|DEL] chan <info>", - /* OCINFO_ADD_SUCCESS */ - "OperInfo line has been added to channel %s", - /* OCINFO_DEL_SUCCESS */ - "OperInfo line has been removed from channel %s", - /* OINFO_HELP */ - "Syntax: OINFO [ADD|DEL] nick <info>\n" - "Add or Delete Oper information for the given nick\n" - "This will show up when any oper /ns info nick's the user.\n" - "and can be used for 'tagging' users etc....", - /* OCINFO_HELP */ - "Syntax: OINFO [ADD|DEL] chan <info>\n" - "Add or Delete Oper information for the given channel\n" - "This will show up when any oper /cs info's the channel.\n" - "and can be used for 'tagging' channels etc....", - /* OINFO_HELP_CMD */ - " OINFO Add / Del an OperInfo line to a nick", - /* OCINFO_HELP_CMD */ - " OINFO Add / Del an OperInfo line to a channel" + /* OINFO_SYNTAX */ + "Syntax: OINFO [ADD|DEL] nick <info>", + /* OINFO_ADD_SUCCESS */ + "OperInfo line has been added to nick %s", + /* OINFO_DEL_SUCCESS */ + "OperInfo line has been removed from nick %s", + /* OCINFO_SYNTAX */ + "Syntax: OINFO [ADD|DEL] chan <info>", + /* OCINFO_ADD_SUCCESS */ + "OperInfo line has been added to channel %s", + /* OCINFO_DEL_SUCCESS */ + "OperInfo line has been removed from channel %s", + /* OINFO_HELP */ + "Syntax: OINFO [ADD|DEL] nick <info>\n" + "Add or Delete Oper information for the given nick\n" + "This will show up when any oper /ns info nick's the user.\n" + "and can be used for 'tagging' users etc....", + /* OCINFO_HELP */ + "Syntax: OINFO [ADD|DEL] chan <info>\n" + "Add or Delete Oper information for the given channel\n" + "This will show up when any oper /cs info's the channel.\n" + "and can be used for 'tagging' channels etc....", + /* OINFO_HELP_CMD */ + " OINFO Add / Del an OperInfo line to a nick", + /* OCINFO_HELP_CMD */ + " OINFO Add / Del an OperInfo line to a channel" }; const char* langtable_es[] = { - /* OINFO_SYNTAX */ - "Sintaxis: OINFO [ADD|DEL] nick <info>", - /* OINFO_ADD_SUCCESS */ - "Una linea OperInfo ha sido agregada al nick %s", - /* OINFO_DEL_SUCCESS */ - "La linea OperInfo ha sido removida del nick %s", - /* OCINFO_SYNTAX */ - "Sintaxis: OINFO [ADD|DEL] chan <info>", - /* OCINFO_ADD_SUCCESS */ - "Linea OperInfo ha sido agregada al canal %s", - /* OCINFO_DEL_SUCCESS */ - "La linea OperInfo ha sido removida del canal %s", - /* OINFO_HELP */ - "Sintaxis: OINFO [ADD|DEL] nick <info>\n" - "Agrega o elimina informacion para Operadores al nick dado\n" - "Esto se mostrara cuando cualquier operador haga /ns info nick\n" - "y puede ser usado para 'marcado' de usuarios, etc....", - /* OCINFO_HELP */ - "Sintaxis: OINFO [ADD|DEL] chan <info>\n" - "Agrega o elimina informacion para Operadores al canal dado\n" - "Esto se mostrara cuando cualquier operador haga /cs info canal\n" - "y puede ser usado para 'marcado' de canales, etc....", - /* OINFO_HELP_CMD */ - " OINFO Agrega / Elimina una linea OperInfo al nick", - /* OCINFO_HELP_CMD */ - " OINFO Agrega / Elimina una linea OperInfo al canal" + /* OINFO_SYNTAX */ + "Sintaxis: OINFO [ADD|DEL] nick <info>", + /* OINFO_ADD_SUCCESS */ + "Una linea OperInfo ha sido agregada al nick %s", + /* OINFO_DEL_SUCCESS */ + "La linea OperInfo ha sido removida del nick %s", + /* OCINFO_SYNTAX */ + "Sintaxis: OINFO [ADD|DEL] chan <info>", + /* OCINFO_ADD_SUCCESS */ + "Linea OperInfo ha sido agregada al canal %s", + /* OCINFO_DEL_SUCCESS */ + "La linea OperInfo ha sido removida del canal %s", + /* OINFO_HELP */ + "Sintaxis: OINFO [ADD|DEL] nick <info>\n" + "Agrega o elimina informacion para Operadores al nick dado\n" + "Esto se mostrara cuando cualquier operador haga /ns info nick\n" + "y puede ser usado para 'marcado' de usuarios, etc....", + /* OCINFO_HELP */ + "Sintaxis: OINFO [ADD|DEL] chan <info>\n" + "Agrega o elimina informacion para Operadores al canal dado\n" + "Esto se mostrara cuando cualquier operador haga /cs info canal\n" + "y puede ser usado para 'marcado' de canales, etc....", + /* OINFO_HELP_CMD */ + " OINFO Agrega / Elimina una linea OperInfo al nick", + /* OCINFO_HELP_CMD */ + " OINFO Agrega / Elimina una linea OperInfo al canal" }; const char* langtable_nl[] = { - /* OINFO_SYNTAX */ - "Gebruik: OINFO [ADD|DEL] nick <info>", - /* OINFO_ADD_SUCCESS */ - "OperInfo regel is toegevoegd aan nick %s", - /* OINFO_DEL_SUCCESS */ - "OperInfo regel is weggehaald van nick %s", - /* OCINFO_SYNTAX */ - "Gebruik: OINFO [ADD|DEL] kanaal <info>", - /* OCINFO_ADD_SUCCESS */ - "OperInfo regel is toegevoegd aan kanaal %s", - /* OCINFO_DEL_SUCCESS */ - "OperInfo regel is weggehaald van kanaal %s", - /* OINFO_HELP */ - "Gebruik: OINFO [ADD|DEL] nick <info>\n" - "Voeg een Oper informatie regel toe aan de gegeven nick, of\n" - "verwijder deze. Deze regel zal worden weergegeven wanneer\n" - "een oper /ns info nick doet voor deze gebruiker, en kan worden\n" - "gebruikt om een gebruiker te 'markeren' etc...", - /* OCINFO_HELP */ - "Gebruik: OINFO [ADD|DEL] kanaal <info>\n" - "Voeg een Oper informatie regel toe aan de gegeven kanaal, of\n" - "verwijder deze. Deze regel zal worden weergegeven wanneer\n" - "een oper /cs info kanaal doet voor dit kanaal, en kan worden\n" - "gebruikt om een kanaal te 'markeren' etc...", - /* OINFO_HELP_CMD */ - " OINFO Voeg een OperInfo regel toe aan een nick of verwijder deze", - /* OCINFO_HELP_CMD */ - " OINFO Voeg een OperInfo regel toe aan een kanaal of verwijder deze" + /* OINFO_SYNTAX */ + "Gebruik: OINFO [ADD|DEL] nick <info>", + /* OINFO_ADD_SUCCESS */ + "OperInfo regel is toegevoegd aan nick %s", + /* OINFO_DEL_SUCCESS */ + "OperInfo regel is weggehaald van nick %s", + /* OCINFO_SYNTAX */ + "Gebruik: OINFO [ADD|DEL] kanaal <info>", + /* OCINFO_ADD_SUCCESS */ + "OperInfo regel is toegevoegd aan kanaal %s", + /* OCINFO_DEL_SUCCESS */ + "OperInfo regel is weggehaald van kanaal %s", + /* OINFO_HELP */ + "Gebruik: OINFO [ADD|DEL] nick <info>\n" + "Voeg een Oper informatie regel toe aan de gegeven nick, of\n" + "verwijder deze. Deze regel zal worden weergegeven wanneer\n" + "een oper /ns info nick doet voor deze gebruiker, en kan worden\n" + "gebruikt om een gebruiker te 'markeren' etc...", + /* OCINFO_HELP */ + "Gebruik: OINFO [ADD|DEL] kanaal <info>\n" + "Voeg een Oper informatie regel toe aan de gegeven kanaal, of\n" + "verwijder deze. Deze regel zal worden weergegeven wanneer\n" + "een oper /cs info kanaal doet voor dit kanaal, en kan worden\n" + "gebruikt om een kanaal te 'markeren' etc...", + /* OINFO_HELP_CMD */ + " OINFO Voeg een OperInfo regel toe aan een nick of verwijder deze", + /* OCINFO_HELP_CMD */ + " OINFO Voeg een OperInfo regel toe aan een kanaal of verwijder deze" }; const char* langtable_de[] = { - /* OINFO_SYNTAX */ - "Syntax: OINFO [ADD|DEL] Nickname <Information>", - /* OINFO_ADD_SUCCESS */ - "Eine OperInfo Linie wurde zu den Nicknamen %s hinzugefügt", - /* OINFO_DEL_SUCCESS */ - "Die OperInfo Linie wurde von den Nicknamen %s enfernt", - /* OCINFO_SYNTAX */ - "Syntax: OINFO [ADD|DEL] Channel <Information>", - /* OCINFO_ADD_SUCCESS */ - "Eine OperInfo Linie wurde zu den Channel %s hinzugefügt", - /* OCINFO_DEL_SUCCESS */ - "Die OperInfo Linie wurde von den Channel %s enfernt", - /* OINFO_HELP */ - "Syntax: OINFO [ADD|DEL] Nickname <Information>\n" - "Addiert oder löscht eine OperInfo Linie zu den angegebenen\n" - "Nicknamen.Sie wird angezeigt wenn ein Oper mit /ns info sich\n" - "über den Nicknamen informiert.", - /* OCINFO_HELP */ - "Syntax: OINFO [ADD|DEL] chan <info>\n" - "Addiert oder löscht eine OperInfo Linie zu den angegebenen\n" - "Channel.Sie wird angezeigt wenn ein Oper mit /cs info sich\n" - "über den Channel informiert.", - /* OINFO_HELP_CMD */ - " OINFO Addiert / Löscht eine OperInfo Linie zu / von einen Nicknamen", - /* OCINFO_HELP_CMD */ - " OINFO Addiert / Löscht eine OperInfo Linie zu / von einen Channel" + /* OINFO_SYNTAX */ + "Syntax: OINFO [ADD|DEL] Nickname <Information>", + /* OINFO_ADD_SUCCESS */ + "Eine OperInfo Linie wurde zu den Nicknamen %s hinzugefügt", + /* OINFO_DEL_SUCCESS */ + "Die OperInfo Linie wurde von den Nicknamen %s enfernt", + /* OCINFO_SYNTAX */ + "Syntax: OINFO [ADD|DEL] Channel <Information>", + /* OCINFO_ADD_SUCCESS */ + "Eine OperInfo Linie wurde zu den Channel %s hinzugefügt", + /* OCINFO_DEL_SUCCESS */ + "Die OperInfo Linie wurde von den Channel %s enfernt", + /* OINFO_HELP */ + "Syntax: OINFO [ADD|DEL] Nickname <Information>\n" + "Addiert oder löscht eine OperInfo Linie zu den angegebenen\n" + "Nicknamen.Sie wird angezeigt wenn ein Oper mit /ns info sich\n" + "über den Nicknamen informiert.", + /* OCINFO_HELP */ + "Syntax: OINFO [ADD|DEL] chan <info>\n" + "Addiert oder löscht eine OperInfo Linie zu den angegebenen\n" + "Channel.Sie wird angezeigt wenn ein Oper mit /cs info sich\n" + "über den Channel informiert.", + /* OINFO_HELP_CMD */ + " OINFO Addiert / Löscht eine OperInfo Linie zu / von einen Nicknamen", + /* OCINFO_HELP_CMD */ + " OINFO Addiert / Löscht eine OperInfo Linie zu / von einen Channel" }; const char* langtable_pt[] = { - /* OINFO_SYNTAX */ - "Sintaxe: OINFO [ADD|DEL] nick <informação>", - /* OINFO_ADD_SUCCESS */ - "A linha OperInfo foi adicionada ao nick %s", - /* OINFO_DEL_SUCCESS */ - "A linha OperInfo foi removida do nick %s", - /* OCINFO_SYNTAX */ - "Sintaxe: OINFO [ADD|DEL] canal <informação>", - /* OCINFO_ADD_SUCCESS */ - "A linha OperInfo foi adicionada ao canal %s", - /* OCINFO_DEL_SUCCESS */ - "A linha OperInfo foi removida do canal %s", - /* OINFO_HELP */ - "Sintaxe: OINFO [ADD|DEL] nick <informação>\n" - "Adiciona ou apaga informação para Operadores ao nick fornecido\n" - "Isto será mostrado quando qualquer Operador usar /ns info nick\n" - "e pode ser usado para 'etiquetar' usuários etc...", - /* OCINFO_HELP */ - "Sintaxe: OINFO [ADD|DEL] canal <informação>\n" - "Adiciona ou apaga informação para Operadores ao canal fornecido\n" - "Isto será mostrado quando qualquer Operador usar /cs info canal\n" - "e pode ser usado para 'etiquetar' canais etc...", - /* OINFO_HELP_CMD */ - " OINFO Adiciona ou Apaga a linha OperInfo para um nick", - /* OCINFO_HELP_CMD */ - " OINFO Adiciona ou Apaga a linha OperInfo para um canal" + /* OINFO_SYNTAX */ + "Sintaxe: OINFO [ADD|DEL] nick <informação>", + /* OINFO_ADD_SUCCESS */ + "A linha OperInfo foi adicionada ao nick %s", + /* OINFO_DEL_SUCCESS */ + "A linha OperInfo foi removida do nick %s", + /* OCINFO_SYNTAX */ + "Sintaxe: OINFO [ADD|DEL] canal <informação>", + /* OCINFO_ADD_SUCCESS */ + "A linha OperInfo foi adicionada ao canal %s", + /* OCINFO_DEL_SUCCESS */ + "A linha OperInfo foi removida do canal %s", + /* OINFO_HELP */ + "Sintaxe: OINFO [ADD|DEL] nick <informação>\n" + "Adiciona ou apaga informação para Operadores ao nick fornecido\n" + "Isto será mostrado quando qualquer Operador usar /ns info nick\n" + "e pode ser usado para 'etiquetar' usuários etc...", + /* OCINFO_HELP */ + "Sintaxe: OINFO [ADD|DEL] canal <informação>\n" + "Adiciona ou apaga informação para Operadores ao canal fornecido\n" + "Isto será mostrado quando qualquer Operador usar /cs info canal\n" + "e pode ser usado para 'etiquetar' canais etc...", + /* OINFO_HELP_CMD */ + " OINFO Adiciona ou Apaga a linha OperInfo para um nick", + /* OCINFO_HELP_CMD */ + " OINFO Adiciona ou Apaga a linha OperInfo para um canal" }; const char* langtable_ru[] = { - /* OINFO_SYNTAX */ - "Ñèíòàêñèñ: OINFO ADD|DEL íèê òåñò", - /* OINFO_ADD_SUCCESS */ - "Îïåð-Èíôîðìàöèÿ äëÿ íèêà %s äîáàâëåíà", - /* OINFO_DEL_SUCCESS */ - "Îïåð-Èíôîðìàöèÿ äëÿ íèêà %s áûëà óäàëåíà", - /* OCINFO_SYNTAX */ - "Ñèíòàêñèñ: OINFO ADD|DEL #êàíàë òåêñò", - /* OCINFO_ADD_SUCCESS */ - "Îïåð-Èíôîðìàöèÿ äëÿ êàíàëà %s óñïåøíî óñòàíîâëåíà", - /* OCINFO_DEL_SUCCESS */ - "Îïåð-Èíôîðìàöèÿ äëÿ êàíàëà %s áûëà óäàëåíà", - /* OINFO_HELP */ - "Ñèíòàêñèñ: OINFO ADD|DEL íèê òåêñò\n" - "Óñòàíàâëèâàåò èëè óäàëÿåò Îïåð-Èíôîðìàöèþ äëÿ óêàçàííîãî íèêà,\n" - "êîòîðàÿ áóäåò ïîêàçàíà ëþáîìó îïåðàòîðó, çàïðàøèâàþùåìó INFO íèêà.\n" - "Ìîæåò áûòü èñïîëüçîâàíà äëÿ 'ïîìåòêè' ïîëüçîâàòåëåé è ò. ä...", - /* OCINFO_HELP */ - "Ñèíòàêñèñ: OINFO ADD|DEL #êàíàë òåêñò\n" - "Óñòàíàâëèâàåò èëè óäàëÿåò Îïåð-Èíôîðìàöèþ äëÿ óêàçàííîãî êàíàëà,\n" - "êîòîðàÿ áóäåò ïîêàçàíà ëþáîìó îïåðàòîðó, çàïðàøèâàþùåìó INFO êàíàëà.\n" - "Ìîæåò áûòü èñïîëüçîâàíà äëÿ 'ïîìåòêè' êàíàëîâ è ò. ä...", - /* OINFO_HELP_CMD */ - " OINFO Äîáàâëÿåò/Óäàëÿåò îïåð-èíôî äëÿ íèêà", - /* OCINFO_HELP_CMD */ - " OINFO Äîáàâëÿåò/Óäàëÿåò îïåð-èíôî äëÿ êàíàëà" + /* OINFO_SYNTAX */ + "Ñèíòàêñèñ: OINFO ADD|DEL íèê òåñò", + /* OINFO_ADD_SUCCESS */ + "Îïåð-Èíôîðìàöèÿ äëÿ íèêà %s äîáàâëåíà", + /* OINFO_DEL_SUCCESS */ + "Îïåð-Èíôîðìàöèÿ äëÿ íèêà %s áûëà óäàëåíà", + /* OCINFO_SYNTAX */ + "Ñèíòàêñèñ: OINFO ADD|DEL #êàíàë òåêñò", + /* OCINFO_ADD_SUCCESS */ + "Îïåð-Èíôîðìàöèÿ äëÿ êàíàëà %s óñïåøíî óñòàíîâëåíà", + /* OCINFO_DEL_SUCCESS */ + "Îïåð-Èíôîðìàöèÿ äëÿ êàíàëà %s áûëà óäàëåíà", + /* OINFO_HELP */ + "Ñèíòàêñèñ: OINFO ADD|DEL íèê òåêñò\n" + "Óñòàíàâëèâàåò èëè óäàëÿåò Îïåð-Èíôîðìàöèþ äëÿ óêàçàííîãî íèêà,\n" + "êîòîðàÿ áóäåò ïîêàçàíà ëþáîìó îïåðàòîðó, çàïðàøèâàþùåìó INFO íèêà.\n" + "Ìîæåò áûòü èñïîëüçîâàíà äëÿ 'ïîìåòêè' ïîëüçîâàòåëåé è ò. ä...", + /* OCINFO_HELP */ + "Ñèíòàêñèñ: OINFO ADD|DEL #êàíàë òåêñò\n" + "Óñòàíàâëèâàåò èëè óäàëÿåò Îïåð-Èíôîðìàöèþ äëÿ óêàçàííîãî êàíàëà,\n" + "êîòîðàÿ áóäåò ïîêàçàíà ëþáîìó îïåðàòîðó, çàïðàøèâàþùåìó INFO êàíàëà.\n" + "Ìîæåò áûòü èñïîëüçîâàíà äëÿ 'ïîìåòêè' êàíàëîâ è ò. ä...", + /* OINFO_HELP_CMD */ + " OINFO Äîáàâëÿåò/Óäàëÿåò îïåð-èíôî äëÿ íèêà", + /* OCINFO_HELP_CMD */ + " OINFO Äîáàâëÿåò/Óäàëÿåò îïåð-èíôî äëÿ êàíàëà" }; const char* langtable_it[] = { - /* OINFO_SYNTAX */ - "Sintassi: OINFO [ADD|DEL] nick <info>", - /* OINFO_ADD_SUCCESS */ - "Linea OperInfo aggiunta al nick %s", - /* OINFO_DEL_SUCCESS */ - "Linea OperInfo rimossa dal nick %s", - /* OCINFO_SYNTAX */ - "Sintassi: OINFO [ADD|DEL] chan <info>", - /* OCINFO_ADD_SUCCESS */ - "Linea OperInfo aggiunta al canale %s", - /* OCINFO_DEL_SUCCESS */ - "Linea OperInfo rimossa dal canale %s", - /* OINFO_HELP */ - "Sintassi: OINFO [ADD|DEL] nick <info>\n" - "Aggiunge o rimuove informazioni Oper per il nick specificato\n" - "Queste vengono mostrate quando un oper esegue il comando /ns info <nick>\n" - "e possono essere utilizzate per 'marchiare' gli utenti ecc...", - /* OCINFO_HELP */ - "Sintassi: OINFO [ADD|DEL] chan <info>\n" - "Aggiunge o rimuove informazioni Oper per il canale specificato\n" - "Queste vengono mostrate quando un oper esegue il comando /cs info <canale>\n" - "e possono essere utilizzate per 'marchiare' i canali ecc...", - /* OINFO_HELP_CMD */ - " OINFO Aggiunge/Rimuove una linea OperInfo ad/da un nick", - /* OCINFO_HELP_CMD */ - " OINFO Aggiunge/Rimuove una linea OperInfo ad/da un canale" + /* OINFO_SYNTAX */ + "Sintassi: OINFO [ADD|DEL] nick <info>", + /* OINFO_ADD_SUCCESS */ + "Linea OperInfo aggiunta al nick %s", + /* OINFO_DEL_SUCCESS */ + "Linea OperInfo rimossa dal nick %s", + /* OCINFO_SYNTAX */ + "Sintassi: OINFO [ADD|DEL] chan <info>", + /* OCINFO_ADD_SUCCESS */ + "Linea OperInfo aggiunta al canale %s", + /* OCINFO_DEL_SUCCESS */ + "Linea OperInfo rimossa dal canale %s", + /* OINFO_HELP */ + "Sintassi: OINFO [ADD|DEL] nick <info>\n" + "Aggiunge o rimuove informazioni Oper per il nick specificato\n" + "Queste vengono mostrate quando un oper esegue il comando /ns info <nick>\n" + "e possono essere utilizzate per 'marchiare' gli utenti ecc...", + /* OCINFO_HELP */ + "Sintassi: OINFO [ADD|DEL] chan <info>\n" + "Aggiunge o rimuove informazioni Oper per il canale specificato\n" + "Queste vengono mostrate quando un oper esegue il comando /cs info <canale>\n" + "e possono essere utilizzate per 'marchiare' i canali ecc...", + /* OINFO_HELP_CMD */ + " OINFO Aggiunge/Rimuove una linea OperInfo ad/da un nick", + /* OCINFO_HELP_CMD */ + " OINFO Aggiunge/Rimuove una linea OperInfo ad/da un canale" }; this->InsertLanguage(LANG_EN_US, LANG_NUM_STRINGS, langtable_en_us); @@ -328,7 +539,7 @@ class OSInfo : public Module { char *av[1]; - for (int i = 0; i < 1024; i++) + for (int i = 0; i < 1024; ++i) { /* Remove the nick Cores */ for (NickCore *nc = nclists[i]; nc; nc = nc->next) @@ -350,226 +561,6 @@ class OSInfo : public Module } }; - - - -/*************************************************************************/ - -/** - * Provide the user interface to add/remove/update oper information - * about a nick. - * We are going to assume that anyone who gets this far is an oper; - * the createCommand should have handled this checking for us and its - * tedious / a waste to do it twice. - * @param u The user who executed this command - * @return MOD_CONT if we want to process other commands in this command - * stack, MOD_STOP if we dont - **/ -int myAddNickInfo(User * u) -{ - char *text = NULL; - char *cmd = NULL; - char *nick = NULL; - char *info = NULL; - NickAlias *na = NULL; - - /* Get the last buffer anope recived */ - text = moduleGetLastBuffer(); - if (text) { - cmd = myStrGetToken(text, ' ', 0); - nick = myStrGetToken(text, ' ', 1); - info = myStrGetTokenRemainder(text, ' ', 2); - if (cmd && nick) { - if (strcasecmp(cmd, "ADD") == 0) { - /* Syntax error, again! */ - if (info) { - /* ok we've found the user */ - if ((na = findnick(nick))) { - /* Add the module data to the user */ - na->nc->Extend("os_info", sstrdup(info)); - me->NoticeLang(s_NickServ, u, OINFO_ADD_SUCCESS, nick); - /* NickCore not found! */ - } else { - notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, - nick); - } - delete [] info; - } - } else if (strcasecmp(cmd, "DEL") == 0) { - /* ok we've found the user */ - if ((na = findnick(nick))) - { - char *c; - if (na->nc->GetExt("os_info", c)) - { - delete [] c; - na->nc->Shrink("os_info"); - } - - me->NoticeLang(s_NickServ, u, OINFO_DEL_SUCCESS, nick); - /* NickCore not found! */ - } else { - notice_lang(s_NickServ, u, NICK_X_NOT_REGISTERED, - nick); - } - /* another syntax error! */ - } else { - me->NoticeLang(s_NickServ, u, OINFO_SYNTAX); - } - delete [] cmd; - delete [] nick; - /* Syntax error */ - } else if (cmd) { - me->NoticeLang(s_NickServ, u, OINFO_SYNTAX); - delete [] cmd; - /* Syntax error */ - } else { - me->NoticeLang(s_NickServ, u, OINFO_SYNTAX); - } - } - return MOD_CONT; -} - -/** - * Provide the user interface to add/remove/update oper information - * about a channel. - * We are going to assume that anyone who gets this far is an oper; - * the createCommand should have handled this checking for us and - * its tedious / a waste to do it twice. - * @param u The user who executed this command - * @return MOD_CONT if we want to process other commands in this command - * stack, MOD_STOP if we dont - **/ -int myAddChanInfo(User * u) -{ - char *text = NULL; - char *cmd = NULL; - char *chan = NULL; - char *info = NULL; - ChannelInfo *ci = NULL; - - /* Get the last buffer anope recived */ - text = moduleGetLastBuffer(); - if (text) { - cmd = myStrGetToken(text, ' ', 0); - chan = myStrGetToken(text, ' ', 1); - info = myStrGetTokenRemainder(text, ' ', 2); - if (cmd && chan) { - if (strcasecmp(cmd, "ADD") == 0) { - if (info) { - if ((ci = cs_findchan(chan))) { - /* Add the module data to the channel */ - ci->Extend("os_info", sstrdup(info)); - me->NoticeLang(s_ChanServ, u, OCINFO_ADD_SUCCESS, chan); - /* ChanInfo */ - } else { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, - chan); - } - delete [] info; - } - } else if (strcasecmp(cmd, "DEL") == 0) { - if ((ci = cs_findchan(chan))) { - /* Del the module data from the channel */ - char *c; - if (ci->GetExt("os_info", c)) - { - delete [] c; - ci->Shrink("os_info"); - } - me->NoticeLang(s_ChanServ, u, OCINFO_DEL_SUCCESS, chan); - /* ChanInfo */ - } else { - notice_lang(s_ChanServ, u, CHAN_X_NOT_REGISTERED, - chan); - } - /* another syntax error! */ - } else { - me->NoticeLang(s_ChanServ, u, OCINFO_SYNTAX); - } - delete [] cmd; - delete [] chan; - /* Syntax error */ - } else if (cmd) { - me->NoticeLang(s_ChanServ, u, OCINFO_SYNTAX); - delete [] cmd; - /* Syntax error */ - } else { - me->NoticeLang(s_ChanServ, u, OCINFO_SYNTAX); - } - } - return MOD_CONT; -} - -/*************************************************************************/ - -/** - * Called after a user does a /msg nickserv info [nick] - * @param u The user who requested info - * @return MOD_CONT to continue processing commands or MOD_STOP to stop - **/ -int myNickInfo(User * u) -{ - char *text = NULL; - char *nick = NULL; - NickAlias *na = NULL; - - /* Only show our goodies to opers */ - if (is_oper(u)) { - /* Get the last buffer anope recived */ - text = moduleGetLastBuffer(); - if (text) { - nick = myStrGetToken(text, ' ', 0); - if (nick) { - /* ok we've found the user */ - if ((na = findnick(nick))) { - /* If we have any info on this user */ - char *c; - if (na->nc->GetExt("os_info", c)) - { - notice_user(s_NickServ, u, " OperInfo: %s", c); - } - } - delete [] nick; - } - } - } - return MOD_CONT; -} - -/** - * Called after a user does a /msg chanserv info chan - * @param u The user who requested info - * @return MOD_CONT to continue processing commands or MOD_STOP to stop - **/ -int myChanInfo(User * u) -{ - char *text = NULL; - char *chan = NULL; - ChannelInfo *ci = NULL; - - /* Only show our goodies to opers */ - if (is_oper(u)) { - /* Get the last buffer anope recived */ - text = moduleGetLastBuffer(); - if (text) { - chan = myStrGetToken(text, ' ', 0); - if (chan) { - if ((ci = cs_findchan(chan))) { - /* If we have any info on this channel */ - char *c; - if (ci->GetExt("os_info", c)) - { - notice_user(s_ChanServ, u, " OperInfo: %s", c); - } - } - delete [] chan; - } - } - } - return MOD_CONT; -} - /*************************************************************************/ /** @@ -591,30 +582,36 @@ int mLoadData() /* will _never_ be this big thanks to the 512 limit of a message */ char buffer[2000]; - if ((in = fopen(OSInfoDBName, "r")) == NULL) { + if (!(in = fopen(OSInfoDBName, "r"))) + { alog("os_info: WARNING: can not open the database file! (it might not exist, this is not fatal)"); ret = 1; - } else { - while (fgets(buffer, 1500, in)) { + } + else + { + while (fgets(buffer, 1500, in)) + { type = myStrGetToken(buffer, ' ', 0); name = myStrGetToken(buffer, ' ', 1); info = myStrGetTokenRemainder(buffer, ' ', 2); - if (type) { - if (name) { - if (info) { + if (type) + { + if (name) + { + if (info) + { len = strlen(info); /* Take the \n from the end of the line */ info[len - 1] = '\0'; - if (stricmp(type, "C") == 0) { + if (!stricmp(type, "C")) + { if ((ci = cs_findchan(name))) - { ci->Extend("os_info", strdup("info")); - } - } else if (stricmp(type, "N") == 0) { + } + else if (!stricmp(type, "N")) + { if ((na = findnick(name))) - { na->nc->Extend("os_info", strdup(info)); - } } delete [] info; } @@ -642,41 +639,44 @@ int mSaveData(int argc, char **argv) int ret = 0; FILE *out; - if (argc >= 1) { - if (!stricmp(argv[0], EVENT_START)) { - if ((out = fopen(OSInfoDBName, "w")) == NULL) { + if (argc >= 1) + { + if (!stricmp(argv[0], EVENT_START)) + { + if (!(out = fopen(OSInfoDBName, "w"))) + { alog("os_info: ERROR: can not open the database file!"); - ircdproto->SendGlobops(s_OperServ, - "os_info: ERROR: can not open the database file!"); + ircdproto->SendGlobops(s_OperServ, "os_info: ERROR: can not open the database file!"); ret = 1; - } else { - for (i = 0; i < 1024; i++) { - for (nc = nclists[i]; nc; nc = nc->next) { + } + else + { + for (i = 0; i < 1024; ++i) + { + for (nc = nclists[i]; nc; nc = nc->next) + { /* If we have any info on this user */ char *c; if (nc->GetExt("os_info", c)) - { fprintf(out, "N %s %s\n", nc->display, c); - } } } - - for (i = 0; i < 256; i++) { - for (ci = chanlists[i]; ci; ci = ci->next) { + for (i = 0; i < 256; ++i) + { + for (ci = chanlists[i]; ci; ci = ci->next) + { /* If we have any info on this channel */ char *c; if (ci->GetExt("os_info", c)) - { fprintf(out, "C %s %s\n", ci->name, c); - } } } fclose(out); } - } else { - ret = 0; } + else + ret = 0; } return ret; @@ -719,12 +719,12 @@ int mLoadConfig() int mEventReload(int argc, char **argv) { int ret = 0; - if (argc >= 1) { - if (!stricmp(argv[0], EVENT_START)) { + if (argc >= 1) + { + if (!stricmp(argv[0], EVENT_START)) + { alog("os_info: Reloading configuration directives..."); ret = mLoadConfig(); - } else { - /* Nothing for now */ } } @@ -736,43 +736,20 @@ int mEventReload(int argc, char **argv) /*************************************************************************/ -int mNickHelp(User * u) -{ - if (is_oper(u)) { - me->NoticeLang(s_NickServ, u, OINFO_HELP); - } else { - notice_lang(s_NickServ, u, NO_HELP_AVAILABLE, "OINFO"); - } - return MOD_CONT; -} - -int mChanHelp(User * u) -{ - if (is_oper(u)) { - me->NoticeLang(s_ChanServ, u, OCINFO_HELP); - } else { - notice_lang(s_ChanServ, u, NO_HELP_AVAILABLE, "OINFO"); - } - return MOD_CONT; -} - /* This help will be added to the main NickServ list */ -void mMainNickHelp(User * u) +void mMainNickHelp(User *u) { - if (is_oper(u)) { + if (is_oper(u)) me->NoticeLang(s_NickServ, u, OINFO_HELP_CMD); - } } -/* This help will be added to the main NickServ list */ -void mMainChanHelp(User * u) +/* This help will be added to the main ChanServ list */ +void mMainChanHelp(User *u) { - if (is_oper(u)) { + if (is_oper(u)) me->NoticeLang(s_ChanServ, u, OCINFO_HELP_CMD); - } } /*************************************************************************/ - MODULE_INIT("os_info", OSInfo) diff --git a/src/news.c b/src/news.c index aac04991f..072d90f71 100644 --- a/src/news.c +++ b/src/news.c @@ -303,126 +303,6 @@ void display_news(User * u, int16 type) /*************************************************************************/ /***************************** News editing ******************************/ /*************************************************************************/ -/* Declared in extern.h */ -int do_logonnews(User * u) -{ - do_news(u, NEWS_LOGON); - return MOD_CONT; -} - - -/* Declared in extern.h */ -int do_opernews(User * u) -{ - do_news(u, NEWS_OPER); - return MOD_CONT; -} - -/* Declared in extern.h */ -int do_randomnews(User * u) -{ - do_news(u, NEWS_RANDOM); - return MOD_CONT; -} - -/*************************************************************************/ - -/* Main news command handling routine. */ -void do_news(User * u, short type) -{ - int is_servadmin = is_services_admin(u); - const char *cmd = strtok(NULL, " "); - const char *type_name; - int *msgs; - - msgs = findmsgs(type, &type_name); - if (!msgs) { - alog("news: Invalid type to do_news()"); - return; - } - - if (!cmd) - cmd = ""; - - if (stricmp(cmd, "LIST") == 0) { - do_news_list(u, type, msgs); - } else if (stricmp(cmd, "ADD") == 0) { - if (is_servadmin) - do_news_add(u, type, msgs, type_name); - else - notice_lang(s_OperServ, u, PERMISSION_DENIED); - - } else if (stricmp(cmd, "DEL") == 0) { - if (is_servadmin) - do_news_del(u, type, msgs, type_name); - else - notice_lang(s_OperServ, u, PERMISSION_DENIED); - - } else { - char buf[32]; - snprintf(buf, sizeof(buf), "%sNEWS", type_name); - syntax_error(s_OperServ, u, buf, msgs[MSG_SYNTAX]); - } -} - -/*************************************************************************/ - -/* Handle a {LOGON,OPER}NEWS LIST command. */ - -static void do_news_list(User * u, int16 type, int *msgs) -{ - int i, count = 0; - char timebuf[64]; - struct tm *tm; - - for (i = 0; i < nnews; i++) { - if (news[i].type == type) { - if (count == 0) - notice_lang(s_OperServ, u, msgs[MSG_LIST_HEADER]); - tm = localtime(&news[i].time); - strftime_lang(timebuf, sizeof(timebuf), - u, STRFTIME_DATE_TIME_FORMAT, tm); - notice_lang(s_OperServ, u, msgs[MSG_LIST_ENTRY], - news[i].num, timebuf, - *news[i].who ? news[i].who : "<unknown>", - news[i].text); - count++; - } - } - if (count == 0) - notice_lang(s_OperServ, u, msgs[MSG_LIST_NONE]); - else { - notice_lang(s_OperServ, u, END_OF_ANY_LIST, "News"); - } -} - -/*************************************************************************/ - -/* Handle a {LOGON,OPER}NEWS ADD command. */ - -static void do_news_add(User * u, int16 type, int *msgs, - const char *type_name) -{ - char *text = strtok(NULL, ""); - int n; - - if (!text) { - char buf[32]; - snprintf(buf, sizeof(buf), "%sNEWS", type_name); - syntax_error(s_OperServ, u, buf, msgs[MSG_ADD_SYNTAX]); - } else { - if (readonly) { - notice_lang(s_OperServ, u, READ_ONLY_MODE); - return; - } - n = add_newsitem(u, text, type); - if (n < 0) - notice_lang(s_OperServ, u, msgs[MSG_ADD_FULL]); - else - notice_lang(s_OperServ, u, msgs[MSG_ADDED], n); - } -} - /* Actually add a news item. Return the number assigned to the item, or -1 * if the news list is full (32767 items). @@ -460,44 +340,6 @@ static int add_newsitem(User * u, const char *text, short type) /*************************************************************************/ -/* Handle a {LOGON,OPER}NEWS DEL command. */ - -static void do_news_del(User * u, int16 type, int *msgs, - const char *type_name) -{ - char *text = strtok(NULL, " "); - int i, num; - - if (!text) { - char buf[32]; - snprintf(buf, sizeof(buf), "%sNEWS", type_name); - syntax_error(s_OperServ, u, buf, msgs[MSG_DEL_SYNTAX]); - } else { - if (readonly) { - notice_lang(s_OperServ, u, READ_ONLY_MODE); - return; - } - if (stricmp(text, "ALL") != 0) { - num = atoi(text); - if (num > 0 && del_newsitem(num, type)) { - notice_lang(s_OperServ, u, msgs[MSG_DELETED], num); - /* Reset the order - #0000397 */ - for (i = 0; i < nnews; i++) { - if ((news[i].type == type) && (news[i].num > num)) - news[i].num--; - } - } else - notice_lang(s_OperServ, u, msgs[MSG_DEL_NOT_FOUND], num); - } else { - if (del_newsitem(0, type)) - notice_lang(s_OperServ, u, msgs[MSG_DELETED_ALL]); - else - notice_lang(s_OperServ, u, msgs[MSG_DEL_NONE]); - } - } -} - - /* Actually delete a news item. If `num' is 0, delete all news items of * the given type. Returns the number of items deleted. */ diff --git a/src/nickserv.c b/src/nickserv.c index 428f0d242..0bf328151 100644 --- a/src/nickserv.c +++ b/src/nickserv.c @@ -529,9 +529,9 @@ int validate_user(User * u) na->last_seen = time(NULL); if (na->last_usermask) delete [] na->last_usermask; - na->last_usermask = new char[strlen(common_get_vident(u)) + strlen(common_get_vhost(u)) + 2]; - sprintf(na->last_usermask, "%s@%s", common_get_vident(u), - common_get_vhost(u)); + na->last_usermask = new char[u->GetIdent().length() + u->GetDisplayedHost().length() + 2]; + sprintf(na->last_usermask, "%s@%s", u->GetIdent().c_str(), + u->GetDisplayedHost().c_str()); if (na->last_realname) delete [] na->last_realname; na->last_realname = sstrdup(u->realname); @@ -795,12 +795,12 @@ int is_on_access(User * u, NickCore * nc) if (nc->accesscount == 0) return 0; - buf = new char[strlen(u->username) + strlen(u->host) + 2]; - sprintf(buf, "%s@%s", u->username, u->host); + buf = new char[u->GetIdent().length() + strlen(u->host) + 2]; + sprintf(buf, "%s@%s", u->GetIdent().c_str(), u->host); if (ircd->vhost) { if (u->vhost) { - buf2 = new char[strlen(u->username) + strlen(u->vhost) + 2]; - sprintf(buf2, "%s@%s", u->username, u->vhost); + buf2 = new char[u->GetIdent().length() + strlen(u->vhost) + 2]; + sprintf(buf2, "%s@%s", u->GetIdent().c_str(), u->vhost); } } diff --git a/src/process.c b/src/process.c index 0be36e09a..638f1d683 100644 --- a/src/process.c +++ b/src/process.c @@ -356,13 +356,7 @@ void process() } if (ac >= 1) { - if (nickIsServices(av[0], 1)) { - mod_current_buffer = - (ac > 1 ? sstrdup(av[1]) : sstrdup(av[0])); - } else { - mod_current_buffer = - (ac > 1 ? sstrdup(av[1]) : sstrdup(av[0])); - } + mod_current_buffer = (ac > 1 ? sstrdup(av[1]) : sstrdup(av[0])); } else { mod_current_buffer = NULL; } diff --git a/src/protocol/bahamut.c b/src/protocol/bahamut.c index 215000249..f5a62116a 100644 --- a/src/protocol/bahamut.c +++ b/src/protocol/bahamut.c @@ -165,7 +165,6 @@ IRCDCAPAB myIrcdcap[] = { 0, /* VHOST */ 0, /* SSJ3 */ 0, /* NICK2 */ - 0, /* UMODE2 */ 0, /* VL */ 0, /* TLKEXT */ 0, /* DODKEY */ diff --git a/src/protocol/inspircd11.c b/src/protocol/inspircd11.c index 15decaef0..5ae4257aa 100644 --- a/src/protocol/inspircd11.c +++ b/src/protocol/inspircd11.c @@ -174,7 +174,6 @@ IRCDCAPAB myIrcdcap[] = { 0, /* VHOST */ CAPAB_SSJ3, /* SSJ3 */ CAPAB_NICK2, /* NICK2 */ - 0, /* UMODE2 */ CAPAB_VL, /* VL */ CAPAB_TLKEXT, /* TLKEXT */ 0, /* DODKEY */ diff --git a/src/protocol/inspircd12.cpp b/src/protocol/inspircd12.cpp index ec0646da9..350ac8ee2 100644 --- a/src/protocol/inspircd12.cpp +++ b/src/protocol/inspircd12.cpp @@ -23,6 +23,7 @@ #define UMODE_r 0x00000010 #define UMODE_w 0x00000020 #define UMODE_A 0x00000040 +#define UMODE_k 0x00000080 #define UMODE_g 0x80000000 #define UMODE_x 0x40000000 @@ -174,7 +175,6 @@ IRCDCAPAB myIrcdcap[] = { 0, /* VHOST */ CAPAB_SSJ3, /* SSJ3 */ CAPAB_NICK2, /* NICK2 */ - 0, /* UMODE2 */ CAPAB_VL, /* VL */ CAPAB_TLKEXT, /* TLKEXT */ 0, /* DODKEY */ @@ -197,7 +197,7 @@ unsigned long umodes[128] = { 0, 0, 0, 0, 0, 0, UMODE_a, 0, 0, 0, 0, 0, UMODE_g, - UMODE_h, UMODE_i, 0, 0, 0, 0, 0, UMODE_o, + UMODE_h, UMODE_i, 0, UMODE_k, 0, 0, 0, UMODE_o, 0, 0, UMODE_r, 0, 0, 0, 0, UMODE_w, UMODE_x, @@ -498,8 +498,7 @@ class InspIRCdProto : public IRCDProto void SendVhostDel(User *u) { - inspircd_cmd_chghost(u->uid, (u->mode & umodes[static_cast<int>('x')]) ? u->chost.c_str() : u->host); - notice_lang(s_HostServ, u, HOST_OFF); + inspircd_cmd_chghost(u->GetUID().c_str(), (u->mode & umodes[static_cast<int>('x')]) ? u->chost.c_str() : u->host); } void SendAkill(const char *user, const char *host, const char *who, time_t when, time_t expires, const char *reason) @@ -511,17 +510,22 @@ class InspIRCdProto : public IRCDProto send_cmd(ServerName, "ADDLINE G %s@%s %s %ld %ld :%s", user, host, who, static_cast<long int>(when), static_cast<long int>(timeleft), reason); } + void CanSVSKill(const char *source, const char *user, const char *buf) + { + return !user->mode & UMODE_k; + } + void SendSVSKillInternal(const char *source, const char *user, const char *buf) { BotInfo *bi = findbot(source); User *u = finduser(user); - send_cmd(bi ? bi->uid : TS6SID, "KILL %s :%s", u ? u->uid : user, buf); + send_cmd(bi ? bi->uid : TS6SID, "KILL %s :%s", u ? u->GetUID().c_str(): user, buf); } void SendSVSMode(User *u, int ac, const char **av) { BotInfo *bi = findbot(s_NickServ); - send_cmd(bi->uid, "MODE %s %s", u->uid, merge_args(ac, av)); + send_cmd(bi->uid, "MODE %s %s", u->GetUID().c_str(), merge_args(ac, av)); } void SendNumericInternal(const char *source, int numeric, const char *dest, const char *buf) @@ -545,13 +549,20 @@ class InspIRCdProto : public IRCDProto send_cmd(ServerName, "UID %s %ld %s %s %s %s 0.0.0.0 %ld +%s :%s", uid, static_cast<long>(time(NULL)), nick, host, host, user, static_cast<long>(time(NULL)), modes, real); } + bool CanKick(BotInfo *source, const char *chan, const char *user, const char *buf) + { + return !user->mode & UMODE_k; + } + void SendKickInternal(BotInfo *source, const char *chan, const char *user, const char *buf) { User *u = finduser(user); if (buf) - send_cmd(source->uid, "KICK %s %s :%s", chan, u ? u->uid : user, buf); + send_cmd(source->uid, "KICK %s %s :%s", chan, u->GetUID().c_str() +, buf); else - send_cmd(source->uid, "KICK %s %s :%s", chan, u ? u->uid : user, user); + send_cmd(source->uid, "KICK %s %s :%s", chan, u->GetUID().c_str() +, user); } void SendNoticeChanopsInternal(BotInfo *source, const char *dest, const char *buf) @@ -669,14 +680,14 @@ class InspIRCdProto : public IRCDProto { User *u = finduser(nick); BotInfo *bi = findbot(source); - send_cmd(bi->uid, "SVSJOIN %s %s", u->uid, chan); + send_cmd(bi->uid, "SVSJOIN %s %s", u->GetUID().c_str(), chan); } void SendSVSPart(const char *source, const char *nick, const char *chan) { User *u = finduser(nick); BotInfo *bi = findbot(source); - send_cmd(bi->uid, "SVSPART %s %s", u->uid, chan); + send_cmd(bi->uid, "SVSPART %s %s", u->GetUID().c_str(), chan); } void SendEOB() diff --git a/src/protocol/ratbox.c b/src/protocol/ratbox.c index fc5211e30..f99a0bd0e 100644 --- a/src/protocol/ratbox.c +++ b/src/protocol/ratbox.c @@ -150,7 +150,6 @@ IRCDCAPAB myIrcdcap[] = { 0, /* VHOST */ 0, /* SSJ3 */ 0, /* NICK2 */ - 0, /* UMODE2 */ 0, /* VL */ 0, /* TLKEXT */ 0, /* DODKEY */ @@ -577,7 +576,7 @@ class RatboxProto : public IRCDTS6Proto { BotInfo *bi = findbot(source); User *u = find_byuid(user); - send_cmd(bi ? bi->uid : source, "KILL %s :%s", u ? u->uid : user, buf); + send_cmd(bi ? bi->uid : source, "KILL %s :%s", u ? u->GetUID().c_str(): user, buf); } void SendSVSMode(User *u, int ac, const char **av) @@ -635,8 +634,10 @@ class RatboxProto : public IRCDTS6Proto void SendKickInternal(BotInfo *bi, const char *chan, const char *user, const char *buf) { User *u = finduser(user); - if (buf) send_cmd(bi->uid, "KICK %s %s :%s", chan, u ? u->uid : user, buf); - else send_cmd(bi->uid, "KICK %s %s", chan, u ? u->uid : user); + if (buf) send_cmd(bi->uid, "KICK %s %s :%s", chan, u ? u->GetUID().c_str() +: user, buf); + else send_cmd(bi->uid, "KICK %s %s", chan, u ? u->GetUID().c_str() +: user); } void SendNoticeChanopsInternal(BotInfo *source, const char *dest, const char *buf) @@ -667,7 +668,7 @@ class RatboxProto : public IRCDTS6Proto void SendInvite(BotInfo *source, const char *chan, const char *nick) { User *u = finduser(nick); - send_cmd(source->uid, "INVITE %s %s", u ? u->uid : nick, chan); + send_cmd(source->uid, "INVITE %s %s", u ? u->GetUID().c_str(): nick, chan); } int IsNickValid(const char *nick) diff --git a/src/protocol/unreal32.c b/src/protocol/unreal32.c index d28df8c01..02721c09f 100644 --- a/src/protocol/unreal32.c +++ b/src/protocol/unreal32.c @@ -187,7 +187,6 @@ IRCDCAPAB myIrcdcap[] = { 0, /* VHOST */ CAPAB_SSJ3, /* SSJ3 */ CAPAB_NICK2, /* NICK2 */ - CAPAB_UMODE2, /* UMODE2 */ CAPAB_VL, /* VL */ CAPAB_TLKEXT, /* TLKEXT */ 0, /* DODKEY */ @@ -664,6 +663,11 @@ class UnrealIRCdProto : public IRCDProto SendSQLine(nick, "Reserved for services"); } + bool CanKick(BotInfo *source, const char *chan, const char *user, const char *buf) + { + return !user->mode & MODE_q; + } + void SendKickInternal(BotInfo *source, const char *chan, const char *user, const char *buf) { if (buf) send_cmd(source->nick, "H %s %s :%s", chan, user, buf); @@ -1059,7 +1063,10 @@ int anope_event_umode2(const char *source, int ac, const char **av) if (ac < 1) return MOD_CONT; - do_umode2(source, ac, av); + const char *newav[4]; + newav[0] = source; + newav[1] = av[0]; + do_umode(source, ac, av); return MOD_CONT; } diff --git a/src/sessions.c b/src/sessions.c index 0563156cf..94137b073 100644 --- a/src/sessions.c +++ b/src/sessions.c @@ -99,82 +99,6 @@ void get_exception_stats(long *nrec, long *memuse) } /*************************************************************************/ -/************************* Session List Display **************************/ -/*************************************************************************/ - -/* Syntax: SESSION LIST threshold - * Lists all sessions with atleast threshold clients. - * The threshold value must be greater than 1. This is to prevent - * accidental listing of the large number of single client sessions. - * - * Syntax: SESSION VIEW host - * Displays detailed session information about the supplied host. - */ - -int do_session(User * u) -{ - Session *session; - Exception *exception; - char *cmd = strtok(NULL, " "); - char *param1 = strtok(NULL, " "); - int mincount; - int i; - - if (!LimitSessions) { - notice_lang(s_OperServ, u, OPER_SESSION_DISABLED); - return MOD_CONT; - } - - if (!cmd) - cmd = ""; - - if (stricmp(cmd, "LIST") == 0) { - if (!param1) { - syntax_error(s_OperServ, u, "SESSION", - OPER_SESSION_LIST_SYNTAX); - - } else if ((mincount = atoi(param1)) <= 1) { - notice_lang(s_OperServ, u, OPER_SESSION_INVALID_THRESHOLD); - - } else { - notice_lang(s_OperServ, u, OPER_SESSION_LIST_HEADER, mincount); - notice_lang(s_OperServ, u, OPER_SESSION_LIST_COLHEAD); - for (i = 0; i < 1024; i++) { - for (session = sessionlist[i]; session; - session = session->next) { - if (session->count >= mincount) - notice_lang(s_OperServ, u, - OPER_SESSION_LIST_FORMAT, - session->count, session->host); - } - } - } - } else if (stricmp(cmd, "VIEW") == 0) { - if (!param1) { - syntax_error(s_OperServ, u, "SESSION", - OPER_SESSION_VIEW_SYNTAX); - - } else { - session = findsession(param1); - if (!session) { - notice_lang(s_OperServ, u, OPER_SESSION_NOT_FOUND, param1); - } else { - exception = find_host_exception(param1); - - notice_lang(s_OperServ, u, OPER_SESSION_VIEW_FORMAT, - param1, session->count, - exception ? exception-> - limit : DefSessionLimit); - } - } - - } else { - syntax_error(s_OperServ, u, "SESSION", OPER_SESSION_SYNTAX); - } - return MOD_CONT; -} - -/*************************************************************************/ /********************* Internal Session Functions ************************/ /*************************************************************************/ @@ -615,232 +539,3 @@ static int exception_view_callback(User * u, int num, va_list args) } /*************************************************************************/ - -/* Syntax: EXCEPTION ADD [+expiry] mask limit reason - * Adds mask to the exception list with limit as the maximum session - * limit and +expiry as an optional expiry time. - * - * Syntax: EXCEPTION DEL mask - * Deletes the first exception that matches mask exactly. - * - * Syntax: EXCEPTION LIST [mask] - * Lists all exceptions or those matching mask. - * - * Syntax: EXCEPTION VIEW [mask] - * Displays detailed information about each exception or those matching - * mask. - * - * Syntax: EXCEPTION MOVE num position - * Moves the exception at position num to position. - */ - -int do_exception(User * u) -{ - char *cmd = strtok(NULL, " "); - char *mask, *reason, *expiry, *limitstr; - int limit, expires; - int i; - int x; - - if (!LimitSessions) { - notice_lang(s_OperServ, u, OPER_EXCEPTION_DISABLED); - return MOD_CONT; - } - - if (!cmd) - cmd = ""; - - if (stricmp(cmd, "ADD") == 0) { - if (nexceptions >= 32767) { - notice_lang(s_OperServ, u, OPER_EXCEPTION_TOO_MANY); - return MOD_CONT; - } - - mask = strtok(NULL, " "); - if (mask && *mask == '+') { - expiry = mask; - mask = strtok(NULL, " "); - } else { - expiry = NULL; - } - limitstr = strtok(NULL, " "); - reason = strtok(NULL, ""); - - if (!reason) { - syntax_error(s_OperServ, u, "EXCEPTION", - OPER_EXCEPTION_ADD_SYNTAX); - return MOD_CONT; - } - - expires = expiry ? dotime(expiry) : ExceptionExpiry; - if (expires < 0) { - notice_lang(s_OperServ, u, BAD_EXPIRY_TIME); - return MOD_CONT; - } else if (expires > 0) { - expires += time(NULL); - } - - limit = (limitstr && isdigit(*limitstr)) ? atoi(limitstr) : -1; - - if (limit < 0 || limit > MaxSessionLimit) { - notice_lang(s_OperServ, u, OPER_EXCEPTION_INVALID_LIMIT, - MaxSessionLimit); - return MOD_CONT; - - } else { - if (strchr(mask, '!') || strchr(mask, '@')) { - notice_lang(s_OperServ, u, - OPER_EXCEPTION_INVALID_HOSTMASK); - return MOD_CONT; - } - - x = exception_add(u, mask, limit, reason, u->nick, expires); - - if (x == 1) { - notice_lang(s_OperServ, u, OPER_EXCEPTION_ADDED, mask, - limit); - } - - if (readonly) - notice_lang(s_OperServ, u, READ_ONLY_MODE); - } - } else if (stricmp(cmd, "DEL") == 0) { - mask = strtok(NULL, " "); - - if (!mask) { - syntax_error(s_OperServ, u, "EXCEPTION", - OPER_EXCEPTION_DEL_SYNTAX); - return MOD_CONT; - } - - if (isdigit(*mask) && strspn(mask, "1234567890,-") == strlen(mask)) { - int count, deleted, last = -1; - deleted = - process_numlist(mask, &count, exception_del_callback, u, - &last); - if (!deleted) { - if (count == 1) { - notice_lang(s_OperServ, u, - OPER_EXCEPTION_NO_SUCH_ENTRY, last); - } else { - notice_lang(s_OperServ, u, OPER_EXCEPTION_NO_MATCH); - } - } else if (deleted == 1) { - notice_lang(s_OperServ, u, OPER_EXCEPTION_DELETED_ONE); - } else { - notice_lang(s_OperServ, u, OPER_EXCEPTION_DELETED_SEVERAL, - deleted); - } - } else { - int deleted = 0; - - for (i = 0; i < nexceptions; i++) { - if (stricmp(mask, exceptions[i].mask) == 0) { - exception_del(i); - notice_lang(s_OperServ, u, OPER_EXCEPTION_DELETED, - mask); - deleted = 1; - break; - } - } - if (!deleted && i == nexceptions) - notice_lang(s_OperServ, u, OPER_EXCEPTION_NOT_FOUND, mask); - } - - /* Renumber the exception list. I don't believe in having holes in - * lists - it makes code more complex, harder to debug and we end up - * with huge index numbers. Imho, fixed numbering is only beneficial - * when one doesn't have range capable manipulation. -TheShadow */ - - for (i = 0; i < nexceptions; i++) - exceptions[i].num = i; - - if (readonly) - notice_lang(s_OperServ, u, READ_ONLY_MODE); - - } else if (stricmp(cmd, "MOVE") == 0) { - Exception *exception; - char *n1str = strtok(NULL, " "); /* From position */ - char *n2str = strtok(NULL, " "); /* To position */ - int n1, n2; - - if (!n2str) { - syntax_error(s_OperServ, u, "EXCEPTION", - OPER_EXCEPTION_MOVE_SYNTAX); - return MOD_CONT; - } - - n1 = atoi(n1str) - 1; - n2 = atoi(n2str) - 1; - - if ((n1 >= 0 && n1 < nexceptions) && (n2 >= 0 && n2 < nexceptions) - && (n1 != n2)) { - exception = static_cast<Exception *>(smalloc(sizeof(Exception))); - memcpy(exception, &exceptions[n1], sizeof(Exception)); - - if (n1 < n2) { - /* Shift upwards */ - memmove(&exceptions[n1], &exceptions[n1 + 1], - sizeof(Exception) * (n2 - n1)); - memmove(&exceptions[n2], exception, sizeof(Exception)); - } else { - /* Shift downwards */ - memmove(&exceptions[n2 + 1], &exceptions[n2], - sizeof(Exception) * (n1 - n2)); - memmove(&exceptions[n2], exception, sizeof(Exception)); - } - - free(exception); - - notice_lang(s_OperServ, u, OPER_EXCEPTION_MOVED, - exceptions[n1].mask, n1 + 1, n2 + 1); - - /* Renumber the exception list. See the DEL block above for why. */ - for (i = 0; i < nexceptions; i++) - exceptions[i].num = i; - - if (readonly) - notice_lang(s_OperServ, u, READ_ONLY_MODE); - } else { - syntax_error(s_OperServ, u, "EXCEPTION", - OPER_EXCEPTION_MOVE_SYNTAX); - } - } else if (stricmp(cmd, "LIST") == 0) { - int sent_header = 0; - expire_exceptions(); - mask = strtok(NULL, " "); - if (mask && strspn(mask, "1234567890,-") == strlen(mask)) { - process_numlist(mask, NULL, exception_list_callback, u, - &sent_header); - } else { - for (i = 0; i < nexceptions; i++) { - if (!mask || match_wild_nocase(mask, exceptions[i].mask)) - exception_list(u, i, &sent_header); - } - } - if (!sent_header) - notice_lang(s_OperServ, u, OPER_EXCEPTION_NO_MATCH); - - } else if (stricmp(cmd, "VIEW") == 0) { - int sent_header = 0; - expire_exceptions(); - mask = strtok(NULL, " "); - if (mask && strspn(mask, "1234567890,-") == strlen(mask)) { - process_numlist(mask, NULL, exception_view_callback, u, - &sent_header); - } else { - for (i = 0; i < nexceptions; i++) { - if (!mask || match_wild_nocase(mask, exceptions[i].mask)) - exception_view(u, i, &sent_header); - } - } - if (!sent_header) - notice_lang(s_OperServ, u, OPER_EXCEPTION_NO_MATCH); - - } else { - syntax_error(s_OperServ, u, "EXCEPTION", OPER_EXCEPTION_SYNTAX); - } - return MOD_CONT; -} - -/*************************************************************************/ diff --git a/src/users.c b/src/users.c index 106f15fb7..35d4b6635 100644 --- a/src/users.c +++ b/src/users.c @@ -26,7 +26,7 @@ time_t maxusertime; /*************************************************************************/ /*************************************************************************/ -User::User(const std::string &snick) +User::User(const std::string &snick, const std::string &suid) { User **list; // XXX: we could do well to steal CoreException from insp @@ -38,7 +38,7 @@ User::User(const std::string &snick) /* we used to do this by calloc, no more. */ this->next = NULL; this->prev = NULL; - username = host = hostip = vhost = vident = realname = nickTrack = uid = NULL; + host = hostip = vhost = realname = nickTrack = NULL; server = NULL; na = NULL; chans = NULL; @@ -46,6 +46,7 @@ User::User(const std::string &snick) invalid_pw_count = timestamp = my_signon = svid = mode = invalid_pw_time = lastmemosend = lastnickreg = lastmail = 0; strscpy(this->nick, snick.c_str(), NICKMAX); + this->uid = suid; list = &userlist[HASH(this->nick)]; this->next = *list; @@ -133,21 +134,68 @@ void User::SetDisplayedHost(const std::string &shost) update_host(this); } -void User::SetIdent(const std::string &ident) + +const std::string User::GetDisplayedHost() const +{ + if (ircd->vhostmode && (this->mode & ircd->vhostmode)) + return this->vhost; + else if (ircd->vhost && this->vhost) + return this->vhost; + else + return this->host; +} + + + + +const std::string &User::GetUID() const { - if (ident.empty()) - throw "empty ident in SetIdent"; + return this->uid; +} + + - if (this->vident) - delete [] this->vident; - this->vident = sstrdup(ident.c_str()); + + +void User::SetVIdent(const std::string &sident) +{ + this->vident = sident; if (debug) - alog("debug: %s changed ident to %s", this->nick, username); + alog("debug: %s changed ident to %s", this->nick, sident.c_str()); update_host(this); } +const std::string &User::GetVIdent() const +{ + if (ircd->vhostmode && (this->mode & ircd->vhostmode)) + return this->vident; + else if (ircd->vident && !this->vident.empty()) + return this->vident; + else + return this->ident; +} + +void User::SetIdent(const std::string &sident) +{ + this->ident = sident; + + if (debug) + alog("debug: %s changed real ident to %s", this->nick, sident.c_str()); + + update_host(this); +} + +const std::string &User::GetIdent() const +{ + return this->ident; +} + + + + + void User::SetRealname(const std::string &srealname) { if (srealname.empty()) @@ -182,13 +230,13 @@ User::~User() if (ircd->vhost) { alog("LOGUSERS: %s (%s@%s => %s) (%s) left the network (%s).", - this->nick, this->username, this->host, + this->nick, this->GetIdent().c_str(), this->host, (this->vhost ? this->vhost : "(none)"), srealname, this->server->name); } else { alog("LOGUSERS: %s (%s@%s) (%s) left the network (%s).", - this->nick, this->username, this->host, + this->nick, this->GetIdent().c_str(), this->host, srealname, this->server->name); } @@ -208,15 +256,10 @@ User::~User() if (debug >= 2) alog("debug: User::~User(): free user data"); - delete [] this->username; delete [] this->host; if (this->vhost) delete [] this->vhost; - if (this->vident) - delete [] this->vident; - if (this->uid) - delete [] this->uid; if (this->realname) delete [] this->realname; @@ -321,9 +364,9 @@ void update_host(User * user) if (user->na->last_usermask) delete [] user->na->last_usermask; - user->na->last_usermask = new char[strlen(common_get_vident(user)) + strlen(common_get_vhost(user)) + 2]; - sprintf(user->na->last_usermask, "%s@%s", common_get_vident(user), - common_get_vhost(user)); + user->na->last_usermask = new char[user->GetIdent().length() + user->GetDisplayedHost().length() + 2]; + sprintf(user->na->last_usermask, "%s@%s", user->GetIdent().c_str(), + user->GetDisplayedHost().c_str()); } } @@ -345,8 +388,6 @@ void get_user_stats(long *nusers, long *memuse) for (user = userlist[i]; user; user = user->next) { count++; mem += sizeof(*user); - if (user->username) - mem += strlen(user->username) + 1; if (user->host) mem += strlen(user->host) + 1; if (ircd->vhost) { @@ -430,10 +471,8 @@ User *find_byuid(const char *uid) u = first_uid(); while (u) { next = next_uid(); - if (u->uid) { - if (!stricmp(uid, u->uid)) { - return u; - } + if (u->GetUID() == uid) { + return u; } u = next; } @@ -453,7 +492,7 @@ User *first_uid() if (debug >= 2) { alog("debug: first_uid() returning %s %s", current_uid ? current_uid->nick : "NULL (end of list)", - current_uid ? current_uid->uid : ""); + current_uid ? current_uid->GetUID().c_str() : ""); } return current_uid; } @@ -469,7 +508,7 @@ User *next_uid() if (debug >= 2) { alog("debug: next_uid() returning %s %s", current_uid ? current_uid->nick : "NULL (end of list)", - current_uid ? current_uid->uid : ""); + current_uid ? current_uid->GetUID().c_str() : ""); } return current_uid; } @@ -562,18 +601,14 @@ User *do_nick(const char *source, const char *nick, const char *username, const * as such, create a user_struct, and if the client is removed, we'll delete it again when the QUIT notice * comes in from the ircd. **/ - if (check_akill(nick, username, host, vhost, ipbuf)) { -/* return NULL; */ - } + check_akill(nick, username, host, vhost, ipbuf); -/** - * DefCon AKILL system, if we want to akill all connecting user's here's where to do it - * then force check_akill again on them... - **/ - /* don't akill on netmerges -Certus */ - /* don't akill clients introduced by ulines. -Viper */ - if (is_sync(findserver(servlist, server)) - && checkDefCon(DEFCON_AKILL_NEW_CLIENTS) && !is_ulined(server)) { + /** + * DefCon AKILL system, if we want to akill all connecting user's here's where to do it + * then force check_akill again on them... + */ + if (is_sync(findserver(servlist, server)) && checkDefCon(DEFCON_AKILL_NEW_CLIENTS) && !is_ulined(server)) + { strncpy(mask, "*@", 3); strncat(mask, host, HOSTMAX); alog("DEFCON: adding akill for %s", mask); @@ -581,48 +616,35 @@ User *do_nick(const char *source, const char *nick, const char *username, const time(NULL) + DefConAKILL, DefConAkillReason ? DefConAkillReason : "DEFCON AKILL"); - if (check_akill(nick, username, host, vhost, ipbuf)) { -/* return NULL; */ - } + check_akill(nick, username, host, vhost, ipbuf); } + + /* As with akill checks earlier, we can't not add the user record, as the user may be exempt from bans. + * Instead, we'll just wait for the IRCd to tell us they are gone. + */ + if (ircd->sgline) + check_sgline(nick, realname); - /* SGLINE */ - if (ircd->sgline) { - if (check_sgline(nick, realname)) - return NULL; - } + if (ircd->sqline) + check_sqline(nick, 0); - /* SQLINE */ - if (ircd->sqline) { - if (check_sqline(nick, 0)) - return NULL; - } + if (ircd->szline && ircd->nickip) + check_szline(nick, ipbuf); - /* SZLINE */ - if (ircd->szline && ircd->nickip) { - if (check_szline(nick, ipbuf)) - return NULL; - } /* Now check for session limits */ - if (LimitSessions && !is_ulined(server) - && !add_session(nick, host, ipbuf)) - return NULL; + if (LimitSessions && !is_ulined(server)) + add_session(nick, host, ipbuf); /* Allocate User structure and fill it in. */ - user = new User(nick); - user->username = sstrdup(username); + user = new User(nick, uid ? uid : ""); + user->SetIdent(username); user->host = sstrdup(host); user->server = findserver(servlist, server); user->realname = sstrdup(realname); user->timestamp = ts; user->my_signon = time(NULL); user->vhost = vhost ? sstrdup(vhost) : sstrdup(host); - if (uid) { - user->uid = sstrdup(uid); /* p10/ts6 stuff */ - } else { - user->uid = NULL; - } - user->vident = sstrdup(username); + user->SetVIdent(username); /* We now store the user's ip in the user_ struct, * because we will use it in serveral places -- DrStein */ if (ircd->nickip) { @@ -677,10 +699,10 @@ User *do_nick(const char *source, const char *nick, const char *username, const if (LogUsers) { logrealname = normalizeBuffer(user->realname); if (ircd->vhost) { - alog("LOGUSERS: %s (%s@%s => %s) (%s) changed nick to %s (%s).", user->nick, user->username, user->host, (user->vhost ? user->vhost : "(none)"), logrealname, nick, user->server->name); + alog("LOGUSERS: %s (%s@%s => %s) (%s) changed nick to %s (%s).", user->nick, user->GetIdent().c_str(), user->host, (user->vhost ? user->vhost : "(none)"), logrealname, nick, user->server->name); } else { alog("LOGUSERS: %s (%s@%s) (%s) changed nick to %s (%s).", - user->nick, user->username, user->host, logrealname, + user->nick, user->GetIdent().c_str(), user->host, logrealname, nick, user->server->name); } if (logrealname) { @@ -744,16 +766,16 @@ User *do_nick(const char *source, const char *nick, const char *username, const if (user->na->last_usermask) delete [] user->na->last_usermask; - user->na->last_usermask = new char[strlen(common_get_vident(user)) + strlen(common_get_vhost(user)) + 2]; + user->na->last_usermask = new char[user->GetIdent().length() + user->GetDisplayedHost().length() + 2]; sprintf(user->na->last_usermask, "%s@%s", - common_get_vident(user), common_get_vhost(user)); + user->GetIdent().c_str(), user->GetDisplayedHost().c_str()); snprintf(tsbuf, sizeof(tsbuf), "%lu", static_cast<unsigned long>(user->timestamp)); ircdproto->SendSVID2(user, tsbuf); alog("%s: %s!%s@%s automatically identified for nick %s", - s_NickServ, user->nick, user->username, + s_NickServ, user->nick, user->GetIdent().c_str(), user->host, user->nick); } } @@ -792,24 +814,6 @@ void do_umode(const char *source, int ac, const char **av) ircdproto->ProcessUsermodes(user, ac - 1, &av[1]); } -/* Handle a UMODE2 command for a user. - * av[0] = modes - */ - -void do_umode2(const char *source, int ac, const char **av) -{ - User *user; - - user = finduser(source); - if (!user) { - alog("user: MODE %s for nonexistent nick %s: %s", av[0], source, - merge_args(ac, av)); - return; - } - - ircdproto->ProcessUsermodes(user, ac, &av[0]); -} - /*************************************************************************/ /* Handle a QUIT command. @@ -926,7 +930,7 @@ int is_excepted(ChannelInfo * ci, User * user) /*************************************************************************/ /* Is the given MASK ban-excepted? */ -int is_excepted_mask(ChannelInfo * ci, char *mask) +int is_excepted_mask(ChannelInfo * ci, const char *mask) { if (!ci->c || !ircd->except) return 0; @@ -971,11 +975,11 @@ int match_usermask(const char *mask, User * user) if (nick) { result = match_wild_nocase(nick, user->nick) - && match_wild_nocase(username, user->username) + && match_wild_nocase(username, user->GetIdent().c_str()) && (match_wild_nocase(host, user->host) || match_wild_nocase(host, user->vhost)); } else { - result = match_wild_nocase(username, user->username) + result = match_wild_nocase(username, user->GetIdent().c_str()) && (match_wild_nocase(host, user->host) || match_wild_nocase(host, user->vhost)); } @@ -984,51 +988,6 @@ int match_usermask(const char *mask, User * user) return result; } - -/*************************************************************************/ - -/* simlar to match_usermask, except here we pass the host as the IP */ - -int match_userip(const char *mask, User * user, char *iphost) -{ - char *mask2; - char *nick, *username, *host; - int result; - - if (!mask || !*mask) { - return 0; - } - - mask2 = sstrdup(mask); - - if (strchr(mask2, '!')) { - nick = strtok(mask2, "!"); - username = strtok(NULL, "@"); - } else { - nick = NULL; - username = strtok(mask2, "@"); - } - host = strtok(NULL, ""); - if (!username || !host) { - delete [] mask2; - return 0; - } - - if (nick) { - result = match_wild_nocase(nick, user->nick) - && match_wild_nocase(username, user->username) - && (match_wild_nocase(host, iphost) - || match_wild_nocase(host, user->vhost)); - } else { - result = match_wild_nocase(username, user->username) - && (match_wild_nocase(host, iphost) - || match_wild_nocase(host, user->vhost)); - } - - delete [] mask2; - return result; -} - /*************************************************************************/ /* Split a usermask up into its constitutent parts. Returned strings are @@ -1076,40 +1035,42 @@ void split_usermask(const char *mask, char **nick, char **user, char *create_mask(User * u) { char *mask, *s, *end; - int ulen = strlen(common_get_vident(u)); + std::string mident = u->GetIdent(); + std::string mhost = u->GetDisplayedHost(); + int ulen = mident.length(); /* Get us a buffer the size of the username plus hostname. The result * will never be longer than this (and will often be shorter), thus we * can use strcpy() and sprintf() safely. */ - end = mask = new char[ulen + strlen(common_get_vhost(u)) + 3]; - end += sprintf(end, "%s%s@", - (ulen < - (*(common_get_vident(u)) == - '~' ? USERMAX + 1 : USERMAX) ? "*" : ""), - (*(common_get_vident(u)) == - '~' ? common_get_vident(u) + - 1 : common_get_vident(u))); - - if (strspn(common_get_vhost(u), "0123456789.") == - strlen(common_get_vhost(u)) - && (s = strchr(common_get_vhost(u), '.')) + end = mask = new char[ulen + mhost.length() + 3]; + if (mident[0] == '~') + end += sprintf(end, "*%s@", mident.c_str()); + else + end += sprintf(end, "%s@", mident.c_str()); + + // XXX: someone needs to rewrite this godawful kitten murdering pile of crap. + if (strspn(mhost.c_str(), "0123456789.") == mhost.length() + && (s = strchr(mhost.c_str(), '.')) && (s = strchr(s + 1, '.')) && (s = strchr(s + 1, '.')) - && (!strchr(s + 1, '.'))) { /* IP addr */ - s = sstrdup(common_get_vhost(u)); + && (!strchr(s + 1, '.'))) + { /* IP addr */ + s = sstrdup(mhost.c_str()); *strrchr(s, '.') = 0; sprintf(end, "%s.*", s); delete [] s; - } else { - if ((s = strchr(common_get_vhost(u), '.')) && strchr(s + 1, '.')) { - s = sstrdup(strchr(common_get_vhost(u), '.') - 1); + } + else + { + if ((s = strchr(mhost.c_str(), '.')) && strchr(s + 1, '.')) { + s = sstrdup(strchr(mhost.c_str(), '.') - 1); *s = '*'; strcpy(end, s); delete [] s; } else { - strcpy(end, common_get_vhost(u)); + strcpy(end, mhost.c_str()); } } return mask; diff --git a/src/windows.cpp b/src/windows.cpp new file mode 100644 index 000000000..29a2131d1 --- /dev/null +++ b/src/windows.cpp @@ -0,0 +1,27 @@ + /* POSIX emulation layer for Windows. + * + * Copyright (C) 2008 Robin Burchell <w00t@inspircd.org> + * Copyright (C) 2008 Anope Team <info@anope.org> + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + * + * $Id$ + * + */ + +#ifdef WIN32 +const char *dlerror() +{ + static char errbuf[513]; + DWORD err = GetLastError(); + if (err == 0) + return NULL; + FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM | + FORMAT_MESSAGE_IGNORE_INSERTS, NULL, err, 0, errbuf, 512, + NULL); + return errbuf; +} +#endif |