/*
- * Cleanup routine to be called when the server is shutting down.
+ * Cleanup routine to be called when the server is shutting down. Returns the needed exit code.
*/
-void master_cleanup(int exitcode) {
+int master_cleanup(int exitcode) {
struct CleanupFunctionHook *fcn;
static int already_cleaning_up = 0;
syslog(LOG_NOTICE, "citserver: Exiting with status %d\n", exitcode);
fflush(stdout); fflush(stderr);
- if (restart_server != 0)
- exit(1);
- if ((running_as_daemon != 0) && ((exitcode == 0) ))
+ if (restart_server != 0) {
+ exitcode = 1;
+ }
+ else if ((running_as_daemon != 0) && ((exitcode == 0) )) {
exitcode = CTDLEXIT_SHUTDOWN;
- exit(exitcode);
+ }
+ return(exitcode);
}
void cit_oneline_backtrace(void);
void cit_panic_backtrace(int SigNum);
void master_startup (void);
-void master_cleanup (int exitcode);
+int master_cleanup (int exitcode);
void set_wtmpsupp (char *newtext);
void set_wtmpsupp_to_current_room(void);
void do_command_loop(void);
#ifdef HAVE_DB_H
#include <db.h>
#elif defined(HAVE_DB4_DB_H)
-#include <db4/db.h>
+#include <db5/db.h>
#else
-#error Neither <db.h> nor <db4/db.h> was found by configure. Install db4-devel.
+#error Neither <db.h> nor <db5/db.h> was found by configure. Install db5-devel.
#endif
-
-#if DB_VERSION_MAJOR < 4 || DB_VERSION_MINOR < 1
-#error Citadel requires Berkeley DB v4.1 or newer. Please upgrade.
+#if DB_VERSION_MAJOR < 5
+#error Citadel requires Berkeley DB v5.0 or newer. Please upgrade.
#endif
-
#include <libcitadel.h>
#include "ctdl_module.h"
#include "citserver.h"
#include "config.h"
-
static DB *dbp[MAXCDB]; /* One DB handle for each Citadel database */
static DB_ENV *dbenv; /* The DB environment (global) */
dbenv->set_paniccall(dbenv, dbpanic);
dbenv->set_errcall(dbenv, cdb_verbose_err);
dbenv->set_errpfx(dbenv, "ctdl");
-#if (DB_VERSION_MAJOR > 4) || ( (DB_VERSION_MAJOR == 4) && (DB_VERSION_MINOR >= 3) )
dbenv->set_msgcall(dbenv, cdb_verbose_log);
-#endif
dbenv->set_verbose(dbenv, DB_VERB_DEADLOCK, 1);
dbenv->set_verbose(dbenv, DB_VERB_RECOVERY, 1);
#include <stdio.h>
#include <sys/types.h>
#include <grp.h>
+#include <sys/file.h>
#include <libcitadel.h>
#include "citserver.h"
void go_threading(void);
+
+
+/*
+ * Create or remove a lock file, so we only have one Citadel Server running at a time.
+ */
+void ctdl_lockfile(int yo) {
+ static char lockfilename[SIZ];
+ static FILE *fp;
+
+
+ if (yo) {
+ syslog(LOG_DEBUG, "Creating lockfile");
+ snprintf(lockfilename, sizeof lockfilename, "%s/citadel.lock", ctdl_run_dir);
+ fp = fopen(lockfilename, "w");
+ if (!fp) {
+ syslog(LOG_ERR, "Cannot open or create %s", lockfilename);
+ exit(CTDLEXIT_DB);
+ }
+ if (flock(fileno(fp), (LOCK_EX|LOCK_NB)) != 0) {
+ syslog(LOG_ERR, "Cannot lock %s , is another citserver running?", lockfilename);
+ exit(CTDLEXIT_DB);
+ }
+ return;
+ }
+
+ syslog(LOG_DEBUG, "Removing lockfile");
+ unlink(lockfilename);
+ flock(fileno(fp), LOCK_UN);
+ fclose(fp);
+}
+
+
+
+
+
+
/*
* Here's where it all begins.
*/
#endif
+ ctdl_lockfile(1);
+
/* Initialize... */
init_sysdep();
go_threading();
- master_cleanup(exit_signal);
- return(0);
+ int exit_code = master_cleanup(exit_signal);
+ ctdl_lockfile(0);
+ return(exit_code);
}