mirror of
https://github.com/anope/anope.git
synced 2026-06-29 08:16:39 +02:00
BUILD : 1.7.8 (574) BUGS : N/A NOTES : Internal Events, Win32 can build with encryption, nickIsServices() works if format is nick@services
git-svn-id: svn://svn.anope.org/anope/trunk@574 31f1291d-b8d6-0310-a050-a5561fc1590b git-svn-id: http://anope.svn.sourceforge.net/svnroot/anope/trunk@424 5417fbe8-f217-4b02-8779-1006273d7864
This commit is contained in:
parent
f194129217
commit
59f3a38ffd
@@ -1,8 +1,11 @@
|
||||
Anope Version S V N
|
||||
-------------------
|
||||
Provided by Anope Dev. <dev@anope.org> - 2005
|
||||
02/13 A Internal Event support, see EVENTS in the doc folder for help [ #00]
|
||||
02/05 A Support for Unreal 3.2 +I channel mode. [ #00]
|
||||
02/03 A Merged anope-win32 branch into the main, now Win32 ready. [ #00]
|
||||
02/13 F nickIsServices() works if format is nick@services [ #00]
|
||||
02/12 F Win32 builds can now build with encryption [ #00]
|
||||
02/10 F mod_current_buffer was not set in all possible cases [#296]
|
||||
02/07 F Updated userkey information in example.conf. [ #00]
|
||||
02/06 F Win32 Module Load Errors. [#294]
|
||||
|
||||
+153
@@ -0,0 +1,153 @@
|
||||
Internal Events
|
||||
|
||||
1. Intro
|
||||
2. Complex Events
|
||||
3. Triggered Events
|
||||
4. Triggered Events List
|
||||
|
||||
==============================================================================================
|
||||
1. Introduction to Internal Events
|
||||
==============================================================================================
|
||||
|
||||
Internal Events are setup to give module developers more information about what the core
|
||||
is doing at different times. This information can be as complex as data we are feeding to the
|
||||
uplink, to simple triggered events such as the databases being saved. A list of triggered
|
||||
events can be found below. Additional there is a module included with the core which can
|
||||
provide some clue as to how to use the code in your modules. The rest of this document assumes
|
||||
that you are used to writting modules.
|
||||
|
||||
==============================================================================================
|
||||
2. Complex Events
|
||||
==============================================================================================
|
||||
|
||||
This type of events are based around what happens when we talk to the IRCD, much like
|
||||
MESSAGE events that the IRCD sends to us. The events are triggered when Anope writes to the
|
||||
ircd. To watch for these events you must have some knowledge of how the IRCD command system
|
||||
works. In our example we will trap for NICK events.
|
||||
|
||||
A. All functions most be formatted as
|
||||
|
||||
int functioname(char *source, int ac, char **av);
|
||||
|
||||
B. In AnopeInit you must declare EvtMessage in some fashion, it is into this variable that
|
||||
we will create the event handler. Here is what the base AnopeInit should look like at
|
||||
this point.
|
||||
|
||||
int AnopeInit(int argc, char **argv)
|
||||
{
|
||||
EvtMessage *msg = NULL;
|
||||
int status;
|
||||
|
||||
moduleAddAuthor(AUTHOR);
|
||||
moduleAddVersion(VERSION);
|
||||
return MOD_CONT;
|
||||
}
|
||||
|
||||
C. Pass "createEventHandler" the name of the message in this case NICK, and the function
|
||||
that was created in Step A. At this point you should assign the return of
|
||||
"createEventHandler" to the EvtMessage variable.
|
||||
|
||||
msg = createEventHandler("NICK", my_nick);
|
||||
|
||||
D. The Handler is not ready for use, now you must add it to the hash, with
|
||||
"moduleAddEventHandler", you will want to pass to this function the return
|
||||
of "createEventHandler"
|
||||
|
||||
status = moduleAddEventHandler(msg);
|
||||
|
||||
it will return the module error code so you can confirm that it was added
|
||||
correctly.
|
||||
|
||||
E. With that setup in your function you will be passed 3 items. The source most of the time
|
||||
this will be set to ServerName or NULL, consult our ircd documentation about how messages
|
||||
are formatted. AC is the count of variables you will find in AV.
|
||||
|
||||
int my_nick(char *source, int ac, char **av)
|
||||
{
|
||||
alog("Internal Event - nick is %s",av[0]);
|
||||
return MOD_CONT;
|
||||
}
|
||||
|
||||
==============================================================================================
|
||||
3. Triggered Events
|
||||
==============================================================================================
|
||||
|
||||
These events also known as "event hooks" are internal events such as expiring of nicks to
|
||||
the saving of databases.
|
||||
|
||||
A. All functions most be formatted as
|
||||
|
||||
int functioname(char *message);
|
||||
|
||||
B. In AnopeInit you must declare EvtHook in some fashion, it is into this variable that
|
||||
we will create the event handler. Here is what the base AnopeInit should look like at
|
||||
this point.
|
||||
|
||||
int AnopeInit(int argc, char **argv)
|
||||
{
|
||||
EvtHook *hook = NULL;
|
||||
int status;
|
||||
|
||||
moduleAddAuthor(AUTHOR);
|
||||
moduleAddVersion(VERSION);
|
||||
return MOD_CONT;
|
||||
}
|
||||
|
||||
C. Pass "createEventHook" the name of the event, in this case we are going to hook to the
|
||||
saving of databases, "EVENT_DB_SAVING"
|
||||
|
||||
hook = createEventHook(EVENT_DB_SAVING, my_save);
|
||||
|
||||
D. The Handler is not ready for use, now you must add it to the hash, with
|
||||
"moduleAddEventHook", you will want to pass to this function the return
|
||||
of "createEventHook"
|
||||
|
||||
status = moduleAddEventHook(hook);
|
||||
|
||||
it will return the module error code so you can confirm that it was added
|
||||
correctly.
|
||||
|
||||
E. With that setup in your function you will be passed 1 items, the message is very simple
|
||||
it could be as simple as a start, stop or message. In the case of saving it has a start
|
||||
and stop
|
||||
|
||||
int my_save(char *source)
|
||||
{
|
||||
|
||||
if (!stricmp(source, EVENT_START)) {
|
||||
alog("Saving the databases! has started");
|
||||
} else {
|
||||
alog("Saving the databases is complete");
|
||||
}
|
||||
return MOD_CONT;
|
||||
}
|
||||
|
||||
==============================================================================================
|
||||
4. Triggered Events List
|
||||
==============================================================================================
|
||||
| Event Hook | Event Argument |
|
||||
==============================================================================================
|
||||
| EVENT_DB_SAVING | EVENT_START, EVENT_STOP |
|
||||
| EVENT_NEWNICK | Nick as it connected |
|
||||
| EVENT_BOT_UNASSIGN | Channel name |
|
||||
| EVENT_BOT_JOIN | Channel name |
|
||||
| EVENT_BOT_CREATE | Bot Nick |
|
||||
| EVENT_BOT_CHANGE | Bot Nick |
|
||||
| EVENT_BOT_DEL | Bot Nick |
|
||||
| EVENT_BOT_ASSIGN | Bot Nick |
|
||||
| EVENT_TOPIC_UPDATED | Channel Name |
|
||||
| EVENT_CHAN_EXPIRE | Channel Name |
|
||||
| EVENT_CHAN_REGISTERED | Channel Name |
|
||||
| EVENT_CHAN_DROP | Channel Name |
|
||||
| EVENT_CHAN_FORBIDDEN | Channel Name |
|
||||
| EVENT_CHAN_SUSPENDED | Channel Name |
|
||||
| EVENT_CONNECT | EVENT_START, EVENT_STOP |
|
||||
| EVENT_DB_EXPIRE | EVENT_START, EVENT_STOP |
|
||||
| EVENT_RESTART | EVENT_START |
|
||||
| EVENT_SHUTDOWN | EVENT_START, EVENT_STOP |
|
||||
| EVENT_SIGNAL | quit message |
|
||||
| EVENT_NICK_REGISTED | Nick |
|
||||
| EVENT_NICK_DROPPED | Nick |
|
||||
| EVENT_NICK_FORBIDDEN | Nick |
|
||||
| EVENT_CHANGE_NICK | Nick |
|
||||
==============================================================================================
|
||||
+9
-3
@@ -53,16 +53,22 @@ the following free components from Microsoft. Once downloaded install these pack
|
||||
(ie.. PROXY_SCANNER=1), note the proxy scan is not the best and its recommended to use
|
||||
another thrid party scanner.
|
||||
|
||||
D. If you are using Visual Studio 6, this next line can be very important. If you are an
|
||||
D. Do you want to use the MD5 message-digest algorithm to encrypt passwords?
|
||||
(Selecting "yes" protects your passwords from being stolen if someone
|
||||
gains access to the Services databases, but makes it impossible to recover
|
||||
forgotten passwords. There is no way to reverse this operation, so make
|
||||
sure you really want to enable it.). Change DB_ENCRYPTION to be equal to 1
|
||||
|
||||
E. If you are using Visual Studio 6, this next line can be very important. If you are an
|
||||
error during compile about "unresolved external symbol __ftol2", remove the # in front
|
||||
of VC6=/QIfist and attempt to compile again.
|
||||
|
||||
E. When compiling if you get an error about 'Cannot find wsock32.lib' or 'Cannot find
|
||||
F. When compiling if you get an error about 'Cannot find wsock32.lib' or 'Cannot find
|
||||
msvcrt.lib' You need to define the libpath, in the LIBPATH directive. You can define
|
||||
the path one of two ways, either with \ or / if you use \ you must add a secondary \
|
||||
so c:\mysql would be c:\\sdk\lib be sure to remove the # in front of LFLAGS
|
||||
|
||||
F. Most import is to set the DATDEST to be the folder name where data will be stored.
|
||||
G. Most import is to set the DATDEST to be the folder name where data will be stored.
|
||||
This does not need to be the full path just the folder under the main executable
|
||||
in which data will exist. In our example we will use "data"
|
||||
|
||||
|
||||
@@ -0,0 +1,42 @@
|
||||
/* Prototypes and external variable declarations.
|
||||
*
|
||||
* (C) 2003-2005 Anope Team
|
||||
* Contact us at info@anope.org
|
||||
*
|
||||
* Please read COPYING and README for furhter details.
|
||||
*
|
||||
* Based on the original code of Epona by Lara.
|
||||
* Based on the original code of Services by Andy Church.
|
||||
*
|
||||
* $Id:$
|
||||
*
|
||||
*/
|
||||
|
||||
#define EVENT_START "start"
|
||||
#define EVENT_STOP "stop"
|
||||
|
||||
#define EVENT_DB_SAVING "db_saving"
|
||||
#define EVENT_NEWNICK "newnick"
|
||||
#define EVENT_BOT_UNASSIGN "bot_unassign"
|
||||
#define EVENT_BOT_JOIN "bot_join"
|
||||
#define EVENT_BOT_CREATE "bot_create"
|
||||
#define EVENT_BOT_CHANGE "bot_change"
|
||||
#define EVENT_BOT_DEL "bot_del"
|
||||
#define EVENT_BOT_ASSIGN "bot_assign"
|
||||
#define EVENT_TOPIC_UPDATED "chan_topic_updated"
|
||||
#define EVENT_CHAN_EXPIRE "chan_expire"
|
||||
#define EVENT_CHAN_REGISTERED "chan_registered"
|
||||
#define EVENT_CHAN_DROP "chan_dropped"
|
||||
#define EVENT_CHAN_FORBIDDEN "chan_forbidden"
|
||||
#define EVENT_CHAN_SUSPENDED "chan_suspended"
|
||||
#define EVENT_CHAN_UNSUSPEND "chan_unsuspend"
|
||||
#define EVENT_CONNECT "connect"
|
||||
#define EVENT_DB_EXPIRE "db_expire"
|
||||
#define EVENT_RESTART "restart"
|
||||
#define EVENT_SHUTDOWN "shutdown"
|
||||
#define EVENT_SIGNAL "signal"
|
||||
#define EVENT_NICK_REGISTED "nick_registered"
|
||||
#define EVENT_NICK_DROPPED "nick_dropped"
|
||||
#define EVENT_NICK_FORBIDDEN "nick_forbidden"
|
||||
#define EVENT_CHANGE_NICK "change_nick"
|
||||
|
||||
@@ -1168,4 +1168,9 @@ E int decode_ip(char *buf);
|
||||
|
||||
E char *host_resolve(char *host);
|
||||
|
||||
extern void event_message_process(char *eventbuf);
|
||||
extern void eventprintf(char *fmt, ...);
|
||||
extern void event_process_hook(char *name, char *eventbuf);
|
||||
extern void send_event(char *name, const char *fmt, ...);
|
||||
|
||||
#endif /* EXTERN_H */
|
||||
|
||||
+62
-2
@@ -62,6 +62,8 @@ typedef void * ano_module_t;
|
||||
#define OPERSERV OS_cmdTable
|
||||
#define IRCD IRCD_cmdTable
|
||||
#define MODULE_HASH Module_table
|
||||
#define EVENT EVENT_cmdTable
|
||||
#define EVENTHOOKS HOOK_cmdTable
|
||||
|
||||
/**********************************************************************
|
||||
* Module Returns
|
||||
@@ -103,7 +105,10 @@ typedef struct ModuleHash_ ModuleHash;
|
||||
typedef struct Message_ Message;
|
||||
typedef struct MessageHash_ MessageHash;
|
||||
typedef struct ModuleCallBack_ ModuleCallBack;
|
||||
|
||||
typedef struct EvtMessage_ EvtMessage;
|
||||
typedef struct EvtMessageHash_ EvtMessageHash;
|
||||
typedef struct EvtHook_ EvtHook;
|
||||
typedef struct EvtHookHash_ EvtHookHash;
|
||||
|
||||
extern MDE CommandHash *HOSTSERV[MAX_CMD_HASH];
|
||||
extern MDE CommandHash *BOTSERV[MAX_CMD_HASH];
|
||||
@@ -113,6 +118,8 @@ extern MDE CommandHash *CHANSERV[MAX_CMD_HASH];
|
||||
extern MDE CommandHash *HELPSERV[MAX_CMD_HASH];
|
||||
extern MDE CommandHash *OPERSERV[MAX_CMD_HASH];
|
||||
extern MDE MessageHash *IRCD[MAX_CMD_HASH];
|
||||
extern EvtMessageHash *EVENT[MAX_CMD_HASH];
|
||||
extern EvtHookHash *EVENTHOOKS[MAX_CMD_HASH];
|
||||
|
||||
struct Module_ {
|
||||
char *name;
|
||||
@@ -202,6 +209,36 @@ struct ModuleCallBack_ {
|
||||
ModuleCallBack *next;
|
||||
};
|
||||
|
||||
struct EvtMessage_ {
|
||||
char *name;
|
||||
int (*func)(char *source, int ac, char **av);
|
||||
int core;
|
||||
char *mod_name;
|
||||
EvtMessage *next;
|
||||
};
|
||||
|
||||
struct EvtMessageHash_ {
|
||||
char *name;
|
||||
EvtMessage *evm;
|
||||
EvtMessageHash *next;
|
||||
};
|
||||
|
||||
|
||||
struct EvtHook_ {
|
||||
int (*func)(char *source);
|
||||
int core;
|
||||
char *name;
|
||||
char *mod_name;
|
||||
EvtHook *next;
|
||||
};
|
||||
|
||||
struct EvtHookHash_ {
|
||||
char *name;
|
||||
EvtHook *evh;
|
||||
EvtHookHash *next;
|
||||
};
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* Module Managment Functions */
|
||||
Module *createModule(char *filename); /* Create a new module, using the given name */
|
||||
@@ -243,8 +280,9 @@ MDE int addCommand(CommandHash *cmdTable[], Command *c,int pos);
|
||||
MDE int delCommand(CommandHash *cmdTable[], Command *c,char *mod_name); /* Del a command from a cmd table */
|
||||
MDE int moduleDelCommand(CommandHash *cmdTable[],char *name); /* Del a command from a cmd table */
|
||||
Command *findCommand(CommandHash *cmdTable[], const char *name); /* Find a command */
|
||||
|
||||
/*************************************************************************/
|
||||
/*************************************************************************/
|
||||
|
||||
/* Message Managment Functions */
|
||||
MDE Message *createMessage(char *name,int (*func)(char *source, int ac, char **av));
|
||||
Message *findMessage(MessageHash *msgTable[], const char *name); /* Find a Message */
|
||||
@@ -255,7 +293,29 @@ int delMessage(MessageHash *msgTable[], Message *m, char *mod_name); /* Del a M
|
||||
MDE int moduleDelMessage(char *name);
|
||||
int destroyMessage(Message *m); /* destroy a Message*/
|
||||
Message *findMessage(MessageHash *msgTable[], const char *name);
|
||||
|
||||
/*************************************************************************/
|
||||
|
||||
MDE EvtMessage *createEventHandler(char *name, int (*func) (char *source, int ac, char **av));
|
||||
EvtMessage *findEventHandler(EvtMessageHash * msgEvtTable[], const char *name);
|
||||
int addCoreEventHandler(EvtMessageHash * msgEvtTable[], EvtMessage * evm);
|
||||
MDE int moduleAddEventHandler(EvtMessage * evm);
|
||||
MDE int moduleEventDelHandler(char *name);
|
||||
int delEventHandler(EvtMessageHash * msgEvtTable[], EvtMessage * evm, char *mod_name);
|
||||
int destroyEventHandler(EvtMessage * evm);
|
||||
int addEventHandler(EvtMessageHash * msgEvtTable[], EvtMessage * evm);
|
||||
|
||||
MDE EvtHook *createEventHook(char *name, int (*func) (char *source));
|
||||
EvtHook *findEventHook(EvtHookHash * HookEvtTable[], const char *name);
|
||||
int addCoreEventHook(EvtHookHash * HookEvtTable[], EvtHook * evh);
|
||||
MDE int moduleAddEventHook(EvtHook * evh);
|
||||
MDE int moduleEventDelHook(const char *name);
|
||||
int delEventHook(EvtHookHash * HookEvtTable[], EvtHook * evh, char *mod_name);
|
||||
int destroyEventHook(EvtHook * evh);
|
||||
extern char *mod_current_evtbuffer;
|
||||
|
||||
/*************************************************************************/
|
||||
|
||||
MDE int moduleAddCallback(char *name,time_t when,int (*func)(int argc, char *argv[]),int argc, char **argv);
|
||||
MDE void moduleDelCallback(char *name);
|
||||
MDE void moduleCallBackRun(void);
|
||||
|
||||
@@ -177,6 +177,7 @@ extern int toupper(char), tolower(char);
|
||||
/* Miscellaneous definitions. */
|
||||
#include "defs.h"
|
||||
#include "slist.h"
|
||||
#include "events.h"
|
||||
|
||||
/*************************************************************************/
|
||||
|
||||
|
||||
+8
-1
@@ -40,6 +40,9 @@ USE_MYSQL=0
|
||||
# Set this to 1 to enable the proxy scanner
|
||||
PROXY_SCANNER=0
|
||||
|
||||
# Set this to 1 to enable the proxy scanner
|
||||
DB_ENCRYPTION=0
|
||||
|
||||
# If you want to change the names/locations of files/folders, you
|
||||
# can do that here.
|
||||
PROGRAM=anope.exe
|
||||
@@ -56,7 +59,7 @@ DATDEST=data
|
||||
LIBPATH=
|
||||
|
||||
# If you edited the line above, uncomment the next line.
|
||||
#LFLAGS=/LIBPATH:"$(LIBPATH)"
|
||||
LFLAGS=/LIBPATH:"$(LIBPATH)"
|
||||
|
||||
|
||||
###############################################################
|
||||
@@ -156,6 +159,10 @@ LIBS=$(LIBS) libmysql.lib zlib.lib
|
||||
BASE_CFLAGS=/D USE_THREADS $(BASE_CFLAGS)
|
||||
!ENDIF
|
||||
|
||||
!IF $(DB_ENCRYPTION) == 1
|
||||
BASE_CFLAGS=/D USE_ENCRYPTION $(BASE_CFLAGS)
|
||||
!ENDIF
|
||||
|
||||
# Note that changing any of these options (or, in fact, anything in this
|
||||
# file) will automatically cause a full rebuild of Services.
|
||||
|
||||
|
||||
+4
-3
@@ -2,13 +2,13 @@ MYSQL_OBJ = $(MYSQL:.c=.o)
|
||||
RDB_OBJ = $(RDB:.c=.o)
|
||||
IRCD_OBJ = $(IRCDFILE:.c=.o)
|
||||
OBJS = actions.o base64.o botserv.o channels.o chanserv.o commands.o compat.o converter.o \
|
||||
config.o datafiles.o encrypt.o helpserv.o hostserv.o init.o language.o list.o log.o mail.o main.o \
|
||||
config.o datafiles.o encrypt.o events.o helpserv.o hostserv.o init.o language.o list.o log.o mail.o main.o \
|
||||
memory.o memoserv.o messages.o misc.o modules.o news.o nickserv.o operserv.o \
|
||||
process.o proxy.o send.o servers.o sessions.o slist.o sockutil.o \
|
||||
timeout.o users.o \
|
||||
$(VSNPRINTF_O) $(RDB_OBJ) $(MYSQL_OBJ) $(IRCD_OBJ)
|
||||
SRCS = actions.c base64.c botserv.c channels.c chanserv.c commands.c compat.c converter.c \
|
||||
config.c datafiles.c encrypt.c helpserv.c hostserv.c init.c language.c list.c log.c mail.c main.c \
|
||||
config.c datafiles.c encrypt.c events.c helpserv.c hostserv.c init.c language.c list.c log.c mail.c main.c \
|
||||
memory.c memoserv.c messages.c misc.c modules.c news.c nickserv.c operserv.c \
|
||||
process.c proxy.c send.c servers.c sessions.c slist.c sockutil.c \
|
||||
timeout.c users.c \
|
||||
@@ -54,6 +54,7 @@ config.o: config.c $(INCLUDES)
|
||||
converter.o: converter.c $(INCLUDES)
|
||||
datafiles.o: datafiles.c $(INCLUDES)
|
||||
encrypt.o: encrypt.c $(INCLUDES)
|
||||
events.o: events.c $(INCLUDES)
|
||||
init.o: init.c $(INCLUDES)
|
||||
helpserv.o: helpserv.c $(INCLUDES)
|
||||
hostserv.o: hostserv.c $(INCLUDES)
|
||||
@@ -65,7 +66,7 @@ main.o: main.c $(INCLUDES)
|
||||
memory.o: memory.c $(INCLUDES)
|
||||
memoserv.o: memoserv.c $(INCLUDES)
|
||||
messages.o: messages.c $(INCLUDES)
|
||||
modules.o: modules.c $(INCLUDES)
|
||||
modules.o: modules.c $(INCLUDES)
|
||||
misc.o: misc.c $(INCLUDES)
|
||||
news.o: news.c $(INCLUDES)
|
||||
nickserv.o: nickserv.c $(INCLUDES)
|
||||
|
||||
@@ -849,6 +849,8 @@ BotInfo *findbot(char *nick)
|
||||
|
||||
static void unassign(User * u, ChannelInfo * ci)
|
||||
{
|
||||
send_event(EVENT_BOT_UNASSIGN, ci->name);
|
||||
|
||||
if (ci->c && ci->c->usercount >= BSMinUsers) {
|
||||
anope_cmd_part(ci->bi->nick, ci->name, "UNASSIGN from %s",
|
||||
u->nick);
|
||||
@@ -995,6 +997,7 @@ void bot_join(ChannelInfo * ci)
|
||||
}
|
||||
anope_cmd_join(ci->bi->nick, ci->c->name, ci->c->creation_time);
|
||||
anope_cmd_bot_chan_mode(ci->bi->nick, ci->c->name);
|
||||
send_event(EVENT_BOT_JOIN, ci->name);
|
||||
}
|
||||
|
||||
/*************************************************************************/
|
||||
@@ -1353,6 +1356,8 @@ static int do_bot(User * u)
|
||||
|
||||
notice_lang(s_BotServ, u, BOT_BOT_ADDED, bi->nick, bi->user,
|
||||
bi->host, bi->real);
|
||||
|
||||
send_event(EVENT_BOT_CREATE, bi->nick);
|
||||
}
|
||||
} else if (!stricmp(cmd, "CHANGE")) {
|
||||
char *oldnick = strtok(NULL, " ");
|
||||
@@ -1478,6 +1483,8 @@ static int do_bot(User * u)
|
||||
|
||||
notice_lang(s_BotServ, u, BOT_BOT_CHANGED, oldnick, bi->nick,
|
||||
bi->user, bi->host, bi->real);
|
||||
|
||||
send_event(EVENT_BOT_CHANGE, bi->nick);
|
||||
}
|
||||
} else if (!stricmp(cmd, "DEL")) {
|
||||
char *nick = strtok(NULL, " ");
|
||||
@@ -1489,6 +1496,7 @@ static int do_bot(User * u)
|
||||
else if (!(bi = findbot(nick)))
|
||||
notice_lang(s_BotServ, u, BOT_DOES_NOT_EXIST, nick);
|
||||
else {
|
||||
send_event(EVENT_BOT_DEL, bi->nick);
|
||||
anope_cmd_quit(bi->nick,
|
||||
"Quit: Help! I'm being deleted by %s!",
|
||||
u->nick);
|
||||
@@ -1587,6 +1595,7 @@ static int do_assign(User * u)
|
||||
bot_join(ci);
|
||||
}
|
||||
notice_lang(s_BotServ, u, BOT_ASSIGN_ASSIGNED, bi->nick, ci->name);
|
||||
send_event(EVENT_BOT_ASSIGN, bi->nick);
|
||||
}
|
||||
return MOD_CONT;
|
||||
}
|
||||
|
||||
@@ -1740,6 +1740,7 @@ void record_topic(const char *chan)
|
||||
ci->last_topic = NULL;
|
||||
strscpy(ci->last_topic_setter, c->topic_setter, NICKMAX);
|
||||
ci->last_topic_time = c->topic_time;
|
||||
send_event(EVENT_TOPIC_UPDATED, chan);
|
||||
}
|
||||
|
||||
/*************************************************************************/
|
||||
@@ -1871,6 +1872,7 @@ void expire_chans()
|
||||
next = ci->next;
|
||||
if (!ci->c && now - ci->last_used >= CSExpire
|
||||
&& !(ci->flags & (CI_VERBOTEN | CI_NO_EXPIRE))) {
|
||||
send_event(EVENT_CHAN_EXPIRE, ci->name);
|
||||
alog("Expiring channel %s (founder: %s)", ci->name,
|
||||
(ci->founder ? ci->founder->display : "(none)"));
|
||||
delchan(ci);
|
||||
@@ -2789,6 +2791,7 @@ static int do_register(User * u)
|
||||
anope_cmd_mode(s_ChanServ, chan, "%s %s", ircd->ownerset,
|
||||
u->nick);
|
||||
}
|
||||
send_event(EVENT_CHAN_REGISTERED, chan);
|
||||
}
|
||||
return MOD_CONT;
|
||||
}
|
||||
@@ -2945,6 +2948,7 @@ static int do_drop(User * u)
|
||||
chan);
|
||||
|
||||
notice_lang(s_ChanServ, u, CHAN_DROPPED, chan);
|
||||
send_event(EVENT_CHAN_DROP, chan);
|
||||
}
|
||||
return MOD_CONT;
|
||||
}
|
||||
@@ -6371,6 +6375,7 @@ static int do_forbid(User * u)
|
||||
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, chan);
|
||||
} else {
|
||||
alog("%s: Valid FORBID for %s by %s failed", s_ChanServ, ci->name,
|
||||
u->nick);
|
||||
@@ -6444,6 +6449,7 @@ static int do_suspend(User * u)
|
||||
alog("%s: %s set SUSPEND for channel %s", s_ChanServ, u->nick,
|
||||
ci->name);
|
||||
notice_lang(s_ChanServ, u, CHAN_SUSPEND_SUCCEEDED, chan);
|
||||
send_event(EVENT_CHAN_SUSPENDED, chan);
|
||||
} else {
|
||||
alog("%s: Valid SUSPEND for %s by %s failed", s_ChanServ, ci->name,
|
||||
u->nick);
|
||||
@@ -6486,6 +6492,7 @@ static int do_unsuspend(User * u)
|
||||
alog("%s: %s set UNSUSPEND for channel %s", s_ChanServ, u->nick,
|
||||
ci->name);
|
||||
notice_lang(s_ChanServ, u, CHAN_UNSUSPEND_SUCCEEDED, chan);
|
||||
send_event(EVENT_CHAN_UNSUSPEND, chan);
|
||||
} else {
|
||||
alog("%s: Valid UNSUSPEND for %s by %s failed", s_ChanServ,
|
||||
chan, u->nick);
|
||||
|
||||
+779
@@ -0,0 +1,779 @@
|
||||
/* Events functions.
|
||||
*
|
||||
* (C) 2004-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.
|
||||
*
|
||||
*
|
||||
*/
|
||||
|
||||
#include "modules.h"
|
||||
#include "language.h"
|
||||
#include "version.h"
|
||||
|
||||
extern Module *mod_current_module;
|
||||
extern char *mod_current_module_name;
|
||||
char *mod_current_evtbuffer = NULL;
|
||||
|
||||
EvtMessageHash *EVENT[MAX_CMD_HASH];
|
||||
EvtHookHash *EVENTHOOKS[MAX_CMD_HASH];
|
||||
|
||||
EvtMessage *find_event(const char *name)
|
||||
{
|
||||
EvtMessage *m;
|
||||
m = findEventHandler(EVENT, name);
|
||||
return m;
|
||||
}
|
||||
|
||||
EvtHook *find_eventhook(const char *name)
|
||||
{
|
||||
EvtHook *m;
|
||||
m = findEventHook(EVENTHOOKS, name);
|
||||
return m;
|
||||
}
|
||||
|
||||
void send_event(char *name, const char *fmt, ...)
|
||||
{
|
||||
va_list args;
|
||||
char buf[16384]; /* Really huge, to try and avoid truncation */
|
||||
*buf = '\0';
|
||||
|
||||
if (fmt) {
|
||||
va_start(args, fmt);
|
||||
vsnprintf(buf, BUFSIZE - 1, fmt, args);
|
||||
va_end(args);
|
||||
}
|
||||
event_process_hook(name, buf);
|
||||
}
|
||||
|
||||
void eventprintf(char *fmt, ...)
|
||||
{
|
||||
va_list args;
|
||||
char buf[16384]; /* Really huge, to try and avoid truncation */
|
||||
char *event;
|
||||
|
||||
va_start(args, fmt);
|
||||
vsnprintf(buf, sizeof(buf), fmt, args);
|
||||
event = sstrdup(buf);
|
||||
event_message_process(event);
|
||||
va_end(args);
|
||||
if (event) {
|
||||
free(event);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
void event_message_process(char *eventbuf)
|
||||
{
|
||||
int retVal = 0;
|
||||
EvtMessage *current = NULL;
|
||||
char source[64];
|
||||
char cmd[64];
|
||||
char buf[512]; /* Longest legal IRC command line */
|
||||
char *s;
|
||||
int ac; /* Parameters for the command */
|
||||
char **av;
|
||||
EvtMessage *evm;
|
||||
|
||||
/* zero out the buffers before we do much else */
|
||||
*buf = '\0';
|
||||
*source = '\0';
|
||||
*cmd = '\0';
|
||||
|
||||
strscpy(buf, eventbuf, sizeof(buf));
|
||||
|
||||
doCleanBuffer((char *) buf);
|
||||
|
||||
/* Split the buffer into pieces. */
|
||||
if (*buf == ':') {
|
||||
s = strpbrk(buf, " ");
|
||||
if (!s)
|
||||
return;
|
||||
*s = 0;
|
||||
while (isspace(*++s));
|
||||
strscpy(source, buf + 1, sizeof(source));
|
||||
memmove(buf, s, strlen(s) + 1);
|
||||
} else {
|
||||
*source = 0;
|
||||
}
|
||||
if (!*buf)
|
||||
return;
|
||||
s = strpbrk(buf, " ");
|
||||
if (s) {
|
||||
*s = 0;
|
||||
while (isspace(*++s));
|
||||
} else
|
||||
s = buf + strlen(buf);
|
||||
strscpy(cmd, buf, sizeof(cmd));
|
||||
ac = split_buf(s, &av, 1);
|
||||
|
||||
/* Do something with the message. */
|
||||
evm = find_event(cmd);
|
||||
if (evm) {
|
||||
if (evm->func) {
|
||||
mod_current_module_name = evm->mod_name;
|
||||
retVal = evm->func(source, ac, av);
|
||||
mod_current_module_name = NULL;
|
||||
if (retVal == MOD_CONT) {
|
||||
current = evm->next;
|
||||
while (current && current->func && retVal == MOD_CONT) {
|
||||
mod_current_module_name = current->mod_name;
|
||||
retVal = current->func(source, ac, av);
|
||||
mod_current_module_name = NULL;
|
||||
current = current->next;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
/* Free argument list we created */
|
||||
free(av);
|
||||
}
|
||||
|
||||
void event_process_hook(char *name, char *eventbuf)
|
||||
{
|
||||
int retVal = 0;
|
||||
EvtHook *current = NULL;
|
||||
EvtHook *evh;
|
||||
if (mod_current_evtbuffer) {
|
||||
free(mod_current_evtbuffer);
|
||||
}
|
||||
if (eventbuf) {
|
||||
mod_current_evtbuffer = sstrdup(eventbuf);
|
||||
} else {
|
||||
mod_current_evtbuffer = NULL;
|
||||
}
|
||||
/* Do something with the message. */
|
||||
evh = find_eventhook(name);
|
||||
if (evh) {
|
||||
if (evh->func) {
|
||||
mod_current_module_name = evh->mod_name;
|
||||
retVal = evh->func(eventbuf);
|
||||
mod_current_module_name = NULL;
|
||||
if (retVal == MOD_CONT) {
|
||||
current = evh->next;
|
||||
while (current && current->func && retVal == MOD_CONT) {
|
||||
mod_current_module_name = current->mod_name;
|
||||
retVal = current->func(eventbuf);
|
||||
mod_current_module_name = NULL;
|
||||
current = current->next;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Displays a message list for a given message.
|
||||
* Again this is of little use other than debugging.
|
||||
* @param m the message to display
|
||||
* @return 0 is returned and has no meaning
|
||||
*/
|
||||
int displayEventMessage(EvtMessage * evm)
|
||||
{
|
||||
EvtMessage *msg = NULL;
|
||||
int i = 0;
|
||||
alog("Displaying message list for %s", evm->name);
|
||||
for (msg = evm; msg; msg = msg->next) {
|
||||
alog("%d: 0x%p", ++i, (void *) msg);
|
||||
}
|
||||
alog("end");
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Displays a message list for a given message.
|
||||
* Again this is of little use other than debugging.
|
||||
* @param m the message to display
|
||||
* @return 0 is returned and has no meaning
|
||||
*/
|
||||
int displayEventHook(EvtHook * evh)
|
||||
{
|
||||
EvtHook *msg = NULL;
|
||||
int i = 0;
|
||||
alog("Displaying message list for %s", evh->name);
|
||||
for (msg = evh; msg; msg = msg->next) {
|
||||
alog("%d: 0x%p", ++i, (void *) msg);
|
||||
}
|
||||
alog("end");
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Display the message call stak.
|
||||
* Prints the call stack for a message based on the message name, again useful for debugging and little lese :)
|
||||
* @param name the name of the message to print info for
|
||||
* @return the return int has no relevence atm :)
|
||||
*/
|
||||
int displayHookFromHash(char *name)
|
||||
{
|
||||
EvtHookHash *current = NULL;
|
||||
int index = 0;
|
||||
index = CMD_HASH(name);
|
||||
if (debug > 1) {
|
||||
alog("trying to display message %s", name);
|
||||
}
|
||||
for (current = EVENTHOOKS[index]; current; current = current->next) {
|
||||
if (stricmp(name, current->name) == 0) {
|
||||
displayEventHook(current->evh);
|
||||
}
|
||||
}
|
||||
if (debug > 1) {
|
||||
alog("done displaying message %s", name);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Display the message call stak.
|
||||
* Prints the call stack for a message based on the message name, again useful for debugging and little lese :)
|
||||
* @param name the name of the message to print info for
|
||||
* @return the return int has no relevence atm :)
|
||||
*/
|
||||
int displayEvtMessageFromHash(char *name)
|
||||
{
|
||||
EvtMessageHash *current = NULL;
|
||||
int index = 0;
|
||||
index = CMD_HASH(name);
|
||||
if (debug > 1) {
|
||||
alog("trying to display message %s", name);
|
||||
}
|
||||
for (current = EVENT[index]; current; current = current->next) {
|
||||
if (stricmp(name, current->name) == 0) {
|
||||
displayEventMessage(current->evm);
|
||||
}
|
||||
}
|
||||
if (debug > 1) {
|
||||
alog("done displaying message %s", name);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
* Message Functions
|
||||
*******************************************************************************/
|
||||
|
||||
/**
|
||||
* Create a new Message struct.
|
||||
* @param name the name of the message
|
||||
* @param func a pointer to the function to call when we recive this message
|
||||
* @return a new Message object
|
||||
**/
|
||||
EvtMessage *createEventHandler(char *name,
|
||||
int (*func) (char *source, int ac,
|
||||
char **av))
|
||||
{
|
||||
EvtMessage *evm = NULL;
|
||||
if (!func) {
|
||||
return NULL;
|
||||
}
|
||||
if ((evm = malloc(sizeof(EvtMessage))) == NULL) {
|
||||
fatal("Out of memory!");
|
||||
}
|
||||
evm->name = sstrdup(name);
|
||||
evm->func = func;
|
||||
evm->mod_name = NULL;
|
||||
evm->next = NULL;
|
||||
return evm;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new Message struct.
|
||||
* @param name the name of the message
|
||||
* @param func a pointer to the function to call when we recive this message
|
||||
* @return a new Message object
|
||||
**/
|
||||
EvtHook *createEventHook(char *name, int (*func) (char *message))
|
||||
{
|
||||
EvtHook *evh = NULL;
|
||||
if (!func) {
|
||||
return NULL;
|
||||
}
|
||||
if ((evh = malloc(sizeof(EvtHook))) == NULL) {
|
||||
fatal("Out of memory!");
|
||||
}
|
||||
evh->name = sstrdup(name);
|
||||
evh->func = func;
|
||||
evh->mod_name = NULL;
|
||||
evh->next = NULL;
|
||||
return evh;
|
||||
}
|
||||
|
||||
/**
|
||||
* find a message in the given table.
|
||||
* Looks up the message <name> in the MessageHash given
|
||||
* @param MessageHash the message table to search for this command, will almost always be IRCD
|
||||
* @param name the name of the command were looking for
|
||||
* @return NULL if we cant find it, or a pointer to the Message if we can
|
||||
**/
|
||||
EvtMessage *findEventHandler(EvtMessageHash * msgEvtTable[],
|
||||
const char *name)
|
||||
{
|
||||
int idx;
|
||||
EvtMessageHash *current = NULL;
|
||||
if (!msgEvtTable || !name) {
|
||||
return NULL;
|
||||
}
|
||||
idx = CMD_HASH(name);
|
||||
|
||||
for (current = msgEvtTable[idx]; current; current = current->next) {
|
||||
if (stricmp(name, current->name) == 0) {
|
||||
return current->evm;
|
||||
}
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
* find a message in the given table.
|
||||
* Looks up the message <name> in the MessageHash given
|
||||
* @param MessageHash the message table to search for this command, will almost always be IRCD
|
||||
* @param name the name of the command were looking for
|
||||
* @return NULL if we cant find it, or a pointer to the Message if we can
|
||||
**/
|
||||
EvtHook *findEventHook(EvtHookHash * hookEvtTable[], const char *name)
|
||||
{
|
||||
int idx;
|
||||
EvtHookHash *current = NULL;
|
||||
if (!hookEvtTable || !name) {
|
||||
return NULL;
|
||||
}
|
||||
idx = CMD_HASH(name);
|
||||
|
||||
for (current = hookEvtTable[idx]; current; current = current->next) {
|
||||
if (stricmp(name, current->name) == 0) {
|
||||
return current->evh;
|
||||
}
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add the given message (m) to the MessageHash marking it as a core command
|
||||
* @param msgTable the MessageHash we want to add to
|
||||
* @param m the Message we are adding
|
||||
* @return MOD_ERR_OK on a successful add.
|
||||
**/
|
||||
int addCoreEventHandler(EvtMessageHash * msgEvtTable[], EvtMessage * evm)
|
||||
{
|
||||
if (!msgEvtTable || !evm) {
|
||||
return MOD_ERR_PARAMS;
|
||||
}
|
||||
evm->core = 1;
|
||||
return addEventHandler(msgEvtTable, evm);
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a message to the MessageHash.
|
||||
* @param msgTable the MessageHash we want to add a message to
|
||||
* @param m the Message we want to add
|
||||
* @return MOD_ERR_OK on a successful add.
|
||||
**/
|
||||
int addEventHandler(EvtMessageHash * msgEvtTable[], EvtMessage * evm)
|
||||
{
|
||||
/* We can assume both param's have been checked by this point.. */
|
||||
int index = 0;
|
||||
EvtMessageHash *current = NULL;
|
||||
EvtMessageHash *newHash = NULL;
|
||||
EvtMessageHash *lastHash = NULL;
|
||||
|
||||
if (!msgEvtTable || !evm) {
|
||||
return MOD_ERR_PARAMS;
|
||||
}
|
||||
|
||||
index = CMD_HASH(evm->name);
|
||||
|
||||
for (current = msgEvtTable[index]; current; current = current->next) {
|
||||
if (stricmp(evm->name, current->name) == 0) { /* the msg exist's we are a addHead */
|
||||
evm->next = current->evm;
|
||||
current->evm = evm;
|
||||
if (debug)
|
||||
alog("existing msg: (0x%p), new msg (0x%p)",
|
||||
(void *) evm->next, (void *) evm);
|
||||
return MOD_ERR_OK;
|
||||
}
|
||||
lastHash = current;
|
||||
}
|
||||
|
||||
if ((newHash = malloc(sizeof(EvtMessageHash))) == NULL) {
|
||||
fatal("Out of memory");
|
||||
}
|
||||
newHash->next = NULL;
|
||||
newHash->name = sstrdup(evm->name);
|
||||
newHash->evm = evm;
|
||||
|
||||
if (lastHash == NULL)
|
||||
msgEvtTable[index] = newHash;
|
||||
else
|
||||
lastHash->next = newHash;
|
||||
return MOD_ERR_OK;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a message to the MessageHash.
|
||||
* @param msgTable the MessageHash we want to add a message to
|
||||
* @param m the Message we want to add
|
||||
* @return MOD_ERR_OK on a successful add.
|
||||
**/
|
||||
int addEventHook(EvtHookHash * hookEvtTable[], EvtHook * evh)
|
||||
{
|
||||
/* We can assume both param's have been checked by this point.. */
|
||||
int index = 0;
|
||||
EvtHookHash *current = NULL;
|
||||
EvtHookHash *newHash = NULL;
|
||||
EvtHookHash *lastHash = NULL;
|
||||
|
||||
if (!hookEvtTable || !evh) {
|
||||
return MOD_ERR_PARAMS;
|
||||
}
|
||||
|
||||
index = CMD_HASH(evh->name);
|
||||
|
||||
for (current = hookEvtTable[index]; current; current = current->next) {
|
||||
if (stricmp(evh->name, current->name) == 0) { /* the msg exist's we are a addHead */
|
||||
evh->next = current->evh;
|
||||
current->evh = evh;
|
||||
if (debug)
|
||||
alog("existing msg: (0x%p), new msg (0x%p)",
|
||||
(void *) evh->next, (void *) evh);
|
||||
return MOD_ERR_OK;
|
||||
}
|
||||
lastHash = current;
|
||||
}
|
||||
|
||||
if ((newHash = malloc(sizeof(EvtHookHash))) == NULL) {
|
||||
fatal("Out of memory");
|
||||
}
|
||||
newHash->next = NULL;
|
||||
newHash->name = sstrdup(evh->name);
|
||||
newHash->evh = evh;
|
||||
|
||||
if (lastHash == NULL)
|
||||
hookEvtTable[index] = newHash;
|
||||
else
|
||||
lastHash->next = newHash;
|
||||
return MOD_ERR_OK;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add the given message (m) to the MessageHash marking it as a core command
|
||||
* @param msgTable the MessageHash we want to add to
|
||||
* @param m the Message we are adding
|
||||
* @return MOD_ERR_OK on a successful add.
|
||||
**/
|
||||
int addCoreEventHook(EvtHookHash * hookEvtTable[], EvtHook * evh)
|
||||
{
|
||||
if (!hookEvtTable || !evh) {
|
||||
return MOD_ERR_PARAMS;
|
||||
}
|
||||
evh->core = 1;
|
||||
return addEventHook(hookEvtTable, evh);
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a module message to the IRCD message hash
|
||||
* @param m the Message to add
|
||||
* @param pos the Position to add the message to, e.g. MOD_HEAD, MOD_TAIL, MOD_UNIQUE
|
||||
* @return MOD_ERR_OK on success, althing else on fail.
|
||||
**/
|
||||
int moduleAddEventHandler(EvtMessage * evm)
|
||||
{
|
||||
int status;
|
||||
|
||||
if (!evm) {
|
||||
return MOD_ERR_PARAMS;
|
||||
}
|
||||
|
||||
/* ok, this appears to be a module adding a message from outside of AnopeInit, try to look up its module struct for it */
|
||||
if ((mod_current_module_name) && (!mod_current_module)) {
|
||||
mod_current_module = findModule(mod_current_module_name);
|
||||
}
|
||||
|
||||
if (!mod_current_module) {
|
||||
return MOD_ERR_UNKNOWN;
|
||||
} /* shouldnt happen */
|
||||
evm->core = 0;
|
||||
if (!evm->mod_name) {
|
||||
evm->mod_name = sstrdup(mod_current_module->name);
|
||||
}
|
||||
|
||||
status = addEventHandler(EVENT, evm);
|
||||
if (debug) {
|
||||
displayEvtMessageFromHash(evm->name);
|
||||
}
|
||||
return status;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a module message to the IRCD message hash
|
||||
* @param m the Message to add
|
||||
* @param pos the Position to add the message to, e.g. MOD_HEAD, MOD_TAIL, MOD_UNIQUE
|
||||
* @return MOD_ERR_OK on success, althing else on fail.
|
||||
**/
|
||||
int moduleAddEventHook(EvtHook * evh)
|
||||
{
|
||||
int status;
|
||||
|
||||
if (!evh) {
|
||||
return MOD_ERR_PARAMS;
|
||||
}
|
||||
|
||||
if ((mod_current_module_name) && (!mod_current_module)) {
|
||||
mod_current_module = findModule(mod_current_module_name);
|
||||
}
|
||||
|
||||
if (!mod_current_module) {
|
||||
return MOD_ERR_UNKNOWN;
|
||||
} /* shouldnt happen */
|
||||
evh->core = 0;
|
||||
if (!evh->mod_name) {
|
||||
evh->mod_name = sstrdup(mod_current_module->name);
|
||||
}
|
||||
|
||||
status = addEventHook(EVENTHOOKS, evh);
|
||||
if (debug) {
|
||||
displayHookFromHash(evh->name);
|
||||
}
|
||||
return status;
|
||||
}
|
||||
|
||||
/**
|
||||
* remove the given message from the IRCD message hash
|
||||
* @param name the name of the message to remove
|
||||
* @return MOD_ERR_OK on success, althing else on fail.
|
||||
**/
|
||||
int moduleEventDelHandler(char *name)
|
||||
{
|
||||
EvtMessage *evm;
|
||||
int status;
|
||||
|
||||
if (!mod_current_module) {
|
||||
return MOD_ERR_UNKNOWN;
|
||||
}
|
||||
evm = findEventHandler(EVENT, name);
|
||||
if (!evm) {
|
||||
return MOD_ERR_NOEXIST;
|
||||
}
|
||||
|
||||
status = delEventHandler(EVENT, evm, mod_current_module->name);
|
||||
if (debug) {
|
||||
displayEvtMessageFromHash(evm->name);
|
||||
}
|
||||
return status;
|
||||
}
|
||||
|
||||
/**
|
||||
* remove the given message from the IRCD message hash
|
||||
* @param name the name of the message to remove
|
||||
* @return MOD_ERR_OK on success, althing else on fail.
|
||||
**/
|
||||
int moduleEventDelHook(const char *name)
|
||||
{
|
||||
EvtHook *evh;
|
||||
int status;
|
||||
|
||||
if (!mod_current_module) {
|
||||
return MOD_ERR_UNKNOWN;
|
||||
}
|
||||
evh = findEventHook(EVENTHOOKS, name);
|
||||
if (!evh) {
|
||||
return MOD_ERR_NOEXIST;
|
||||
}
|
||||
|
||||
status = delEventHook(EVENTHOOKS, evh, mod_current_module->name);
|
||||
if (debug) {
|
||||
displayHookFromHash(evh->name);
|
||||
}
|
||||
return status;
|
||||
}
|
||||
|
||||
/**
|
||||
* remove the given message from the given message hash, for the given module
|
||||
* @param msgTable which MessageHash we are removing from
|
||||
* @param m the Message we want to remove
|
||||
* @mod_name the name of the module we are removing
|
||||
* @return MOD_ERR_OK on success, althing else on fail.
|
||||
**/
|
||||
int delEventHandler(EvtMessageHash * msgEvtTable[], EvtMessage * evm,
|
||||
char *mod_name)
|
||||
{
|
||||
int index = 0;
|
||||
EvtMessageHash *current = NULL;
|
||||
EvtMessageHash *lastHash = NULL;
|
||||
EvtMessage *tail = NULL, *last = NULL;
|
||||
|
||||
if (!evm || !msgEvtTable) {
|
||||
return MOD_ERR_PARAMS;
|
||||
}
|
||||
|
||||
index = CMD_HASH(evm->name);
|
||||
|
||||
for (current = msgEvtTable[index]; current; current = current->next) {
|
||||
if (stricmp(evm->name, current->name) == 0) {
|
||||
if (!lastHash) {
|
||||
tail = current->evm;
|
||||
if (tail->next) {
|
||||
while (tail) {
|
||||
if (mod_name && tail->mod_name
|
||||
&& (stricmp(mod_name, tail->mod_name) == 0)) {
|
||||
if (last) {
|
||||
last->next = tail->next;
|
||||
} else {
|
||||
current->evm = tail->next;
|
||||
}
|
||||
return MOD_ERR_OK;
|
||||
}
|
||||
last = tail;
|
||||
tail = tail->next;
|
||||
}
|
||||
} else {
|
||||
msgEvtTable[index] = current->next;
|
||||
free(current->name);
|
||||
return MOD_ERR_OK;
|
||||
}
|
||||
} else {
|
||||
tail = current->evm;
|
||||
if (tail->next) {
|
||||
while (tail) {
|
||||
if (mod_name && tail->mod_name
|
||||
&& (stricmp(mod_name, tail->mod_name) == 0)) {
|
||||
if (last) {
|
||||
last->next = tail->next;
|
||||
} else {
|
||||
current->evm = tail->next;
|
||||
}
|
||||
return MOD_ERR_OK;
|
||||
}
|
||||
last = tail;
|
||||
tail = tail->next;
|
||||
}
|
||||
} else {
|
||||
lastHash->next = current->next;
|
||||
free(current->name);
|
||||
return MOD_ERR_OK;
|
||||
}
|
||||
}
|
||||
}
|
||||
lastHash = current;
|
||||
}
|
||||
return MOD_ERR_NOEXIST;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* remove the given message from the given message hash, for the given module
|
||||
* @param msgTable which MessageHash we are removing from
|
||||
* @param m the Message we want to remove
|
||||
* @mod_name the name of the module we are removing
|
||||
* @return MOD_ERR_OK on success, althing else on fail.
|
||||
**/
|
||||
int delEventHook(EvtHookHash * hookEvtTable[], EvtHook * evh,
|
||||
char *mod_name)
|
||||
{
|
||||
int index = 0;
|
||||
EvtHookHash *current = NULL;
|
||||
EvtHookHash *lastHash = NULL;
|
||||
EvtHook *tail = NULL, *last = NULL;
|
||||
|
||||
if (!evh || !hookEvtTable) {
|
||||
return MOD_ERR_PARAMS;
|
||||
}
|
||||
|
||||
index = CMD_HASH(evh->name);
|
||||
|
||||
for (current = hookEvtTable[index]; current; current = current->next) {
|
||||
if (stricmp(evh->name, current->name)) {
|
||||
if (!lastHash) {
|
||||
tail = current->evh;
|
||||
if (tail->next) {
|
||||
while (tail) {
|
||||
if (mod_name && tail->mod_name
|
||||
&& (stricmp(mod_name, tail->mod_name) == 0)) {
|
||||
if (last) {
|
||||
last->next = tail->next;
|
||||
} else {
|
||||
current->evh = tail->next;
|
||||
}
|
||||
return MOD_ERR_OK;
|
||||
}
|
||||
last = tail;
|
||||
tail = tail->next;
|
||||
}
|
||||
} else {
|
||||
hookEvtTable[index] = current->next;
|
||||
free(current->name);
|
||||
return MOD_ERR_OK;
|
||||
}
|
||||
} else {
|
||||
tail = current->evh;
|
||||
if (tail->next) {
|
||||
while (tail) {
|
||||
if (mod_name && tail->mod_name
|
||||
&& (stricmp(mod_name, tail->mod_name) == 0)) {
|
||||
if (last) {
|
||||
last->next = tail->next;
|
||||
} else {
|
||||
current->evh = tail->next;
|
||||
}
|
||||
return MOD_ERR_OK;
|
||||
}
|
||||
last = tail;
|
||||
tail = tail->next;
|
||||
}
|
||||
} else {
|
||||
lastHash->next = current->next;
|
||||
free(current->name);
|
||||
return MOD_ERR_OK;
|
||||
}
|
||||
}
|
||||
}
|
||||
lastHash = current;
|
||||
}
|
||||
return MOD_ERR_NOEXIST;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Destory a message, freeing its memory.
|
||||
* @param m the message to be destroyed
|
||||
* @return MOD_ERR_SUCCESS on success
|
||||
**/
|
||||
int destroyEventHandler(EvtMessage * evm)
|
||||
{
|
||||
if (!evm) {
|
||||
return MOD_ERR_PARAMS;
|
||||
}
|
||||
if (evm->name) {
|
||||
free(evm->name);
|
||||
}
|
||||
evm->func = NULL;
|
||||
if (evm->mod_name) {
|
||||
free(evm->mod_name);
|
||||
}
|
||||
evm->next = NULL;
|
||||
return MOD_ERR_OK;
|
||||
}
|
||||
|
||||
/**
|
||||
* Destory a message, freeing its memory.
|
||||
* @param m the message to be destroyed
|
||||
* @return MOD_ERR_SUCCESS on success
|
||||
**/
|
||||
int destroyEventHook(EvtHook * evh)
|
||||
{
|
||||
if (!evh) {
|
||||
return MOD_ERR_PARAMS;
|
||||
}
|
||||
if (evh->name) {
|
||||
free(evh->name);
|
||||
}
|
||||
evh->func = NULL;
|
||||
if (evh->mod_name) {
|
||||
free(evh->mod_name);
|
||||
}
|
||||
evh->next = NULL;
|
||||
return MOD_ERR_OK;
|
||||
}
|
||||
@@ -683,6 +683,8 @@ int init(int ac, char **av)
|
||||
alog("Info: Not reflecting database records.");
|
||||
}
|
||||
#endif
|
||||
send_event(EVENT_CONNECT, EVENT_START);
|
||||
|
||||
/* Connect to the remote server */
|
||||
servsock = conn(RemoteServer, RemotePort, LocalHost, LocalPort);
|
||||
if (servsock < 0 && RemoteServer2) {
|
||||
@@ -715,6 +717,7 @@ int init(int ac, char **av)
|
||||
}
|
||||
|
||||
anope_cmd_connect(servernum);
|
||||
send_event(EVENT_CONNECT, EVENT_STOP);
|
||||
|
||||
sgets2(inbuf, sizeof(inbuf), servsock);
|
||||
if (strnicmp(inbuf, "ERROR", 5) == 0) {
|
||||
|
||||
+10
@@ -101,6 +101,7 @@ static int started = 0;
|
||||
|
||||
extern void expire_all(void)
|
||||
{
|
||||
send_event(EVENT_DB_EXPIRE, EVENT_START);
|
||||
waiting = -3;
|
||||
if (debug)
|
||||
alog("debug: Running expire routines");
|
||||
@@ -131,12 +132,15 @@ extern void expire_all(void)
|
||||
if (ProxyDetect)
|
||||
proxy_expire();
|
||||
#endif
|
||||
send_event(EVENT_DB_EXPIRE, EVENT_STOP);
|
||||
}
|
||||
|
||||
/*************************************************************************/
|
||||
|
||||
void save_databases(void)
|
||||
{
|
||||
send_event(EVENT_DB_SAVING, EVENT_START);
|
||||
|
||||
waiting = -2;
|
||||
if (debug)
|
||||
alog("debug: Saving FFF databases");
|
||||
@@ -207,6 +211,7 @@ void save_databases(void)
|
||||
}
|
||||
}
|
||||
#endif
|
||||
send_event(EVENT_DB_SAVING, EVENT_STOP);
|
||||
}
|
||||
|
||||
/*************************************************************************/
|
||||
@@ -216,6 +221,7 @@ void save_databases(void)
|
||||
static void services_restart(void)
|
||||
{
|
||||
alog("Restarting");
|
||||
send_event(EVENT_RESTART, EVENT_START);
|
||||
if (!quitmsg)
|
||||
quitmsg = "Restarting";
|
||||
anope_cmd_squit(ServerName, quitmsg);
|
||||
@@ -255,6 +261,8 @@ static void services_shutdown(void)
|
||||
{
|
||||
User *u, *next;
|
||||
|
||||
send_event(EVENT_SHUTDOWN, EVENT_START);
|
||||
|
||||
if (!quitmsg)
|
||||
quitmsg = "Terminating, reason unknown";
|
||||
alog("%s", quitmsg);
|
||||
@@ -272,6 +280,7 @@ static void services_shutdown(void)
|
||||
u = next;
|
||||
}
|
||||
}
|
||||
send_event(EVENT_SHUTDOWN, EVENT_STOP);
|
||||
disconn(servsock);
|
||||
}
|
||||
|
||||
@@ -430,6 +439,7 @@ void sighandler(int signum)
|
||||
if (signum == SIGSEGV) {
|
||||
do_backtrace(1);
|
||||
}
|
||||
send_event(EVENT_SIGNAL, quitmsg);
|
||||
|
||||
if (started) {
|
||||
services_shutdown();
|
||||
|
||||
+6
-4
@@ -18,16 +18,16 @@ include ../Makefile.inc.win32
|
||||
###########################################################################
|
||||
|
||||
OBJS = actions.obj base64.obj botserv.obj channels.obj chanserv.obj commands.obj compat.obj \
|
||||
converter.obj config.obj datafiles.obj encrypt.obj helpserv.obj hostserv.obj \
|
||||
converter.obj config.obj datafiles.obj encrypt.obj events.obj helpserv.obj hostserv.obj \
|
||||
init.obj language.obj list.obj log.obj mail.obj main.obj memory.obj memoserv.obj \
|
||||
messages.obj misc.obj modules.obj news.obj nickserv.obj operserv.obj \
|
||||
process.obj proxy.obj send.obj servers.obj sessions.obj slist.obj sockutil.obj \
|
||||
timeout.obj users.obj $(RDB_O) $(MYSQL_O) $(CAPAB_O)
|
||||
|
||||
SRCS = actions.c base64.c botserv.c channels.c chanserv.c commands.c compat.c converter.c \
|
||||
config.c datafiles.c encrypt.c helpserv.c hostserv.c init.c language.c list.c log.c mail.c main.c \
|
||||
memory.c memoserv.c messages.c misc.c modules.c news.c nickserv.c operserv.c \
|
||||
process.c proxy.c send.c servers.obj sessions.c slist.c sockutil.c \
|
||||
config.c datafiles.c encrypt.c events.c helpserv.c hostserv.c init.c language.c list.c \
|
||||
log.c mail.c main.c memory.c memoserv.c messages.c misc.c modules.c news.c nickserv.c \
|
||||
operserv.c process.c proxy.c send.c servers.obj sessions.c slist.c sockutil.c \
|
||||
timeout.c users.c $(RDB_C) $(MYSQL_C) $(CAPAB_C)
|
||||
|
||||
###########################################################################
|
||||
@@ -69,6 +69,7 @@ config.obj: config.c ..\include\services.h
|
||||
converter.obj: converter.c ..\include\services.h ..\include\datafiles.h
|
||||
datafiles.obj: datafiles.c ..\include\services.h ..\include\datafiles.h
|
||||
encrypt.obj: encrypt.c ..\include\encrypt.h ..\include\sysconf.h
|
||||
events.obj: events.c ..\include\modules.h ..\include\language.h ..\include\version.h
|
||||
init.obj: init.c ..\include\services.h
|
||||
hostserv.obj: hostserv.c ..\include\services.h ..\include\pseudo.h
|
||||
language.obj: language.c ..\include\services.h ..\include\language.h
|
||||
@@ -79,6 +80,7 @@ main.obj: main.c ..\include\services.h ..\include\
|
||||
memory.obj: memory.c ..\include\services.h
|
||||
memoserv.obj: memoserv.c ..\include\services.h ..\include\pseudo.h
|
||||
messages.obj: messages.c ..\include\services.h ..\include\messages.h ..\include\language.h
|
||||
modules.obj: modules.c ..\include\modules.h ..\include\language.h ..\include\version.h
|
||||
misc.obj: misc.c ..\include\services.h ..\include\language.h
|
||||
news.obj: news.c ..\include\services.h ..\include\pseudo.h
|
||||
nickserv.obj: nickserv.c ..\include\services.h ..\include\pseudo.h
|
||||
|
||||
+9
-1
@@ -814,9 +814,17 @@ void EnforceQlinedNick(char *nick, char *killer)
|
||||
int nickIsServices(char *nick, int bot)
|
||||
{
|
||||
int found = 0;
|
||||
char *s;
|
||||
|
||||
if (!nick) {
|
||||
return found;
|
||||
return found;
|
||||
}
|
||||
|
||||
s = strchr(nick, '@');
|
||||
if (s) {
|
||||
*s++ = 0;
|
||||
if (stricmp(s, ServerName) != 0)
|
||||
return found;
|
||||
}
|
||||
|
||||
if (s_NickServ && (stricmp(nick, s_NickServ) == 0))
|
||||
|
||||
@@ -0,0 +1,53 @@
|
||||
/**
|
||||
* Simple module to show the usage of event messages and hooks
|
||||
* This module is an example, and has no useful purpose!
|
||||
*
|
||||
* Please visit http://modules.anope.org for useful modules!
|
||||
*
|
||||
**/
|
||||
|
||||
#include "module.h"
|
||||
|
||||
#define AUTHOR "Anope"
|
||||
#define VERSION "1.1"
|
||||
|
||||
int my_nick(char *source, int ac, char **av);
|
||||
int my_save(char *message);
|
||||
|
||||
int AnopeInit(int argc, char **argv)
|
||||
{
|
||||
EvtMessage *msg = NULL;
|
||||
EvtHook *hook = NULL;
|
||||
int status;
|
||||
msg = createEventHandler("NICK", my_nick);
|
||||
status = moduleAddEventHandler(msg);
|
||||
|
||||
hook = createEventHook(EVENT_DB_SAVING, my_save);
|
||||
status = moduleAddEventHook(hook);
|
||||
|
||||
moduleAddAuthor(AUTHOR);
|
||||
moduleAddVersion(VERSION);
|
||||
return MOD_CONT;
|
||||
}
|
||||
|
||||
void AnopeFini(void)
|
||||
{
|
||||
/* unloading */
|
||||
}
|
||||
|
||||
int my_nick(char *source, int ac, char **av)
|
||||
{
|
||||
alog("Internal Event - nick is %s",av[0]);
|
||||
return MOD_CONT;
|
||||
}
|
||||
|
||||
int my_save(char *message)
|
||||
{
|
||||
if (!stricmp(message, EVENT_START)) {
|
||||
alog("Saving the databases! has started");
|
||||
} else {
|
||||
alog("Saving the databases is complete");
|
||||
}
|
||||
return MOD_CONT;
|
||||
}
|
||||
|
||||
@@ -1,2 +1,2 @@
|
||||
SRCS=hs_moo.c ircd_catserv.c
|
||||
SRCS=hs_moo.c ircd_catserv.c events.c
|
||||
|
||||
|
||||
@@ -2306,6 +2306,7 @@ static int do_confirm(User * u)
|
||||
else
|
||||
notice_lang(s_NickServ, u, NICK_REGISTERED_NO_MASK,
|
||||
u->nick);
|
||||
send_event(EVENT_NICK_REGISTED, u->nick);
|
||||
#ifndef USE_ENCRYPTION
|
||||
notice_lang(s_NickServ, u, NICK_PASSWORD_IS, na->nc->pass);
|
||||
#endif
|
||||
@@ -2804,6 +2805,8 @@ static int do_drop(User * u)
|
||||
(na->nc->email ? na->nc->email : "none"));
|
||||
delnick(na);
|
||||
|
||||
send_event(EVENT_NICK_DROPPED, nick);
|
||||
|
||||
if (!is_mine) {
|
||||
if (WallDrop)
|
||||
anope_cmd_global(s_NickServ, "\2%s\2 used DROP on \2%s\2",
|
||||
@@ -4282,6 +4285,7 @@ static int do_forbid(User * u)
|
||||
|
||||
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, nick);
|
||||
} else {
|
||||
alog("%s: Valid FORBID for %s by %s failed", s_NickServ, nick,
|
||||
u->nick);
|
||||
|
||||
+1
-1
@@ -246,7 +246,7 @@ void process()
|
||||
av[0] to see if its a service nick if so assign mod_current_buffer the
|
||||
value from AV[1] else just assign av[0] - TSL */
|
||||
if (av[0]) {
|
||||
if (nickIsServices(av[0], 0)) {
|
||||
if (nickIsServices(av[0], 1)) {
|
||||
if (av[1]) {
|
||||
mod_current_buffer = sstrdup(av[1]);
|
||||
} else {
|
||||
|
||||
@@ -58,11 +58,13 @@ void vsend_cmd(const char *source, const char *fmt, va_list args)
|
||||
|
||||
if (source) {
|
||||
sockprintf(servsock, ":%s %s\r\n", source, buf);
|
||||
eventprintf(":%s %s", source, buf);
|
||||
if (debug) {
|
||||
alog("debug: Sent: :%s %s", source, buf);
|
||||
}
|
||||
} else {
|
||||
sockprintf(servsock, "%s\r\n", buf);
|
||||
eventprintf("%s", buf);
|
||||
if (debug) {
|
||||
alog("debug: Sent: %s", buf);
|
||||
}
|
||||
|
||||
@@ -645,6 +645,7 @@ User *do_nick(const char *source, char *nick, char *username, char *host,
|
||||
} else {
|
||||
user->svid = 1;
|
||||
}
|
||||
send_event(EVENT_NEWNICK, nick);
|
||||
|
||||
} else {
|
||||
/* An old user changing nicks. */
|
||||
@@ -685,6 +686,7 @@ User *do_nick(const char *source, char *nick, char *username, char *host,
|
||||
}
|
||||
|
||||
change_user_nick(user, nick);
|
||||
send_event(EVENT_CHANGE_NICK, nick);
|
||||
|
||||
if ((old_na ? old_na->nc : NULL) ==
|
||||
(user->na ? user->na->nc : NULL))
|
||||
|
||||
+5
-1
@@ -8,10 +8,14 @@
|
||||
VERSION_MAJOR="1"
|
||||
VERSION_MINOR="7"
|
||||
VERSION_PATCH="8"
|
||||
VERSION_BUILD="573"
|
||||
VERSION_BUILD="574"
|
||||
|
||||
# $Log$
|
||||
#
|
||||
# BUILD : 1.7.8 (574)
|
||||
# BUGS : N/A
|
||||
# NOTES : Internal Events, Win32 can build with encryption, nickIsServices() works if format is nick@services
|
||||
#
|
||||
# BUILD : 1.7.8 (573)
|
||||
# BUGS : 296
|
||||
# NOTES : mod_current_buffer was not set in all possible cases
|
||||
|
||||
Reference in New Issue
Block a user