initialise server parameters from commandline

overwrite defaults with commandline parameters before first use
(log level settings used as an example)
This commit is contained in:
ac-stef
2017-06-27 15:15:23 +02:00
parent d6af5be3da
commit dd295bb54a
4 changed files with 107 additions and 25 deletions
+1 -1
View File
@@ -71,7 +71,7 @@ void exitlogging()
{
if(fp) { fclose(fp); fp = NULL; }
#ifdef AC_USE_SYSLOG
if(syslogthreshold < ACLOG_NUM) closelog();
if(enabled && syslogthreshold < ACLOG_NUM) closelog();
#endif
syslogthreshold = ACLOG_NUM;
enabled = false;
+28 -6
View File
@@ -4593,6 +4593,24 @@ void quitproc(int param)
exit(param == 2 ? EXIT_SUCCESS : EXIT_FAILURE); // 3 is the only reply on Win32 apparently, SIGINT == 2 == Ctrl-C
}
const char *loglevelnames[] = { "debug", "verbose", "info", "warning", "error", "disabled", "" };
SERVPARLISTF(logthreshold_console, 0, ACLOG_INFO, 0, loglevelnames, restartlogging, "CConsole log level");
SERVPARLISTF(logthreshold_syslog, 0, ACLOG_NUM, 0, loglevelnames, restartlogging, "CSyslog log level");
SERVPARLISTF(logthreshold_file, 0, ACLOG_INFO, 0, loglevelnames, restartlogging, "CLogfile log level");
void restartlogging()
{
if(isdedicated)
{
exitlogging();
string identity;
if(scl.logident[0]) filtertext(identity, scl.logident, FTXT__LOGIDENT);
else formatstring(identity)("%s#%d", scl.ip[0] ? scl.ip : "local", scl.serverport);
initlogging(identity, scl.syslogfacility, logthreshold_console, logthreshold_file, logthreshold_syslog, scl.logtimestamp, scl.logfilepath);
}
}
void initserver(bool dedicated)
{
copystring(servpubkey, "");
@@ -4602,16 +4620,20 @@ void initserver(bool dedicated)
sg->smapname[0] = '\0';
// start logging
string identity;
if(scl.logident[0]) filtertext(identity, scl.logident, FTXT__LOGIDENT);
else formatstring(identity)("%s#%d", scl.ip[0] ? scl.ip : "local", scl.serverport);
int conthres = scl.verbose > 1 ? ACLOG_DEBUG : (scl.verbose ? ACLOG_VERBOSE : ACLOG_INFO);
if(dedicated && !initlogging(identity, scl.syslogfacility, conthres, scl.filethres, scl.syslogthres, scl.logtimestamp, scl.logfilepath)) printf("WARNING: logging not started!\n");
initserverparameter("logthreshold_console", scl.verbose > 1 ? ACLOG_DEBUG : (scl.verbose ? ACLOG_VERBOSE : ACLOG_INFO));
initserverparameter("logthreshold_syslog", scl.syslogthres);
initserverparameter("logthreshold_file", scl.filethres);
if((isdedicated = dedicated))
{
restartlogging();
if(!logcheck(ACLOG_ERROR)) printf("WARNING: logging not started!\n");
}
logline(ACLOG_INFO, "logging local AssaultCube server (version %d, protocol %d/%d) now..", AC_VERSION, SERVER_PROTOCOL_VERSION, EXT_VERSION);
copystring(sg->servdesc_current, scl.servdesc_full);
servermsinit(dedicated);
if((isdedicated = dedicated))
if(isdedicated)
{
serverparameters.init(scl.parfilepath);
if(serverparameters.load()) serverparameters.read(); // do this early, so the parameters are properly set during initialisation
+63 -18
View File
@@ -1,16 +1,22 @@
// serverfiles.h
// abuse globals to register server parameters
extern int addservparint(const char *name, int minval, int cur, int maxval, const char *list[], int *storage, int *shadowstorage, void (*fun)(), bool logchanges, bool fromfile, const char *desc);
extern bool addservparstr(const char *name, int minlen, int maxlen, int filt, const char *cur, char *storage, char *shadowstorage, void (*fun)(), bool logchanges, bool fromfile, const char *desc);
#ifdef _DEBUG
#define SERVPAR(name, min, cur, max, desc) int last_##name, name = addservparint(#name, min, cur, max, NULL, &name, &last_##name, NULL, false, true, desc)
#define SERVPARLIST(name, min, cur, max, list, desc) int last_##name, name = addservparint(#name, min, cur, max, list, &name, &last_##name, NULL, false, true, desc)
#define SERVPARF(name, min, cur, max, body, desc) extern int last_##name, name; void var_##name() { body; } int last_##name, name = addservparint(#name, min, cur, max, NULL,&name, &last_##name, var_##name, false, true, desc)
#define SERVPARF(name, min, cur, max, fun, desc) extern void fun(); int last_##name, name = addservparint(#name, min, cur, max, NULL,&name, &last_##name, fun, false, true, desc)
#define SERVPARLISTF(name, min, cur, max, list, fun, desc) extern void fun(); int last_##name, name = addservparint(#name, min, cur, max, list, &name, &last_##name, fun, false, true, desc)
#define SERVSTR(name, cur, min, max, filt, desc) char last_##name[max+1], name[max+1]; bool __sdummy_##name = addservparstr(#name, min, max, filt, cur, name, last_##name, NULL, false, true, desc)
#define SERVSTRF(name, cur, min, max, filt, fun, desc) char last_##name[max+1], name[max+1]; extern void fun(); bool __sdummy_##name = addservparstr(#name, min, max, filt, cur, name, last_##name, fun, false, true, desc)
#else
#define SERVPAR(name, min, cur, max, desc) int last_##name, name = addservparint(#name, min, cur, max, NULL, &name, &last_##name, NULL, false, true, NULL)
#define SERVPARLIST(name, min, cur, max, list, desc) int last_##name, name = addservparint(#name, min, cur, max, list, &name, &last_##name, NULL, false, true, NULL)
#define SERVPARF(name, min, cur, max, body, desc) extern int last_##name, name; void var_##name() { body; } int last_##name, name = addservparint(#name, min, cur, max, NULL, &name, &last_##name, var_##name, false, true, NULL)
#define SERVPARF(name, min, cur, max, fun, desc) extern void fun(); int last_##name, name = addservparint(#name, min, cur, max, NULL,&name, &last_##name, fun, false, true, NULL)
#define SERVPARLISTF(name, min, cur, max, list, fun, desc) extern void fun(); int last_##name, name = addservparint(#name, min, cur, max, list, &name, &last_##name, fun, false, true, NULL)
#define SERVSTR(name, cur, min, max, filt, desc) char last_##name[max+1], name[max+1]; bool __sdummy_##name = addservparstr(#name, min, max, filt, cur, name, last_##name, NULL, false, true, NULL)
#define SERVSTRF(name, cur, min, max, filt, fun, desc) char last_##name[max+1], name[max+1]; extern void fun(); bool __sdummy_##name = addservparstr(#name, min, max, filt, cur, name, last_##name, fun, false, true, NULL)
#endif
#define CONFIG_MAXPAR 11
@@ -1584,40 +1590,40 @@ struct servpar
const char *desc;
int chapter;
#endif
bool log; // log value changes (careful!)
bool logchanges; // log value changes (careful!)
bool fromfile; // true: value can be set by config file, false: value is set by server
servpar() {}
// SID_INT
servpar(int type, const char *name, int minval, int maxval, const char *list[], int *i, int *shadow_i, int defval, void (*fun)(), bool log, bool fromfile, const char *_desc)
: type(type), name(name), minval(minval), maxval(maxval), i(i), shadow_i(shadow_i), fun(fun), list(list), defaultint(defval), log(log), fromfile(fromfile)
servpar(int type, const char *name, int minval, int maxval, const char *list[], int *i, int *shadow_i, int defval, void (*fun)(), bool logchanges, bool fromfile, const char *_desc)
: type(type), name(name), minval(minval), maxval(maxval), i(i), shadow_i(shadow_i), fun(fun), list(list), defaultint(defval), logchanges(logchanges), fromfile(fromfile)
{ DEBUGCODE(desc = _desc); }
// SID_STR
servpar(int type, const char *name, int minlen, int maxlen, int filter, char *s, char *shadow_s, const char *defaultstr, void (*fun)(), bool log, int fromfile, const char *_desc)
: type(type), name(name), minlen(minlen), maxlen(maxlen), s(s), shadow_s(shadow_s), fun(fun), defaultstr(defaultstr), filter(filter), log(log), fromfile(fromfile)
servpar(int type, const char *name, int minlen, int maxlen, int filter, char *s, char *shadow_s, const char *defaultstr, void (*fun)(), bool logchanges, int fromfile, const char *_desc)
: type(type), name(name), minlen(minlen), maxlen(maxlen), s(s), shadow_s(shadow_s), fun(fun), defaultstr(defaultstr), filter(filter), logchanges(logchanges), fromfile(fromfile)
{ DEBUGCODE(desc = _desc;) }
};
hashtable<const char *, servpar> *servpars = NULL;
int addservparint(const char *name, int minval, int cur, int maxval, const char *list[], int *storage, int *shadowstorage, void (*fun)(), bool log, bool fromfile, const char *desc)
int addservparint(const char *name, int minval, int cur, int maxval, const char *list[], int *storage, int *shadowstorage, void (*fun)(), bool logchanges, bool fromfile, const char *desc)
{
if(!servpars) servpars = new hashtable<const char *, servpar>;
if(list && minval == maxval) while(list[maxval - minval + 1][0]) maxval++; // get list length
ASSERT(cur >= minval && cur <= maxval);
servpar v(SID_INT, name, minval, maxval, list, storage, shadowstorage, cur, fun, log, fromfile, desc);
servpar v(SID_INT, name, minval, maxval, list, storage, shadowstorage, cur, fun, logchanges, fromfile, desc);
servpars->access(name, v);
*shadowstorage = cur;
return cur;
}
bool addservparstr(const char *name, int minlen, int maxlen, int filt, const char *cur, char *storage, char *shadowstorage, void (*fun)(), bool log, bool fromfile, const char *desc)
bool addservparstr(const char *name, int minlen, int maxlen, int filt, const char *cur, char *storage, char *shadowstorage, void (*fun)(), bool logchanges, bool fromfile, const char *desc)
{
if(!servpars) servpars = new hashtable<const char *, servpar>;
ASSERT(maxlen > minlen && minlen >= 0 && int(strlen(cur)) >= minlen && int(strlen(cur)) <= maxlen);
servpar v(SID_STR, name, minlen, maxlen, filt, storage, shadowstorage, cur, fun, log, fromfile, desc);
servpar v(SID_STR, name, minlen, maxlen, filt, storage, shadowstorage, cur, fun, logchanges, fromfile, desc);
servpars->access(name, v);
strncpy(storage, cur, maxlen + 1);
strncpy(shadowstorage, cur, maxlen + 1);
@@ -1671,8 +1677,11 @@ struct serverparameter : serverconfigfile
{
if(*id.i != *id.shadow_i)
{
if(id.fun) ((void (__cdecl *)())id.fun)();
int tmp = *id.i;
*id.i = *id.shadow_i;
*id.shadow_i = tmp; // for the duration of fun(), last_parname _is_ actually the old value (at any other time, it's the next value)
if(id.fun) ((void (__cdecl *)())id.fun)();
*id.shadow_i = *id.i;
}
break;
}
@@ -1680,8 +1689,16 @@ struct serverparameter : serverconfigfile
{
if(strcmp(id.s, id.shadow_s))
{
if(id.fun) ((void (__cdecl *)())id.fun)();
strncpy(id.s, id.shadow_s, id.maxlen + 1);
if(id.fun)
{
char tmp[id.maxlen + 1];
strncpy(tmp, id.s, id.maxlen + 1);
strncpy(id.s, id.shadow_s, id.maxlen + 1);
strncpy(id.shadow_s, tmp, id.maxlen + 1); // for the duration of fun(), last_parname _is_ actually the old value (at any other time, it's the next value)
((void (__cdecl *)())id.fun)();
strncpy(id.shadow_s, id.s, id.maxlen + 1);
}
else strncpy(id.s, id.shadow_s, id.maxlen + 1);
}
break;
}
@@ -1701,11 +1718,38 @@ struct serverparameter : serverconfigfile
}
};
// optionally overwrite builtin default values with commandline parameters - before updating from file starts
void initserverparameter(const char *name, int value)
{
ASSERT(servpars);
servpar *id = servpars->access(name);
ASSERT(id && id->type == SID_INT);
if(value >= id->minval && value <= id->maxval) *id->i = *id->shadow_i = value;
}
void initserverparameter(const char *name, const char *value)
{
ASSERT(servpars);
servpar *id = servpars->access(name);
ASSERT(id && id->type == SID_STR);
string tmp;
filtertext(tmp, value, id->filter);
int len = (int)strlen(tmp);
if(len >= id->minlen && len <= id->maxlen)
{
strncpy(id->s, value, id->maxlen + 1);
strncpy(id->shadow_s, value, id->maxlen + 1);
}
}
// write a nice template for serverparameters.cfg
#ifdef _DEBUG
int siddocsort(servpar **a, servpar **b) { return (*a)->chapter == (*b)->chapter ? strcmp((*a)->name, (*b)->name) : (*a)->chapter - (*b)->chapter; }
const char *siddocchapters[] = { "dDebug switches", "mMisc settings", "vVote settings", "gMaprot settings", "sServer setup settings", "" };
const char *siddocchaptersorting = "sgvmd";
const char *siddocchapters[] = { "dDebug switches", "mMisc settings", "vVote settings", "gMaprot settings", "sServer setup settings", "CCommandline switch overrides", "" };
const char *siddocchaptersorting = "sgvmdC", *siddocchaptercommentedout = "C";
void serverparameters_dumpdocu(char *fname)
{
@@ -1735,6 +1779,7 @@ void serverparameters_dumpdocu(char *fname)
if(ch < 0) f->printf("\n// **** untitled chapter %c ****\n\n", lastchap);
else f->printf("\n// **** %s ****\n\n", siddocchapters[ch] + 1);
}
const char *commentout = strchr(siddocchaptercommentedout, id.desc[0]) != NULL ? "//" : "";
switch(id.type)
{
case SID_INT:
@@ -1744,12 +1789,12 @@ void serverparameters_dumpdocu(char *fname)
{
for(int k = 0; id.list[k] && id.list[k][0]; k++) f->printf(", %d:%s", id.minval + k, id.list[k]);
}
f->printf("\n%s:%d\n\n", id.name, id.defaultint);
f->printf("\n%s%s:%d\n\n", commentout, id.name, id.defaultint);
break;
}
case SID_STR:
{
f->printf("// %s %s\n// string [%d..%d chars], default \"%s\"\n%s:%s\n\n", id.name, id.desc + 1, id.minlen, id.maxlen, id.defaultstr, id.name, id.defaultstr);
f->printf("// %s %s\n// string [%d..%d chars], default \"%s\"\n%s%s:%s\n\n", id.name, id.desc + 1, id.minlen, id.maxlen, id.defaultstr, commentout, id.name, id.defaultstr);
break;
}
}