]> git.pond.sub.org Git - empserver/commitdiff
New server option -E to choose what to do on oops
authorMarkus Armbruster <armbru@pond.sub.org>
Mon, 21 Apr 2008 19:35:46 +0000 (21:35 +0200)
committerMarkus Armbruster <armbru@pond.sub.org>
Mon, 21 Apr 2008 19:52:27 +0000 (21:52 +0200)
Three options: abort, crash-dump, nothing.  crash-dump works by
aborting a fork.  It isn't implemented for Windows.

The oops action is no longer tied to daemon mode, but -d still implies
-E abort for convenience.

include/misc.h
man/emp_server.6
src/lib/gen/log.c
src/server/main.c

index 6169d1bfc31437ba644a19a74e43ee49044ac551..2bf4c082583304643352ee3d2327c7d862ebae8b 100644 (file)
 #define hours(x)       (60*60*(x))
 #define days(x)                (60*60*24*(x))
 
-extern int debug;
+enum oops_action {
+    OOPS_ABORT,
+    OOPS_CRASH_DUMP,
+    OOPS_NOTHING
+};
+extern enum oops_action oops_action;
 
 /*
  * If EXPR is true, an internal error occured.
index d7b387b994e552db4834eb3153fea96975ca9d70..ef4c1c7757c02ce6ac8f4b6417793c4bcbf0c8be 100644 (file)
@@ -13,7 +13,10 @@ emp_server \- Empire server
 .BI \-e " configfile"
 ]
 [
-.BI \-R " random-seed"
+.BI \-E " action"
+]
+[
+.BI \-R " seed"
 ]
 .if \nw \{\
 .br
@@ -42,14 +45,20 @@ pages within the game.
 .TP
 .B \-d
 Debug mode.  This will prevent the server from forking itself into the
-background.  It will also make it abort when it detects an internal
-error.  You normally want to use this flag if you are running
+background.  Implies -E abort.  You normally want to use this flag if
+you are running
 .B emp_server
 from within a debugger.
 .TP
 .BI \-e " configfile"
 Use game configuration in \fIconfigfile\fR.
 .TP
+.BI \-E " action"
+What to do on recoverable internal error ("oops"): \fBabort\fP,
+\fBcrash\-dump\fP (but continue), \fBnothing\fP (default).
+.ie \nw \fBcrash-dump\fP is not implemented for Windows.
+.el \fBcrash-dump\fP works by aborting a fork of the server process.
+.TP
 .B \-h
 Help.  Print brief usage information and exit.
 .if \nw \{\
@@ -73,7 +82,7 @@ Uninstall the Windows Service with the specified name.\}
 .B \-s
 Enable thread stack checking.
 .TP
-.B \-R " random-seed"
+.B \-R " seed"
 Set the seed for random function.
 .TP
 .B \-v
index 80799b79e18554e73abbef33bfe2d36155095c67..6cdca129cb2a8ac6b5b7621578e8dc9031b9dea6 100644 (file)
@@ -46,8 +46,7 @@
 #include "player.h"
 #include "prototypes.h"
 
-/* Debugging?  If yes call abort() on internal error.  */
-int debug = 1;
+enum oops_action oops_action = OOPS_ABORT;
 
 static char logfile[32];
 static int logfd = -1;
@@ -133,7 +132,18 @@ int
 oops(char *msg, char *file, int line)
 {
     logerror("Oops: %s in %s:%d", msg ? msg : "bug", file, line);
-    if (debug) abort();
+    switch (oops_action) {
+    case OOPS_ABORT:
+       abort();
+    case OOPS_CRASH_DUMP:
+#ifndef _WIN32
+       if (fork() == 0)
+           abort();
+#endif
+       /* fall through */
+    case OOPS_NOTHING:
+       break;
+    }
     return 1;
 }
 
index 1a794af8397e1eca487ec3d31ef53bb47c4ffab8..34409820c8c410a0d6de3f6ee4f5a6d563a16c17 100644 (file)
@@ -54,6 +54,7 @@
 #include "file.h"
 #include "journal.h"
 #include "land.h"
+#include "match.h"
 #include "misc.h"
 #include "nat.h"
 #include "nuke.h"
@@ -92,13 +93,22 @@ static char pidfname[] = "server.pid";
 /* Run as daemon?  If yes, detach from controlling terminal etc. */
 static int daemonize = 1;
 
+static void
+help(char *program_name, char *complaint)
+{
+    if (complaint)
+       fprintf(stderr, "%s: %s\n", program_name, complaint);
+    fprintf(stderr, "Try -h for help.\n");
+}
+
 static void
 print_usage(char *program_name)
 {
     printf("Usage: %s [OPTION]...\n"
-          "  -d              debug mode\n"
+          "  -d              debug mode, implies -E abort\n"
           "  -e CONFIG-FILE  configuration file\n"
           "                  (default %s)\n"
+          "  -E ACTION       what to do on oops: abort, crash-dump, nothing (default)\n"
           "  -h              display this help and exit\n"
 #ifdef _WIN32
           "  -i              install service `%s'\n"
@@ -122,6 +132,7 @@ print_usage(char *program_name)
 int
 main(int argc, char **argv)
 {
+    static char *oops_key[] = { "abort", "crash-dump", "nothing", NULL };
     int flags = 0;
 #if defined(_WIN32)
     int install_service_set = 0;
@@ -130,28 +141,36 @@ main(int argc, char **argv)
     int remove_service_set = 0;
 #endif
     char *config_file = NULL;
-    int op, sig;
+    int op, idx, sig;
     unsigned seed = time(NULL);
 
-    debug = 0;
+    oops_action = OOPS_NOTHING;
 
 #ifdef _WIN32
 # define XOPTS "iI:uU:"
 #else
 # define XOPTS
 #endif
-    while ((op = getopt(argc, argv, "de:hpsR:v" XOPTS)) != EOF) {
+    while ((op = getopt(argc, argv, "de:E:hpsR:v" XOPTS)) != EOF) {
        switch (op) {
        case 'p':
            flags |= EMPTH_PRINT;
            /* fall through */
        case 'd':
-           debug = 1;
+           oops_action = OOPS_ABORT;
            daemonize = 0;
            break;
        case 'e':
            config_file = optarg;
            break;
+       case 'E':
+           idx = stmtch(optarg, oops_key, 0, sizeof(*oops_key));
+           if (idx < 0) {
+               help(argv[0], "invalid argument for -E");
+               return EXIT_FAILURE;
+           }
+           oops_action = idx;
+           break;
 #if defined(_WIN32)
        case 'I':
            service_name = optarg;
@@ -179,19 +198,19 @@ main(int argc, char **argv)
            print_usage(argv[0]);
            return EXIT_SUCCESS;
        default:
-           fprintf(stderr, "Try -h for help.\n");
+           help(argv[0], NULL);
            return EXIT_FAILURE;
        }
     }
 
 #if defined(_WIN32)
-    if ((debug || flags || config_file != NULL) &&
+    if ((!daemonize || flags || config_file != NULL) &&
        remove_service_set) {
        fprintf(stderr, "Can't use -p, -s, -d or -e with either "
            "-u or -U options\n");
        exit(EXIT_FAILURE);
     }
-    if ((debug || flags) && install_service_set) {
+    if ((!daemonize || flags) && install_service_set) {
        fprintf(stderr, "Can't use -d, -p or -s with either "
            "-i or -I options\n");
        exit(EXIT_FAILURE);