/* MemoServ functions.
*
* (C) 2003-2005 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 "services.h"
#include "pseudo.h"
/*************************************************************************/
/* *INDENT-OFF* */
NickCore *nclists[1024];
static int delmemo(MemoInfo *mi, int num);
static int do_help(User *u);
static int do_send(User *u);
void memo_send(User *u, char *name, char *text, int z);
static int do_cancel(User *u);
static int do_list(User *u);
static int do_read(User *u);
static int do_del(User *u);
static int do_set(User *u);
static int do_set_notify(User *u, MemoInfo *mi, char *param);
static int do_set_limit(User *u, MemoInfo *mi, char *param);
static int do_info(User *u);
static int do_staff(User *u);
static int do_sendall(User *u);
void moduleAddMemoServCmds(void);
static void new_memo_mail(NickCore *nc, Memo *m);
static int do_rsend(User *u);
static int do_memocheck(User *u);
void rsend_notify(User *u, Memo *m, const char *chan);
/*************************************************************************/
void moduleAddMemoServCmds(void) {
Command *c;
c = createCommand("HELP", do_help, NULL, -1, -1,-1,-1,-1); addCoreCommand(MEMOSERV,c);
c = createCommand("SEND", do_send, NULL, MEMO_HELP_SEND, -1,-1,-1,-1); addCoreCommand(MEMOSERV,c);
c = createCommand("CANCEL", do_cancel, NULL, MEMO_HELP_CANCEL, -1,-1,-1,-1); addCoreCommand(MEMOSERV,c);
c = createCommand("LIST", do_list, NULL, MEMO_HELP_LIST, -1,-1,-1,-1); addCoreCommand(MEMOSERV,c);
c = createCommand("READ", do_read, NULL, MEMO_HELP_READ, -1,-1,-1,-1); addCoreCommand(MEMOSERV,c);
c = createCommand("DEL", do_del, NULL, MEMO_HELP_DEL, -1,-1,-1,-1); addCoreCommand(MEMOSERV,c);
c = createCommand("STAFF", do_staff, is_services_oper, -1, -1,MEMO_HELP_STAFF,MEMO_HELP_STAFF,MEMO_HELP_STAFF); addCoreCommand(MEMOSERV,c);
c = createCommand("SET", do_set, NULL, MEMO_HELP_SET, -1,-1,-1,-1); addCoreCommand(MEMOSERV,c);
c = createCommand("SET NOTIFY", NULL, NULL, MEMO_HELP_SET_NOTIFY, -1,-1,-1,-1); addCoreCommand(MEMOSERV,c);
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); addCoreCommand(MEMOSERV,c);
c = createCommand("INFO", do_info, NULL, -1,MEMO_HELP_INFO, -1,MEMO_SERVADMIN_HELP_INFO, MEMO_SERVADMIN_HELP_INFO); addCoreCommand(MEMOSERV,c);
c = createCommand("SENDALL", do_sendall, is_services_admin, -1, -1,-1,MEMO_HELP_SENDALL,MEMO_HELP_SENDALL); addCoreCommand(MEMOSERV,c);
c = createCommand("RSEND", do_rsend, NULL, MEMO_HELP_RSEND, -1,-1,-1,-1); addCoreCommand(MEMOSERV,c);
c = createCommand("CHECK", do_memocheck, NULL, MEMO_HELP_CHECK, -1,-1,-1,-1); addCoreCommand(MEMOSERV,c);
}
/*************************************************************************/
/*************************************************************************/
/* *INDENT-ON* */
/**
* MemoServ initialization.
* @return void
*/
void ms_init(void)
{
Command *cmd;
moduleAddMemoServCmds();
cmd = findCommand(MEMOSERV, "SET LIMIT");
if (cmd)
cmd->help_param1 = (char *) (long) MSMaxMemos;
}
/*************************************************************************/
/**
* memoserv: Main MemoServ routine.
* Note that the User structure passed to the do_* routines will
* always be valid (non-NULL) and will always have a valid
* NickInfo pointer in the `ni' field.
* @param u User Struct
* @param buf Buffer containing the privmsg
* @return void
*/
void memoserv(User * u, char *buf)
{
char *cmd, *s;
cmd = strtok(buf, " ");
if (!cmd) {
return;
} else if (stricmp(cmd, "\1PING") == 0) {
if (!(s = strtok(NULL, ""))) {
s = "";
}
anope_cmd_ctcp(s_MemoServ, u->nick, "PING %s", s);
} else if (skeleton) {
notice_lang(s_MemoServ, u, SERVICE_OFFLINE, s_MemoServ);
} else {
if (!u->na && stricmp(cmd, "HELP") != 0)
notice_lang(s_MemoServ, u, NICK_NOT_REGISTERED_HELP,
s_NickServ);
else
mod_run_cmd(s_MemoServ, u, MEMOSERV, cmd);
}
}
/*************************************************************************/
/**
* check_memos: See if the given user has any unread memos, and send a
* NOTICE to that user if so (and if the appropriate flag is
* set).
* @param u User Struct
* @return void
*/
void check_memos(User * u)
{
NickCore *nc;
int i, newcnt = 0;
if (!u) {
if (debug) {
alog("debug: check_memos called with NULL values");
}
return;
}
if (!(nc = (u->na ? u->na->nc : NULL)) || !nick_recognized(u) ||
!(nc->flags & NI_MEMO_SIGNON)) {
return;
}
for (i = 0; i < nc->memos.memocount; i++) {
if (nc->memos.memos[i].flags & MF_UNREAD)
newcnt++;
}
if (newcnt > 0) {
notice_lang(s_MemoServ, u,
newcnt == 1 ? MEMO_HAVE_NEW_MEMO : MEMO_HAVE_NEW_MEMOS,
newcnt);
if (newcnt == 1 && (nc->memos.memos[i - 1].flags & MF_UNREAD)) {
notice_lang(s_MemoServ, u, MEMO_TYPE_READ_LAST, s_MemoServ);
} else if (newcnt == 1) {
for (i = 0; i < nc->memos.memocount; i++) {
if (nc->memos.memos[i].flags & MF_UNREAD)
break;
}
notice_lang(s_MemoServ, u, MEMO_TYPE_READ_NUM, s_MemoServ,
nc->memos.memos[i].number);
} else {
notice_lang(s_MemoServ, u, MEMO_TYPE_LIST_NEW, s_MemoServ);
}
}
if (nc->memos.memomax > 0 && nc->memos.memocount >= nc->memos.memomax) {
if (nc->memos.memocount > nc->memos.memomax)
notice_lang(s_MemoServ, u, MEMO_OVER_LIMIT, nc->memos.memomax);
else
notice_lang(s_MemoServ, u, MEMO_AT_LIMIT, nc->memos.memomax);
}
}
/*************************************************************************/
/*********************** MemoServ private routines ***********************/
/*************************************************************************/
/**
* Return the MemoInfo corresponding to the given nick or channel name.
* @param name Name to check
* @param ischan - the result its a channel will be stored in here
* @param isforbid - the result if its forbidden will be stored in here
* @return `ischan' 1 if the name was a channel name, else 0.
* @return `isforbid' 1 if the name is forbidden, else 0.
*/
static MemoInfo *getmemoinfo(const char *name, int *ischan, int *isforbid)
{
if (*name == '#') {
ChannelInfo *ci;
if (ischan)
*ischan = 1;
ci = cs_findchan(name);
if (ci) {
if (!(ci->flags & CI_VERBOTEN)) {
*isforbid = 0;
return &ci->memos;
} else {
*isforbid = 1;
return NULL;
|