*/
-/* $Core */
#include "inspircd.h"
#include <signal.h>
*/
const char* ExitCodes[] =
{
- "No error", /* 0 */
- "DIE command", /* 1 */
- "execv() failed", /* 2 */
- "Internal error", /* 3 */
- "Config file error", /* 4 */
- "Logfile error", /* 5 */
- "POSIX fork failed", /* 6 */
- "Bad commandline parameters", /* 7 */
- "No ports could be bound", /* 8 */
- "Can't write PID file", /* 9 */
- "SocketEngine could not initialize", /* 10 */
- "Refusing to start up as root", /* 11 */
- "Found a <die> tag!", /* 12 */
- "Couldn't load module on startup", /* 13 */
- "Could not create windows forked process", /* 14 */
- "Received SIGTERM", /* 15 */
- "Bad command handler loaded", /* 16 */
- "RegisterServiceCtrlHandler failed", /* 17 */
- "UpdateSCMStatus failed", /* 18 */
- "CreateEvent failed" /* 19 */
+ "No error", // 0
+ "DIE command", // 1
+ "Config file error", // 2
+ "Logfile error", // 3
+ "POSIX fork failed", // 4
+ "Bad commandline parameters", // 5
+ "Can't write PID file", // 6
+ "SocketEngine could not initialize", // 7
+ "Refusing to start up as root", // 8
+ "Couldn't load module on startup", // 9
+ "Received SIGTERM" // 10
};
template<typename T> static void DeleteZero(T*&n)
void InspIRCd::Cleanup()
{
+ // Close all listening sockets
for (unsigned int i = 0; i < ports.size(); i++)
{
- /* This calls the constructor and closes the listening socket */
ports[i]->cull();
delete ports[i];
}
DeleteZero(this->Threads);
DeleteZero(this->Timers);
DeleteZero(this->SE);
- /* Close logging */
- this->Logs->CloseLogs();
+ Logs->CloseLogs();
DeleteZero(this->Logs);
}
-void InspIRCd::Restart(const std::string &reason)
-{
- /* SendError flushes each client's queue,
- * regardless of writeability state
- */
- this->SendError(reason);
-
- /* Figure out our filename (if theyve renamed it, we're boned) */
- std::string me;
-
- char** argv = Config->cmdline.argv;
-
-#ifdef _WIN32
- char module[MAX_PATH];
- if (GetModuleFileNameA(NULL, module, MAX_PATH))
- me = module;
-#else
- me = argv[0];
-#endif
-
- this->Cleanup();
-
- if (execv(me.c_str(), argv) == -1)
- {
- /* Will raise a SIGABRT if not trapped */
- throw CoreException(std::string("Failed to execv()! error: ") + strerror(errno));
- }
-}
-
void InspIRCd::SetSignals()
{
#ifndef _WIN32
void InspIRCd::QuickExit(int status)
{
- exit(0);
+ exit(status);
}
bool InspIRCd::DaemonSeed()
#else
signal(SIGTERM, InspIRCd::QuickExit);
- int childpid;
- if ((childpid = fork ()) < 0)
+ int childpid = fork();
+ if (childpid < 0)
return false;
else if (childpid > 0)
{
rlimit rl;
if (getrlimit(RLIMIT_CORE, &rl) == -1)
{
- this->Logs->Log("STARTUP",LOG_DEFAULT,"Failed to getrlimit()!");
+ this->Logs->Log("STARTUP", LOG_DEFAULT, "Failed to getrlimit()!");
return false;
}
rl.rlim_cur = rl.rlim_max;
if (setrlimit(RLIMIT_CORE, &rl) == -1)
- this->Logs->Log("STARTUP",LOG_DEFAULT,"setrlimit() failed, cannot increase coredump size.");
+ this->Logs->Log("STARTUP", LOG_DEFAULT, "setrlimit() failed, cannot increase coredump size.");
return true;
#endif
#ifndef _WIN32
std::string fname(filename);
if (fname.empty())
- fname = DATA_PATH "/inspircd.pid";
+ fname = ServerInstance->Config->Paths.PrependData("inspircd.pid");
std::ofstream outfile(fname.c_str());
if (outfile.is_open())
{
else
{
std::cout << "Failed to write PID-file '" << fname << "', exiting." << std::endl;
- this->Logs->Log("STARTUP",LOG_DEFAULT,"Failed to write PID-file '%s', exiting.",fname.c_str());
+ this->Logs->Log("STARTUP", LOG_DEFAULT, "Failed to write PID-file '%s', exiting.",fname.c_str());
Exit(EXIT_STATUS_PID);
}
#endif
* THIS MUST MATCH THE ORDER OF DECLARATION OF THE FUNCTORS, e.g. the methods
* themselves within the class.
*/
- OperQuit("OperQuit", NULL),
+ OperQuit("operquit", NULL),
GenRandom(&HandleGenRandom),
IsChannel(&HandleIsChannel),
- Rehash(&HandleRehash),
IsNick(&HandleIsNick),
IsIdent(&HandleIsIdent),
OnCheckExemption(&HandleOnCheckExemption)
FailedPortList pl;
int do_version = 0, do_nofork = 0, do_debug = 0,
do_nolog = 0, do_root = 0, do_testsuite = 0; /* flag variables */
- int c = 0;
// Initialize so that if we exit before proper initialization they're not deleted
this->Logs = 0;
// Create base manager classes early, so nothing breaks
this->Users = new UserManager;
- this->Users->unregistered_count = 0;
-
- this->Users->clientlist = new user_hash();
- this->Users->uuidlist = new user_hash();
this->chanlist = new chan_hash();
this->Config = new ServerConfig;
{ 0, 0, 0, 0 }
};
+ int c;
int index;
while ((c = getopt_long(argc, argv, ":c:", longopts, &index)) != -1)
{
if (do_version)
{
- std::cout << std::endl << VERSION << " r" << REVISION << std::endl;
+ std::cout << std::endl << VERSION << " " << REVISION << std::endl;
Exit(EXIT_STATUS_NOERROR);
}
#endif
{
std::cout << "ERROR: Cannot open config file: " << ConfigFileName << std::endl << "Exiting..." << std::endl;
- this->Logs->Log("STARTUP",LOG_DEFAULT,"Unable to open config file %s", ConfigFileName.c_str());
+ this->Logs->Log("STARTUP", LOG_DEFAULT, "Unable to open config file %s", ConfigFileName.c_str());
Exit(EXIT_STATUS_CONFIG);
}
}
std::cout << con_green << "(C) InspIRCd Development Team." << con_reset << std::endl << std::endl;
std::cout << "Developers:" << std::endl;
std::cout << con_green << "\tBrain, FrostyCoolSlug, w00t, Om, Special, peavey" << std::endl;
- std::cout << "\taquanight, psychon, dz, danieldg, jackmcbarn" << con_reset << std::endl << std::endl;
+ std::cout << "\taquanight, psychon, dz, danieldg, jackmcbarn" << std::endl;
+ std::cout << "\tAttila" << con_reset << std::endl << std::endl;
std::cout << "Others:\t\t\t" << con_green << "See /INFO Output" << con_reset << std::endl;
this->Modes = new ModeParser;
SE->RecoverFromFork();
- /* During startup we don't actually initialize this
- * in the thread engine.
+ /* During startup we read the configuration now, not in
+ * a seperate thread
*/
this->Config->Read();
this->Config->Apply(NULL, "");
// Initialize the UID generator with our sid
this->UIDGen.init(Config->sid);
- /* set up fake client again this time with the correct uid */
+ // Create the server user for this server
this->FakeClient = new FakeUser(Config->sid, Config->ServerName);
- // Get XLine to do it's thing.
- this->XLines->CheckELines();
+ // This is needed as all new XLines are marked pending until ApplyLines() is called
this->XLines->ApplyLines();
int bounditems = BindPorts(pl);
this->Modules->LoadAll();
- /* Just in case no modules were loaded - fix for bug #101 */
+ // Build ISupport as ModuleManager::LoadAll() does not do it
this->ISupport.Build();
Config->ApplyDisabledCommands(Config->DisabledCommands);
}
else
{
- Logs->Log("STARTUP", LOG_DEFAULT,"Keeping pseudo-tty open as we are running in the foreground.");
+ Logs->Log("STARTUP", LOG_DEFAULT, "Keeping pseudo-tty open as we are running in the foreground.");
}
#else
/* Set win32 service as running, if we are running as a service */
if (ret == -1)
{
- this->Logs->Log("SETGROUPS", LOG_DEFAULT, "setgroups() failed (wtf?): %s", strerror(errno));
+ this->Logs->Log("STARTUP", LOG_DEFAULT, "setgroups() failed (wtf?): %s", strerror(errno));
this->QuickExit(0);
}
if (!g)
{
- this->Logs->Log("SETGUID", LOG_DEFAULT, "getgrnam() failed (bad user?): %s", strerror(errno));
+ this->Logs->Log("STARTUP", LOG_DEFAULT, "getgrnam() failed (bad user?): %s", strerror(errno));
this->QuickExit(0);
}
if (ret == -1)
{
- this->Logs->Log("SETGUID", LOG_DEFAULT, "setgid() failed (bad user?): %s", strerror(errno));
+ this->Logs->Log("STARTUP", LOG_DEFAULT, "setgid() failed (bad user?): %s", strerror(errno));
this->QuickExit(0);
}
}
if (!u)
{
- this->Logs->Log("SETGUID", LOG_DEFAULT, "getpwnam() failed (bad user?): %s", strerror(errno));
+ this->Logs->Log("STARTUP", LOG_DEFAULT, "getpwnam() failed (bad user?): %s", strerror(errno));
this->QuickExit(0);
}
if (ret == -1)
{
- this->Logs->Log("SETGUID", LOG_DEFAULT, "setuid() failed (bad user?): %s", strerror(errno));
+ this->Logs->Log("STARTUP", LOG_DEFAULT, "setuid() failed (bad user?): %s", strerror(errno));
this->QuickExit(0);
}
}
#endif
}
-int InspIRCd::Run()
+void InspIRCd::Run()
{
/* See if we're supposed to be running the test suite rather than entering the mainloop */
if (Config->cmdline.TestSuite)
{
TestSuite* ts = new TestSuite;
delete ts;
- Exit(0);
+ return;
}
UpdateTime();
if (this->ConfigThread && this->ConfigThread->IsDone())
{
/* Rehash has completed */
- this->Logs->Log("CONFIG",LOG_DEBUG,"Detected ConfigThread exiting, tidying up...");
+ this->Logs->Log("CONFIG", LOG_DEBUG, "Detected ConfigThread exiting, tidying up...");
this->ConfigThread->Finish();
if ((TIME.tv_sec % 3600) == 0)
{
Users->GarbageCollect();
- FOREACH_MOD(I_OnGarbageCollect, OnGarbageCollect());
+ FOREACH_MOD(OnGarbageCollect, ());
}
Timers->TickTimers(TIME.tv_sec);
- this->DoBackgroundUserStuff();
+ Users->DoBackgroundUserStuff();
if ((TIME.tv_sec % 5) == 0)
{
- FOREACH_MOD(I_OnBackgroundTimer,OnBackgroundTimer(TIME.tv_sec));
+ FOREACH_MOD(OnBackgroundTimer, (TIME.tv_sec));
SNO->FlushSnotices();
}
}
s_signal = 0;
}
}
-
- return 0;
-}
-
-/**********************************************************************************/
-
-/* this returns true when all modules are satisfied that the user should be allowed onto the irc server
- * (until this returns true, a user will block in the waiting state, waiting to connect up to the
- * registration timeout maximum seconds)
- */
-bool InspIRCd::AllModulesReportReady(LocalUser* user)
-{
- ModResult res;
- FIRST_MOD_RESULT(OnCheckReady, res, (user));
- return (res == MOD_RES_PASSTHRU);
}
sig_atomic_t InspIRCd::s_signal = 0;