diff options
author | brain <brain@e03df62e-2008-0410-955e-edbf42e46eb7> | 2007-08-11 12:05:31 +0000 |
---|---|---|
committer | brain <brain@e03df62e-2008-0410-955e-edbf42e46eb7> | 2007-08-11 12:05:31 +0000 |
commit | 9595db021dbfc77f0b0bd81ddc01b2578435aa22 (patch) | |
tree | 17aa8a4c5eb434a4a34971e65f41deb15396c8e9 | |
parent | 0f4caa76984ab4f15f8e69b4a396eb38f3a7fd4d (diff) |
Allow rehash to attempt to load missing (and new) lib/cmd_*.so files, to allow users to fix an emergency situation you can create by trying to reload a corrupt .so without needing a restart
git-svn-id: http://svn.inspircd.org/repository/trunk/inspircd@7712 e03df62e-2008-0410-955e-edbf42e46eb7
-rw-r--r-- | include/command_parse.h | 11 | ||||
-rw-r--r-- | src/command_parse.cpp | 41 | ||||
-rw-r--r-- | src/configreader.cpp | 3 |
3 files changed, 40 insertions, 15 deletions
diff --git a/include/command_parse.h b/include/command_parse.h index 58f63a802..2c3605613 100644 --- a/include/command_parse.h +++ b/include/command_parse.h @@ -56,10 +56,6 @@ class CoreExport CommandParser : public classbase */ void ProcessCommand(userrec *user, std::string &cmd); - /** Insert the default RFC1459 commands into the command hash. - */ - void SetupCommandTable(); - /** Finds the init_command symbol in a .so file * @param v A function pointer to be initialized * @param h A valid shared object handle @@ -198,6 +194,13 @@ class CoreExport CommandParser : public classbase * @return True if the command was added */ bool CreateCommand(command_t *f, void* so_handle = NULL); + + /** Insert the default RFC1459 commands into the command hash. + * Ignore any already loaded commands. + * @param user User to spool errors to, or if NULL, when an error occurs spool the errors to + * stdout then exit with EXIT_STATUS_HANDLER. + */ + void SetupCommandTable(userrec* user); }; /** Command handler class for the RELOAD command. diff --git a/src/command_parse.cpp b/src/command_parse.cpp index 6be50dd96..4e374d622 100644 --- a/src/command_parse.cpp +++ b/src/command_parse.cpp @@ -445,7 +445,7 @@ bool CommandParser::CreateCommand(command_t *f, void* so_handle) CommandParser::CommandParser(InspIRCd* Instance) : ServerInstance(Instance) { para.resize(128); - this->SetupCommandTable(); + this->SetupCommandTable(NULL); } bool CommandParser::FindSym(void** v, void* h) @@ -512,7 +512,7 @@ CmdResult cmd_reload::Handle(const char** parameters, int pcnt, userrec *user) } else { - user->WriteServ("NOTICE %s :*** Could not reload command '%s'", user->nick, parameters[0]); + user->WriteServ("NOTICE %s :*** Could not reload command '%s' -- fix this problem, then /REHASH as soon as possible!", user->nick, parameters[0]); return CMD_FAILURE; } } @@ -523,6 +523,10 @@ const char* CommandParser::LoadCommand(const char* name) void* h; command_t* (*cmd_factory_func)(InspIRCd*); + /* Command already exists? Succeed silently - this is needed for REHASH */ + if (RFCCommands.find(name) != RFCCommands.end()) + return NULL; + snprintf(filename, MAXBUF, "%s/%s", LIBRARYDIR, name); h = dlopen(filename, RTLD_NOW | RTLD_GLOBAL); @@ -541,12 +545,15 @@ const char* CommandParser::LoadCommand(const char* name) return NULL; } -void CommandParser::SetupCommandTable() +void CommandParser::SetupCommandTable(userrec* user) { RFCCommands.clear(); - printf("\nLoading core commands"); - fflush(stdout); + if (!user) + { + printf("\nLoading core commands"); + fflush(stdout); + } DIR* library = opendir(LIBRARYDIR); if (library) @@ -556,20 +563,32 @@ void CommandParser::SetupCommandTable() { if (match(entry->d_name, "cmd_*.so")) { - printf("."); - fflush(stdout); + if (!user) + { + printf("."); + fflush(stdout); + } const char* err = this->LoadCommand(entry->d_name); if (err) { - printf("Error loading %s: %s", entry->d_name, err); - exit(EXIT_STATUS_BADHANDLER); + if (user) + { + user->WriteServ("NOTICE %s :*** Failed to load core command %s: %s", entry->d_name, err); + } + else + { + printf("Error loading %s: %s", entry->d_name, err); + exit(EXIT_STATUS_BADHANDLER); + } } } } closedir(library); - printf("\n"); + if (!user) + printf("\n"); } - this->CreateCommand(new cmd_reload(ServerInstance)); + if (cmdlist.find("RELOAD") == cmdlist.end()) + this->CreateCommand(new cmd_reload(ServerInstance)); } diff --git a/src/configreader.cpp b/src/configreader.cpp index 46bb9231e..050276525 100644 --- a/src/configreader.cpp +++ b/src/configreader.cpp @@ -920,6 +920,9 @@ void ServerConfig::Read(bool bail, userrec* user) ServerInstance->Log(DEFAULT,"Successfully unloaded %lu of %lu modules and loaded %lu of %lu modules.",(unsigned long)rem,(unsigned long)removed_modules.size(),(unsigned long)add,(unsigned long)added_modules.size()); } + /** Note: This is safe, the method checks for user == NULL */ + ServerInstance->Parser->SetupCommandTable(user); + if (user) user->WriteServ("NOTICE %s :*** Successfully rehashed server.", user->nick); else |