mirror of
https://github.com/anope/anope.git
synced 2026-06-22 22:06:37 +02:00
24dbf4e00c
git-svn-id: http://anope.svn.sourceforge.net/svnroot/anope/trunk@1969 5417fbe8-f217-4b02-8779-1006273d7864
577 lines
18 KiB
C++
577 lines
18 KiB
C++
/* Modular support
|
|
*
|
|
* (C) 2003-2009 Anope Team
|
|
* Contact us at team@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$
|
|
*/
|
|
|
|
#ifndef MODULES_H
|
|
#define MODULES_H
|
|
|
|
#include <time.h>
|
|
#include "services.h"
|
|
#include <stdio.h>
|
|
|
|
/* Cross OS compatibility macros */
|
|
#ifdef _WIN32
|
|
typedef HMODULE ano_module_t;
|
|
|
|
#define dlopen(file, unused) LoadLibrary(file)
|
|
MDE const char *dlerror();
|
|
#define dlsym(file, symbol) (HMODULE)GetProcAddress(file, symbol)
|
|
#define dlclose(file) FreeLibrary(file) ? 0 : 1
|
|
#define ano_modclearerr() SetLastError(0)
|
|
#define MODULE_EXT ".so"
|
|
#else
|
|
typedef void * ano_module_t;
|
|
|
|
/* We call dlerror() here because it clears the module error after being
|
|
* called. This previously read 'errno = 0', but that didn't work on
|
|
* all POSIX-compliant architectures. This way the error is guaranteed
|
|
* to be cleared, POSIX-wise. -GD
|
|
*/
|
|
#define ano_modclearerr() dlerror()
|
|
#define MODULE_EXT ".so"
|
|
#endif
|
|
|
|
|
|
/*************************************************************************/
|
|
#define CMD_HASH(x) (((x)[0]&31)<<5 | ((x)[1]&31)) /* Will gen a hash from a string :) */
|
|
#define MAX_CMD_HASH 1024
|
|
|
|
/** The return value from commands.
|
|
*/
|
|
enum CommandReturn
|
|
{
|
|
MOD_CONT,
|
|
MOD_STOP
|
|
};
|
|
|
|
#define HOSTSERV HS_cmdTable /* using HOSTSERV etc. looks nicer than HS_cmdTable for modules */
|
|
#define BOTSERV BS_cmdTable
|
|
#define MEMOSERV MS_cmdTable
|
|
#define NICKSERV NS_cmdTable
|
|
#define CHANSERV CS_cmdTable
|
|
#define HELPSERV HE_cmdTable
|
|
#define OPERSERV OS_cmdTable
|
|
#define IRCD IRCD_cmdTable
|
|
#define MODULE_HASH Module_table
|
|
#define EVENT EVENT_cmdTable
|
|
#define EVENTHOOKS HOOK_cmdTable
|
|
|
|
/**********************************************************************
|
|
* Module Returns
|
|
**********************************************************************/
|
|
#define MOD_ERR_OK 0
|
|
#define MOD_ERR_MEMORY 1
|
|
#define MOD_ERR_PARAMS 2
|
|
#define MOD_ERR_EXISTS 3
|
|
#define MOD_ERR_NOEXIST 4
|
|
#define MOD_ERR_NOUSER 5
|
|
#define MOD_ERR_NOLOAD 6
|
|
#define MOD_ERR_NOUNLOAD 7
|
|
#define MOD_ERR_SYNTAX 8
|
|
#define MOD_ERR_NODELETE 9
|
|
#define MOD_ERR_UNKNOWN 10
|
|
#define MOD_ERR_FILE_IO 11
|
|
#define MOD_ERR_NOSERVICE 12
|
|
#define MOD_ERR_NO_MOD_NAME 13
|
|
|
|
/*************************************************************************/
|
|
/* Macros to export the Module API functions/variables */
|
|
#ifndef _WIN32
|
|
#define MDE
|
|
#else
|
|
#ifndef MODULE_COMPILE
|
|
#define MDE __declspec(dllexport)
|
|
#else
|
|
#define MDE __declspec(dllimport)
|
|
#endif
|
|
#endif
|
|
/*************************************************************************/
|
|
|
|
#if !defined(_WIN32)
|
|
#include <dlfcn.h>
|
|
/* Define these for systems without them */
|
|
#ifndef RTLD_NOW
|
|
#define RTLD_NOW 0
|
|
#endif
|
|
#ifndef RTLD_LAZY
|
|
#define RTLD_LAZY RTLD_NOW
|
|
#endif
|
|
#ifndef RTLD_GLOBAL
|
|
#define RTLD_GLOBAL 0
|
|
#endif
|
|
#ifndef RTLD_LOCAL
|
|
#define RTLD_LOCAL 0
|
|
#endif
|
|
#else
|
|
const char *ano_moderr();
|
|
#endif
|
|
|
|
typedef enum { CORE,PROTOCOL,THIRD,SUPPORTED,QATESTED,ENCRYPTION } MODType;
|
|
typedef enum { MOD_OP_LOAD, MOD_OP_UNLOAD } ModuleOperation;
|
|
|
|
/*************************************************************************/
|
|
/* Structure for information about a *Serv command. */
|
|
|
|
struct CommandHash;
|
|
typedef struct ModuleLang_ ModuleLang;
|
|
typedef struct ModuleHash_ ModuleHash;
|
|
typedef struct Message_ Message;
|
|
typedef struct MessageHash_ MessageHash;
|
|
typedef struct ModuleCallBack_ ModuleCallBack;
|
|
typedef struct EvtHook_ EvtHook;
|
|
typedef struct EvtHookHash_ EvtHookHash;
|
|
|
|
extern MDE CommandHash *HOSTSERV[MAX_CMD_HASH];
|
|
extern MDE CommandHash *BOTSERV[MAX_CMD_HASH];
|
|
extern MDE CommandHash *MEMOSERV[MAX_CMD_HASH];
|
|
extern MDE CommandHash *NICKSERV[MAX_CMD_HASH];
|
|
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 MDE ModuleHash *MODULE_HASH[MAX_CMD_HASH];
|
|
extern MDE EvtHookHash *EVENTHOOKS[MAX_CMD_HASH];
|
|
|
|
struct ModuleLang_ {
|
|
int argc;
|
|
char **argv;
|
|
};
|
|
|
|
/** Every services command is a class, inheriting from Command.
|
|
*/
|
|
class Command
|
|
{
|
|
public:
|
|
size_t MaxParams;
|
|
size_t MinParams;
|
|
std::string name;
|
|
|
|
/** Create a new command.
|
|
* @param min_params The minimum number of parameters the parser will require to execute this command
|
|
* @param max_params The maximum number of parameters the parser will create, after max_params, all will be combined into the last argument.
|
|
* NOTE: If max_params is not set (default), there is no limit to the max number of params.
|
|
*/
|
|
Command(const std::string &sname, size_t min_params, size_t max_params = 0) : MaxParams(max_params), MinParams(min_params), name(sname)
|
|
{
|
|
this->has_priv = NULL;
|
|
this->help_param1 = NULL;
|
|
this->help_param2 = NULL;
|
|
this->help_param3 = NULL;
|
|
this->help_param4 = NULL;
|
|
this->core = 0;
|
|
this->next = NULL;
|
|
this->mod_name = NULL;
|
|
this->service = NULL;
|
|
this->all_help = NULL;
|
|
this->regular_help = NULL;
|
|
this->oper_help = NULL;
|
|
this->admin_help = NULL;
|
|
this->root_help = NULL;
|
|
}
|
|
|
|
virtual ~Command()
|
|
{
|
|
this->has_priv = NULL;
|
|
if (this->mod_name) {
|
|
delete [] this->mod_name;
|
|
}
|
|
if (this->service) {
|
|
delete [] this->service;
|
|
}
|
|
this->next = NULL;
|
|
}
|
|
|
|
/** Execute this command.
|
|
* @param u The user executing the command.
|
|
*/
|
|
virtual CommandReturn Execute(User *u, std::vector<std::string> &) { return MOD_CONT; }
|
|
|
|
/** Requested when the user is requesting help on this command. Help on this command should be sent to the user.
|
|
* @param u The user requesting help
|
|
* @param subcommand The subcommand the user is requesting help on, or an empty string. (e.g. /ns help set foo bar lol gives a subcommand of "FOO BAR LOL")
|
|
* @return true if help was provided to the user, false otherwise.
|
|
*/
|
|
virtual bool OnHelp(User *u, const std::string &subcommand) { return false; }
|
|
|
|
/** Requested when the user provides bad syntax to this command (not enough params, etc).
|
|
* @param u The user executing the command.
|
|
*/
|
|
virtual void OnBadSyntax(User *u) { }
|
|
|
|
int (*has_priv)(User *u); /* Returns 1 if user may use command, else 0 */
|
|
|
|
char *help_param1;
|
|
char *help_param2;
|
|
char *help_param3;
|
|
char *help_param4;
|
|
|
|
/* Module related stuff */
|
|
int core; /* Can this command be deleted? */
|
|
char *mod_name; /* Name of the module who owns us, NULL for core's */
|
|
char *service; /* Service we provide this command for */
|
|
int (*all_help)(User *u);
|
|
int (*regular_help)(User *u);
|
|
int (*oper_help)(User *u);
|
|
int (*admin_help)(User *u);
|
|
int (*root_help)(User *u);
|
|
|
|
Command *next; /* Next command responsible for the same command */
|
|
};
|
|
/** Every module in Anope is actually a class.
|
|
*/
|
|
class CoreExport Module
|
|
{
|
|
private:
|
|
bool permanent;
|
|
public:
|
|
/** The module name (e.g. os_modload)
|
|
*/
|
|
std::string name;
|
|
|
|
/** The temporary path/filename
|
|
*/
|
|
std::string filename;
|
|
|
|
ano_module_t handle;
|
|
time_t created;
|
|
std::string version;
|
|
std::string author;
|
|
|
|
MODType type;
|
|
|
|
void (*nickHelp)(User *u); /* service 1 */
|
|
void (*chanHelp)(User *u); /* 2 */
|
|
void (*memoHelp)(User *u); /* 3 */
|
|
void (*botHelp)(User *u); /* 4 */
|
|
void (*operHelp)(User *u); /* 5 */
|
|
void (*hostHelp)(User *u); /* 6 */
|
|
void (*helpHelp)(User *u); /* 7 */
|
|
|
|
MessageHash *msgList[MAX_CMD_HASH];
|
|
ModuleLang lang[NUM_LANGS];
|
|
|
|
/** Creates and initialises a new module.
|
|
* @param loadernick The nickname of the user loading the module.
|
|
*/
|
|
Module(const std::string &modname, const std::string &loadernick);
|
|
|
|
/** Destroys a module, freeing resources it has allocated.
|
|
*/
|
|
~Module();
|
|
|
|
/** Sets a given type (CORE,PROTOCOL,3RD etc) on a module.
|
|
* @param type The type to set the module as.
|
|
*/
|
|
void SetType(MODType type);
|
|
|
|
/** Toggles the permanent flag on a module. If a module is permanent,
|
|
* then it may not be unloaded.
|
|
*
|
|
* Naturally, this setting should be used sparingly!
|
|
*
|
|
* @param state True if this module should be permanent, false else.
|
|
*/
|
|
void SetPermanent(bool state);
|
|
|
|
/** Retrieves whether or not a given module is permanent.
|
|
* @return true if the module is permanent, false else.
|
|
*/
|
|
bool GetPermanent();
|
|
|
|
/** Set the modules version info.
|
|
* @param version the version of the module
|
|
*/
|
|
void SetVersion(const std::string &version);
|
|
|
|
/** Set the modules author info
|
|
* @param author the author of the module
|
|
*/
|
|
void SetAuthor(const std::string &author);
|
|
|
|
/**
|
|
* Add output to nickserv help.
|
|
* when doing a /msg nickserv help, your function will be called to allow it to send out a notice() with the code you wish to dispaly
|
|
* @param func a pointer to the function which will display the code
|
|
**/
|
|
void SetNickHelp(void (*func)(User *));
|
|
|
|
/**
|
|
* Add output to chanserv help.
|
|
* when doing a /msg chanserv help, your function will be called to allow it to send out a notice() with the code you wish to dispaly
|
|
* @param func a pointer to the function which will display the code
|
|
**/
|
|
void SetChanHelp(void (*func)(User *));
|
|
|
|
/**
|
|
* Add output to memoserv help.
|
|
* when doing a /msg memoserv help, your function will be called to allow it to send out a notice() with the code you wish to dispaly
|
|
* @param func a pointer to the function which will display the code
|
|
**/
|
|
void SetMemoHelp(void (*func)(User *));
|
|
|
|
/**
|
|
* Add output to botserv help.
|
|
* when doing a /msg botserv help, your function will be called to allow it to send out a notice() with the code you wish to dispaly
|
|
* @param func a pointer to the function which will display the code
|
|
**/
|
|
void SetBotHelp(void (*func)(User *));
|
|
|
|
/**
|
|
* Add output to operserv help.
|
|
* when doing a /msg operserv help, your function will be called to allow it to send out a notice() with the code you wish to dispaly
|
|
* @param func a pointer to the function which will display the code
|
|
**/
|
|
void SetOperHelp(void (*func)(User *));
|
|
|
|
/**
|
|
* Add output to hostserv help.
|
|
* when doing a /msg hostserv help, your function will be called to allow it to send out a notice() with the code you wish to dispaly
|
|
* @param func a pointer to the function which will display the code
|
|
**/
|
|
void SetHostHelp(void (*func)(User *));
|
|
|
|
/**
|
|
* Add output to helpserv help.
|
|
* when doing a /msg helpserv help, your function will be called to allow it to send out a notice() with the code you wish to dispaly
|
|
* @param func a pointer to the function which will display the code
|
|
**/
|
|
void SetHelpHelp(void (*func)(User *));
|
|
|
|
/**
|
|
* Allow a module to add a set of language strings to anope
|
|
* @param langNumber the language number for the strings
|
|
* @param ac The language count for the strings
|
|
* @param av The language sring list.
|
|
**/
|
|
void InsertLanguage(int langNumber, int ac, const char **av);
|
|
|
|
/**
|
|
* Delete a language from a module
|
|
* @param langNumber the language Number to delete
|
|
**/
|
|
void DeleteLanguage(int langNumber);
|
|
|
|
/**
|
|
* Get the text of the given lanugage string in the corrent language, or
|
|
* in english.
|
|
* @param u The user to send the message to
|
|
* @param number The message number
|
|
**/
|
|
const char *GetLangString(User *u, int number);
|
|
|
|
/**
|
|
* Send a notice to the user in the correct language, or english.
|
|
* @param source Who sends the notice
|
|
* @param u The user to send the message to
|
|
* @param number The message number
|
|
* @param ... The argument list
|
|
**/
|
|
void NoticeLang(char *source, User * u, int number, ...);
|
|
|
|
/** 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 AddEventHook(EvtHook *evh);
|
|
|
|
/**
|
|
* 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 DelEventHook(const char *name);
|
|
|
|
/**
|
|
* Add a module provided command to the given service.
|
|
* e.g. AddCommand(NICKSERV,c,MOD_HEAD);
|
|
* @param cmdTable the services to add the command to
|
|
* @param c the command to add
|
|
* @param pos the position to add to, MOD_HEAD, MOD_TAIL, MOD_UNIQUE
|
|
* @see createCommand
|
|
* @return MOD_ERR_OK on successfully adding the command
|
|
*/
|
|
int AddCommand(CommandHash *cmdTable[], Command * c, int pos);
|
|
|
|
/**
|
|
* Delete a command from the service given.
|
|
* @param cmdTable the cmdTable for the services to remove the command from
|
|
* @param name the name of the command to delete from the service
|
|
* @return returns MOD_ERR_OK on success
|
|
*/
|
|
int DelCommand(CommandHash * cmdTable[], const char *name);
|
|
|
|
/**
|
|
* Adds a timed callback for the current module.
|
|
* This allows modules to request that anope executes one of there functions at a time in the future, without an event to trigger it
|
|
* @param name the name of the callback, this is used for refrence mostly, but is needed it you want to delete this particular callback later on
|
|
* @param when when should the function be executed, this is a time in the future, seconds since 00:00:00 1970-01-01 UTC
|
|
* @param func the function to be executed when the callback is ran, its format MUST be int func(int argc, char **argv);
|
|
* @param argc the argument count for the argv paramter
|
|
* @param atgv a argument list to be passed to the called function.
|
|
* @return MOD_ERR_OK on success, anything else on fail.
|
|
* @see moduleDelCallBack
|
|
**/
|
|
int AddCallback(const char *name, time_t when, int (*func) (int argc, char *argv[]), int argc, char **argv);
|
|
|
|
/**
|
|
* Allow modules to delete a timed callback by name.
|
|
* @param name the name of the callback they wish to delete
|
|
**/
|
|
void DelCallback(const char *name);
|
|
};
|
|
|
|
|
|
|
|
|
|
/** Used to manage modules.
|
|
*/
|
|
class CoreExport ModuleManager
|
|
{
|
|
public:
|
|
/** Load up a list of modules.
|
|
* @param total_modules The number of modules to load
|
|
* @param module_list The list of modules to load
|
|
**/
|
|
static void LoadModuleList(int total_modules, char **module_list);
|
|
|
|
/** Loads a given module.
|
|
* @param m the module to load
|
|
* @param u the user who loaded it, NULL for auto-load
|
|
* @return MOD_ERR_OK on success, anything else on fail
|
|
*/
|
|
static int LoadModule(const std::string &modname, User * u);
|
|
|
|
/** Unload the given module.
|
|
* @param m the module to unload
|
|
* @param u the user who unloaded it
|
|
* @return MOD_ERR_OK on success, anything else on fail
|
|
*/
|
|
static int UnloadModule(Module *m, User * u);
|
|
|
|
/** Run all pending module timer callbacks.
|
|
*/
|
|
static void RunCallbacks();
|
|
private:
|
|
/** Call the module_delete function to safely delete the module
|
|
* @param m the module to delete
|
|
*/
|
|
static void DeleteModule(Module *m);
|
|
};
|
|
|
|
|
|
|
|
struct ModuleHash_ {
|
|
char *name;
|
|
Module *m;
|
|
ModuleHash *next;
|
|
};
|
|
|
|
struct CommandHash {
|
|
char *name; /* Name of the command */
|
|
Command *c; /* Actual command */
|
|
CommandHash *next; /* Next command */
|
|
};
|
|
|
|
struct Message_ {
|
|
char *name;
|
|
int (*func)(const char *source, int ac, const char **av);
|
|
int core;
|
|
Message *next;
|
|
};
|
|
|
|
struct MessageHash_ {
|
|
char *name;
|
|
Message *m;
|
|
MessageHash *next;
|
|
};
|
|
|
|
struct ModuleCallBack_ {
|
|
char *name;
|
|
char *owner_name;
|
|
time_t when;
|
|
int (*func)(int argc, char *argv[]);
|
|
int argc;
|
|
char **argv;
|
|
ModuleCallBack *next;
|
|
};
|
|
|
|
struct EvtHook_ {
|
|
int (*func)(int argc, char **argv);
|
|
int core;
|
|
char *name;
|
|
char *mod_name;
|
|
EvtHook *next;
|
|
};
|
|
|
|
struct EvtHookHash_ {
|
|
char *name;
|
|
EvtHook *evh;
|
|
EvtHookHash *next;
|
|
};
|
|
|
|
|
|
/*************************************************************************/
|
|
/* Module Managment Functions */
|
|
MDE Module *findModule(const char *name); /* Find a module */
|
|
|
|
int encryption_module_init(); /* Load the encryption module */
|
|
int protocol_module_init(); /* Load the IRCD Protocol Module up*/
|
|
void moduleCallBackPrepForUnload(const char *mod_name);
|
|
MDE void moduleCallBackDeleteEntry(ModuleCallBack * prev);
|
|
MDE char *moduleGetLastBuffer();
|
|
MDE void moduleDisplayHelp(int service, User *u);
|
|
MDE int moduleAddHelp(Command * c, int (*func) (User * u));
|
|
MDE int moduleAddRegHelp(Command * c, int (*func) (User * u));
|
|
MDE int moduleAddOperHelp(Command * c, int (*func) (User * u));
|
|
MDE int moduleAddAdminHelp(Command * c, int (*func) (User * u));
|
|
MDE int moduleAddRootHelp(Command * c, int (*func) (User * u));
|
|
extern MDE char *mod_current_buffer;
|
|
|
|
/*************************************************************************/
|
|
/*************************************************************************/
|
|
/* Command Managment Functions */
|
|
Command *findCommand(CommandHash *cmdTable[], const char *name); /* Find a command */
|
|
|
|
/*************************************************************************/
|
|
|
|
/* Message Managment Functions */
|
|
MDE Message *createMessage(const char *name,int (*func)(const char *source, int ac, const char **av));
|
|
Message *findMessage(MessageHash *msgTable[], const char *name); /* Find a Message */
|
|
MDE int addMessage(MessageHash *msgTable[], Message *m, int pos); /* Add a Message to a Message table */
|
|
MDE int addCoreMessage(MessageHash *msgTable[], Message *m); /* Add a Message to a Message table */
|
|
int delMessage(MessageHash *msgTable[], Message *m); /* Del a Message from a msg table */
|
|
int destroyMessage(Message *m); /* destroy a Message*/
|
|
|
|
/*************************************************************************/
|
|
|
|
MDE EvtHook *createEventHook(const char *name, int (*func) (int argc, char **argv));
|
|
EvtHook *findEventHook(EvtHookHash * HookEvtTable[], const char *name);
|
|
int addCoreEventHook(EvtHookHash * HookEvtTable[], EvtHook * evh);
|
|
int delEventHook(EvtHookHash * HookEvtTable[], EvtHook * evh, const char *mod_name);
|
|
int destroyEventHook(EvtHook * evh);
|
|
|
|
/*************************************************************************/
|
|
|
|
MDE bool moduleMinVersion(int major,int minor,int patch,int build); /* Checks if the current version of anope is before or after a given verison */
|
|
|
|
/*************************************************************************/
|
|
/* Some IRCD protocol module support functions */
|
|
|
|
/** Update the protect deatials, could be either protect or admin etc.. */
|
|
MDE void updateProtectDetails(const char *level_info_protect_word, const char *level_info_protectme_word, const char *fant_protect_add, const char *fant_protect_del, const char *level_protect_word, const char *protect_set_mode, const char *protect_unset_mode);
|
|
|
|
/************************************************************************/
|
|
|
|
#endif
|
|
/* EOF */
|