It is possible, as I have this working on my mud currently. The easiest way that I found was to have three functions: do_hotboot, emergency_hotboot, and hotboot. do_hotboot is the same, but segvio call crash_hotboot(), which is basically this:void crash_hotboot(void)
{
echo_to_all(AT_RED,
"\n\rReality swirls and changes around you, and things are not quite as they were...\n\r",
0);
snprintf(log_buf, MSL, "%s", "Hotboot initiated by crash.");
log_string(log_buf);
hotboot(FALSE, TRUE);
}
So the command calls the player checks, safety stuff, etc, where this just writes the files and gets it over with.
Also, dunno if this helps, but this is my segvio code that will crashover and still produce a corestatic void SegVio(int signum)
{
pid_t p;
DESCRIPTOR_DATA *d;
char buf[MSL];
signum = 0;
log_string("SEGMENTATION VIOLATION");
log_string(lastplayercmd);
mudstrlcpy(lastplayercmd, "", MIL * 2);
if (sysdata.PORT)
{
signal(SIGPIPE, SIG_DFL);
signal(SIGSEGV, SIG_DFL);
signal(SIGTERM, SIG_DFL);
if ((p = fork()) == 0)
{
abort(); /* Abort child */
}
if (access("core", F_OK) == 0)
{
snprintf(buf, MSL, "%d.core", p);
rename("core", buf);
}
signal(SIGPIPE, SIG_IGN);
signal(SIGSEGV, SegVio);
signal(SIGTERM, SigTerm); /* Catch kill signals */
if (crashover == TRUE)
{
crashover = FALSE;
log_string("Crashover ready. Starting crashover.");
crash_hotboot();
}
else
{
log_string("Crashover not ready. Shutting down.");
abort();
}
if (crashover == TRUE)
{
crashover = FALSE;
echo_to_all(AT_RED,
"&RATTENTION!! Crash, Hold on while we try and recover.\a",
ECHOTAR_ALL);
for (d = first_descriptor; d; d = d->next)
flush_buffer(d, TRUE);
log_string("Crashover ready. Starting crashover.");
crash_hotboot();
}
else
{
log_string("Crashover not ready. Shutting down.");
abort();
}
}
abort();
}
One thing you want to be careful of is loops. If some of the data in the hotboot is being written and its corrupt, it will crash again, call the function, etc. Thats what the "if (crashover == TRUE)" call are for. Hope this helps. |