SYSCF bits

(This covers some thing that Pat found and some things I found while working
on those.)
Unscramble duplicate use of GREPPATH and GDBPATH symbols.
Add some more info to config.h.
Make missing SYSCF_FILE a fatal error.
Make a parse error in SYSCF_FILE a fatal error.
Rename PANICTRACE_GLIBC (et al) to PANICTRACE_LIBC (et al) since FreeBSD
 and Mac OS X (at least) also implement the needed API.
Allow SYSCF_FILE to be unreadable by the user (for setgid installs).
If SYSCF, do NOT fall back to the compiled in WIZARD account.
Put WIZARD into sysopt and remove special cases in authorize_wizard_mode().
This commit is contained in:
keni
2012-01-27 20:15:31 +00:00
parent a871ad06e9
commit 1d219b4e1b
11 changed files with 147 additions and 82 deletions

View File

@@ -150,7 +150,8 @@
* If SYSCF is defined, the following configuration info is * If SYSCF is defined, the following configuration info is
* available in a global config space, with the compiled-in * available in a global config space, with the compiled-in
* entries as defaults: * entries as defaults:
* WIZARDS ( a value of * allows anyone to be wizard) * WIZARDS (a value of * allows anyone to be wizard)
* (this does NOT default to compiled-in value)
* MAXPLAYERS (see MAX_NR_OF_PLAYERS above and nethack.sh) * MAXPLAYERS (see MAX_NR_OF_PLAYERS above and nethack.sh)
* SUPPORT (how to get local support)(no default) * SUPPORT (how to get local support)(no default)
* RECOVER (how to recover a game at your site)(no default) * RECOVER (how to recover a game at your site)(no default)
@@ -164,6 +165,10 @@
* *
* The following options select how the config space is stored: * The following options select how the config space is stored:
* SYSCF_FILE in the named file * SYSCF_FILE in the named file
*
* The following options pertain to crash reporting:
* GREPPATH (the path to the system grep(1) utility)
* GDBPATH (the path to the system gdb(1) program)
*/ */
#ifndef WIZARD /* allow for compile-time or Makefile changes */ #ifndef WIZARD /* allow for compile-time or Makefile changes */
@@ -177,6 +182,13 @@
# endif # endif
#endif #endif
#ifndef GDBPATH
# define GDBPATH "/usr/bin/gdb"
#endif
#ifndef GREPPATH
# define GREPPATH "/bin/grep"
#endif
#define LOGFILE "logfile" /* larger file for debugging purposes */ #define LOGFILE "logfile" /* larger file for debugging purposes */
#define NEWS "news" /* the file containing the latest hack news */ #define NEWS "news" /* the file containing the latest hack news */
#define PANICLOG "paniclog" /* log of panic and impossible events */ #define PANICLOG "paniclog" /* log of panic and impossible events */

View File

@@ -742,7 +742,7 @@ E void FDECL(unlock_file, (const char *));
#ifdef USER_SOUNDS #ifdef USER_SOUNDS
E boolean FDECL(can_read_file, (const char *)); E boolean FDECL(can_read_file, (const char *));
#endif #endif
E void FDECL(read_config_file, (const char *, int)); E boolean FDECL(read_config_file, (const char *, int));
E void FDECL(check_recordfile, (const char *)); E void FDECL(check_recordfile, (const char *));
#if defined(WIZARD) #if defined(WIZARD)
E void NDECL(read_wizkit); E void NDECL(read_wizkit);
@@ -2357,6 +2357,9 @@ E void NDECL(port_help);
E void FDECL(sethanguphandler, (void (*)(int))); E void FDECL(sethanguphandler, (void (*)(int)));
E boolean NDECL(authorize_wizard_mode); E boolean NDECL(authorize_wizard_mode);
E boolean FDECL(check_user_string, (char *)); E boolean FDECL(check_user_string, (char *));
# ifdef SYSCF_FILE
E void NDECL(assure_syscf_file);
# endif
#endif /* UNIX */ #endif /* UNIX */
/* ### unixtty.c ### */ /* ### unixtty.c ### */
@@ -2384,6 +2387,9 @@ E int NDECL(dosh);
# if defined(SHELL) || defined(DEF_PAGER) || defined(DEF_MAILREADER) # if defined(SHELL) || defined(DEF_PAGER) || defined(DEF_MAILREADER)
E int FDECL(child, (int)); E int FDECL(child, (int));
# endif # endif
# ifdef PANICTRACE
E boolean FDECL(file_exists, (const char *));
# endif
#endif /* UNIX */ #endif /* UNIX */
/* ### unixres.c ### */ /* ### unixres.c ### */

View File

@@ -382,7 +382,10 @@ struct savefile_info {
#endif #endif
/* The following are meaningless if PANICTRACE is not defined: */ /* The following are meaningless if PANICTRACE is not defined: */
#if defined(__linux__) && defined(__GLIBC__) && (__GLIBC__ >= 2) #if defined(__linux__) && defined(__GLIBC__) && (__GLIBC__ >= 2)
# define PANICTRACE_GLIBC # define PANICTRACE_LIBC
#endif
#if defined(MACOSX)
# define PANICTRACE_LIBC
#endif #endif
#ifdef UNIX #ifdef UNIX
# define PANICTRACE_GDB # define PANICTRACE_GDB

View File

@@ -25,8 +25,8 @@ struct sysopt {
char *gdbpath; char *gdbpath;
char *greppath; char *greppath;
int panictrace_gdb; int panictrace_gdb;
# ifdef PANICTRACE_GLIBC # ifdef PANICTRACE_LIBC
int panictrace_glibc; int panictrace_libc;
# endif # endif
#endif #endif
int seduce; int seduce;

View File

@@ -77,13 +77,13 @@ extern void FDECL(nethack_exit,(int));
#ifdef PANICTRACE #ifdef PANICTRACE
# include <errno.h> # include <errno.h>
# ifdef PANICTRACE_GLIBC # ifdef PANICTRACE_LIBC
# include <execinfo.h> # include <execinfo.h>
# endif # endif
/* What do we try and in what order? Tradeoffs: /* What do we try and in what order? Tradeoffs:
* glibc: +no external programs required * libc: +no external programs required
* -requires newish glibc * -requires newish libc/glibc
* -requires -rdynamic * -requires -rdynamic
* gdb: +gives more detailed information * gdb: +gives more detailed information
* +works on more OS versions * +works on more OS versions
@@ -91,17 +91,17 @@ extern void FDECL(nethack_exit,(int));
*/ */
# ifdef SYSCF # ifdef SYSCF
# define SYSOPT_PANICTRACE_GDB sysopt.panictrace_gdb # define SYSOPT_PANICTRACE_GDB sysopt.panictrace_gdb
# ifdef PANICTRACE_GLIBC # ifdef PANICTRACE_LIBC
# define SYSOPT_PANICTRACE_GLIBC sysopt.panictrace_glibc # define SYSOPT_PANICTRACE_LIBC sysopt.panictrace_libc
# else # else
# define SYSOPT_PANICTRACE_GLIBC 0 # define SYSOPT_PANICTRACE_LIBC 0
# endif # endif
# else # else
# define SYSOPT_PANICTRACE_GDB (nh_getenv("NETHACK_USE_GDB")==0?0:2) # define SYSOPT_PANICTRACE_GDB (nh_getenv("NETHACK_USE_GDB")==0?0:2)
# ifdef PANICTRACE_GLIBC # ifdef PANICTRACE_LIBC
# define SYSOPT_PANICTRACE_GLIBC 1 # define SYSOPT_PANICTRACE_LIBC 1
# else # else
# define SYSOPT_PANICTRACE_GLIBC 0 # define SYSOPT_PANICTRACE_LIBC 0
# endif # endif
# endif # endif
@@ -109,7 +109,7 @@ static void NDECL(NH_abort);
# ifndef NO_SIGNAL # ifndef NO_SIGNAL
static void FDECL(panictrace_handler, (int)); static void FDECL(panictrace_handler, (int));
# endif # endif
static boolean NDECL(NH_panictrace_glibc); static boolean NDECL(NH_panictrace_libc);
static boolean NDECL(NH_panictrace_gdb); static boolean NDECL(NH_panictrace_gdb);
# ifndef NO_SIGNAL # ifndef NO_SIGNAL
@@ -163,19 +163,19 @@ static void
NH_abort() NH_abort()
{ {
int gdb_prio = SYSOPT_PANICTRACE_GDB; int gdb_prio = SYSOPT_PANICTRACE_GDB;
int glibc_prio = SYSOPT_PANICTRACE_GLIBC; int libc_prio = SYSOPT_PANICTRACE_LIBC;
static boolean aborting = FALSE; static boolean aborting = FALSE;
if(aborting) return; if(aborting) return;
aborting = TRUE; aborting = TRUE;
# ifndef VMS # ifndef VMS
if(gdb_prio == glibc_prio && gdb_prio > 0) gdb_prio++; if(gdb_prio == libc_prio && gdb_prio > 0) gdb_prio++;
if(gdb_prio > glibc_prio){ if(gdb_prio > libc_prio){
NH_panictrace_gdb() || (glibc_prio && NH_panictrace_glibc()); NH_panictrace_gdb() || (libc_prio && NH_panictrace_libc());
} else { } else {
NH_panictrace_glibc() || (gdb_prio && NH_panictrace_gdb()); NH_panictrace_libc() || (gdb_prio && NH_panictrace_gdb());
} }
# else /* VMS */ # else /* VMS */
@@ -183,7 +183,7 @@ NH_abort()
traceback and exit; 2 = show traceback and stay in debugger */ traceback and exit; 2 = show traceback and stay in debugger */
/* if (wizard && gdb_prio == 1) gdb_prio = 2; */ /* if (wizard && gdb_prio == 1) gdb_prio = 2; */
vms_traceback(gdb_prio); vms_traceback(gdb_prio);
(void)glibc_prio; /* half-hearted attempt at lint suppression */ (void)libc_prio; /* half-hearted attempt at lint suppression */
# endif /* ?VMS */ # endif /* ?VMS */
@@ -194,9 +194,9 @@ NH_abort()
} }
static boolean static boolean
NH_panictrace_glibc() NH_panictrace_libc()
{ {
# ifdef PANICTRACE_GLIBC # ifdef PANICTRACE_LIBC
void *bt[20]; void *bt[20];
size_t count; size_t count;
char **info; char **info;
@@ -212,22 +212,22 @@ NH_panictrace_glibc()
return TRUE; return TRUE;
# else # else
return FALSE; return FALSE;
# endif /* !PANICTRACE_GLIBC */ # endif /* !PANICTRACE_LIBC */
} }
/*
* fooPATH file system path for foo
* fooVAR (possibly const) variable containing fooPATH
*/
# ifdef PANICTRACE_GDB # ifdef PANICTRACE_GDB
# ifdef SYSCF # ifdef SYSCF
# define GDBPATH sysopt.gdbpath # define GDBVAR sysopt.gdbpath
# define GREPPATH sysopt.greppath # define GREPVAR sysopt.greppath
# else # else /* SYSCF */
# ifndef GDBPATH # define GDBVAR GDBPATH
# define GDBPATH "/usr/bin/gdb" # define GREPVAR GREPPATH
# endif # endif /* SYSCF */
# ifndef GREPPATH # endif /* PANICTRACE_GDB */
# define GREPPATH "/bin/grep"
# endif
# endif /* !SYSCF */
# endif /* PANICTRACE_GDB */
static boolean static boolean
NH_panictrace_gdb() NH_panictrace_gdb()
@@ -235,8 +235,8 @@ NH_panictrace_gdb()
# ifdef PANICTRACE_GDB # ifdef PANICTRACE_GDB
/* A (more) generic method to get a stack trace - invoke /* A (more) generic method to get a stack trace - invoke
* gdb on ourself. */ * gdb on ourself. */
char *gdbpath = GDBPATH; char *gdbpath = GDBVAR;
char *greppath = GREPPATH; char *greppath = GREPVAR;
char buf[BUFSZ]; char buf[BUFSZ];
FILE *gdb; FILE *gdb;

View File

@@ -183,7 +183,7 @@ STATIC_DCL void FDECL(docompress_file, (const char *,BOOLEAN_P));
STATIC_DCL boolean FDECL(make_compressed_name, (const char *, char *)); STATIC_DCL boolean FDECL(make_compressed_name, (const char *, char *));
#endif #endif
STATIC_DCL char *FDECL(make_lockname, (const char *,char *)); STATIC_DCL char *FDECL(make_lockname, (const char *,char *));
STATIC_DCL FILE *FDECL(fopen_config_file, (const char *)); STATIC_DCL FILE *FDECL(fopen_config_file, (const char *, int));
STATIC_DCL int FDECL(get_uchars, (FILE *,char *,char *,uchar *,BOOLEAN_P,int,const char *)); STATIC_DCL int FDECL(get_uchars, (FILE *,char *,char *,uchar *,BOOLEAN_P,int,const char *));
int FDECL(parse_config_line, (FILE *,char *,char *,char *,int)); int FDECL(parse_config_line, (FILE *,char *,char *,char *,int));
#ifdef LOADSYMSETS #ifdef LOADSYMSETS
@@ -1772,8 +1772,9 @@ const char *backward_compat_configfile = "nethack.cnf";
#endif #endif
STATIC_OVL FILE * STATIC_OVL FILE *
fopen_config_file(filename) fopen_config_file(filename, src)
const char *filename; const char *filename;
int src;
{ {
FILE *fp; FILE *fp;
#if defined(UNIX) || defined(VMS) #if defined(UNIX) || defined(VMS)
@@ -1781,16 +1782,18 @@ const char *filename;
char *envp; char *envp;
#endif #endif
/* "filename" is an environment variable, so it should hang around */ /* If src != SET_IN_SYS, "filename" is an environment variable, so it
/* if set, it is expected to be a full path name (if relevant) */ * should hang around. If set, it is expected to be a full path name
* (if relevant) */
if (filename) { if (filename) {
#ifdef UNIX #ifdef UNIX
if (access(filename, 4) == -1) { if ((src!=SET_IN_SYS) && access(filename, 4) == -1) {
/* 4 is R_OK on newer systems */ /* 4 is R_OK on newer systems */
/* nasty sneaky attempt to read file through /* nasty sneaky attempt to read file through
* NetHack's setuid permissions -- this is the only * NetHack's setuid permissions -- this is the only
* place a file name may be wholly under the player's * place a file name may be wholly under the player's
* control * control (but SYSCF_FILE is not under the player's
* control so it's OK).
*/ */
raw_printf("Access to %s denied (%d).", raw_printf("Access to %s denied (%d).",
filename, errno); filename, errno);
@@ -2148,16 +2151,16 @@ int src;
} }
sysopt.pointsmin = temp; sysopt.pointsmin = temp;
# ifdef PANICTRACE # ifdef PANICTRACE
# ifdef PANICTRACE_GLIBC # ifdef PANICTRACE_LIBC
} else if (src == SET_IN_SYS && } else if (src == SET_IN_SYS &&
match_varname(buf, "PANICTRACE_GLIBC", 16)) { match_varname(buf, "PANICTRACE_LIBC", 15)) {
int temp = atoi(bufp); int temp = atoi(bufp);
if (temp < 0 || temp > 2) { if (temp < 0 || temp > 2) {
raw_printf("Illegal value in PANICTRACE_GLIBC (not 0,1,2)."); raw_printf("Illegal value in PANICTRACE_LIBC (not 0,1,2).");
return 0; return 0;
} }
sysopt.panictrace_glibc = temp; sysopt.panictrace_libc = temp;
# endif /* PANICTRACE_GLIBC */ # endif /* PANICTRACE_LIBC */
} else if (src == SET_IN_SYS && } else if (src == SET_IN_SYS &&
match_varname(buf, "PANICTRACE_GDB", 14)) { match_varname(buf, "PANICTRACE_GDB", 14)) {
int temp = atoi(bufp); int temp = atoi(bufp);
@@ -2167,10 +2170,18 @@ int src;
} }
sysopt.panictrace_gdb = temp; sysopt.panictrace_gdb = temp;
} else if ( (src==SET_IN_SYS) && match_varname(buf, "GDBPATH", 7)) { } else if ( (src==SET_IN_SYS) && match_varname(buf, "GDBPATH", 7)) {
if(!file_exists(bufp)){
raw_printf("File specified in GDBPATH does not exist.");
return 0;
}
if(sysopt.gdbpath) free(sysopt.gdbpath); if(sysopt.gdbpath) free(sysopt.gdbpath);
sysopt.gdbpath = (char*)alloc(strlen(bufp)+1); sysopt.gdbpath = (char*)alloc(strlen(bufp)+1);
Strcpy(sysopt.gdbpath, bufp); Strcpy(sysopt.gdbpath, bufp);
} else if ( (src==SET_IN_SYS) && match_varname(buf, "GREPPATH", 7)) { } else if ( (src==SET_IN_SYS) && match_varname(buf, "GREPPATH", 7)) {
if(!file_exists(bufp)){
raw_printf("File specified in GREPPATH does not exist.");
return 0;
}
if(sysopt.greppath) free(sysopt.greppath); if(sysopt.greppath) free(sysopt.greppath);
sysopt.greppath = (char*)alloc(strlen(bufp)+1); sysopt.greppath = (char*)alloc(strlen(bufp)+1);
Strcpy(sysopt.greppath, bufp); Strcpy(sysopt.greppath, bufp);
@@ -2377,7 +2388,7 @@ const char *filename;
} }
#endif /* USER_SOUNDS */ #endif /* USER_SOUNDS */
void boolean
read_config_file(filename, src) read_config_file(filename, src)
const char *filename; const char *filename;
int src; int src;
@@ -2397,8 +2408,9 @@ int src;
#endif #endif
char buf[4*BUFSZ]; char buf[4*BUFSZ];
FILE *fp; FILE *fp;
boolean rv = TRUE; /* assume successful parse */
if (!(fp = fopen_config_file(filename))) return; if (!(fp = fopen_config_file(filename, src))) return FALSE;
#if defined(MICRO) || defined(WIN32) #if defined(MICRO) || defined(WIN32)
# ifdef MFLOPPY # ifdef MFLOPPY
@@ -2422,6 +2434,7 @@ OR: Forbid multiline stuff for alternate config sources.
if (!parse_config_line(fp, buf, tmp_ramdisk, tmp_levels, src)) { if (!parse_config_line(fp, buf, tmp_ramdisk, tmp_levels, src)) {
raw_printf("Bad option line: \"%.50s\"", buf); raw_printf("Bad option line: \"%.50s\"", buf);
wait_synch(); wait_synch();
rv = FALSE;
} }
} }
(void) fclose(fp); (void) fclose(fp);
@@ -2445,7 +2458,7 @@ OR: Forbid multiline stuff for alternate config sources.
Strcpy(bones, levels); Strcpy(bones, levels);
# endif /* MFLOPPY */ # endif /* MFLOPPY */
#endif /* MICRO */ #endif /* MICRO */
return; return rv;
} }
#ifdef WIZARD #ifdef WIZARD

View File

@@ -572,7 +572,13 @@ initoptions()
#ifdef SYSCF #ifdef SYSCF
/* someday there may be other SYSCF alternatives besides text file */ /* someday there may be other SYSCF alternatives besides text file */
# ifdef SYSCF_FILE # ifdef SYSCF_FILE
read_config_file(SYSCF_FILE, SET_IN_SYS); /* If SYSCF_FILE is specified, it _must_ exist... */
assure_syscf_file();
/* ... and _must_ parse correctly. */
if(!read_config_file(SYSCF_FILE, SET_IN_SYS)){
raw_printf("Error(s) found in SYSCF_FILE, quitting.");
terminate(EXIT_FAILURE);
}
# endif # endif
#endif #endif
initoptions_finish(); initoptions_finish();

View File

@@ -4,16 +4,25 @@
#include "hack.h" #include "hack.h"
/* for KR1ED config, WIZARD is 0 or 1 and WIZARD_NAME is a string;
for usual config, WIZARD is the string; forcing WIZARD_NAME to match it
eliminates conditional testing for which one to use in string ops */
#ifndef KR1ED
# undef WIZARD_NAME
# define WIZARD_NAME WIZARD
#endif
struct sysopt sysopt; struct sysopt sysopt;
void void
sys_early_init(){ sys_early_init(){
sysopt.support = NULL; sysopt.support = NULL;
sysopt.recover = NULL; sysopt.recover = NULL;
#ifdef notyet #ifdef SYSCF
/* replace use of WIZARD vs WIZARD_NAME vs KR1ED, by filling this in */
#endif
sysopt.wizards = NULL; sysopt.wizards = NULL;
#else
sysopt.wizards = WIZARD_NAME;
#endif
sysopt.shellers = NULL; sysopt.shellers = NULL;
sysopt.maxplayers = 0; /* XXX eventually replace MAX_NR_OF_PLAYERS */ sysopt.maxplayers = 0; /* XXX eventually replace MAX_NR_OF_PLAYERS */
@@ -32,17 +41,17 @@ sys_early_init(){
#ifdef PANICTRACE #ifdef PANICTRACE
/* panic options */ /* panic options */
sysopt.gdbpath = NULL; sysopt.gdbpath = strdup(GDBPATH);
sysopt.greppath = NULL; sysopt.greppath = strdup(GREPPATH);
# ifdef BETA # ifdef BETA
sysopt.panictrace_gdb = 1; sysopt.panictrace_gdb = 1;
# ifdef PANICTRACE_GLIBC # ifdef PANICTRACE_LIBC
sysopt.panictrace_glibc = 2; sysopt.panictrace_libc = 2;
# endif # endif
# else # else
sysopt.panictrace_gdb = 0; sysopt.panictrace_gdb = 0;
# ifdef PANICTRACE_GLIBC # ifdef PANICTRACE_LIBC
sysopt.panictrace_glibc = 0; sysopt.panictrace_libc = 0;
# endif # endif
# endif # endif
#endif #endif

View File

@@ -41,12 +41,12 @@ MAXPLAYERS=10
# Try to get more info in case of a program bug or crash. Using GDB can # Try to get more info in case of a program bug or crash. Using GDB can
# get more information and works on more systems but requires gdb be available; # get more information and works on more systems but requires gdb be available;
# using GLIBC only works if NetHack is linked with glibc. Both require # using LIBC only works if NetHack is linked with a libc that supports the
# certain compilation options. See src/end.c and sys/unix/hints/* for # backtrace(3) API. Both require certain compilation options. See
# more information. # src/end.c and sys/unix/hints/* for more information.
GDBPATH=/usr/bin/gdb GDBPATH=/usr/bin/gdb
GREPPATH=/bin/grep GREPPATH=/bin/grep
# Values are priorities: 0 - do not use this method, 1 - low priority, # Values are priorities: 0 - do not use this method, 1 - low priority,
# 2 - high priority. Non-zero priority methods are tried in order. # 2 - high priority. Non-zero priority methods are tried in order.
PANICTRACE_GDB=1 PANICTRACE_GDB=1
PANICTRACE_GLIBC=2 PANICTRACE_LIBC=2

View File

@@ -555,26 +555,15 @@ port_help()
} }
#endif #endif
/* for KR1ED config, WIZARD is 0 or 1 and WIZARD_NAME is a string;
for usual config, WIZARD is the string; forcing WIZARD_NAME to match it
eliminates conditional testing for which one to use in string ops */
#ifndef KR1ED
# undef WIZARD_NAME
# define WIZARD_NAME WIZARD
#endif
/* validate wizard mode if player has requested access to it */ /* validate wizard mode if player has requested access to it */
boolean boolean
authorize_wizard_mode() authorize_wizard_mode()
{ {
#ifdef WIZARD #ifdef WIZARD
struct passwd *pw = get_unix_pw(); struct passwd *pw = get_unix_pw();
#ifdef SYSCF
if (pw && sysopt.wizards && sysopt.wizards[0]) { if (pw && sysopt.wizards && sysopt.wizards[0]) {
if(check_user_string(sysopt.wizards)) return TRUE; if(check_user_string(sysopt.wizards)) return TRUE;
} else }
#endif
if (pw && !strcmp(pw->pw_name, WIZARD_NAME)) return TRUE;
#endif /* WIZARD */ #endif /* WIZARD */
wiz_error_flag = TRUE; /* not being allowed into wizard mode */ wiz_error_flag = TRUE; /* not being allowed into wizard mode */
return FALSE; return FALSE;
@@ -585,17 +574,12 @@ wd_message()
{ {
if (wiz_error_flag) { if (wiz_error_flag) {
#ifdef WIZARD #ifdef WIZARD
# ifdef SYSCF
if (sysopt.wizards && sysopt.wizards[0]) { if (sysopt.wizards && sysopt.wizards[0]) {
char *tmp = build_english_list(sysopt.wizards); char *tmp = build_english_list(sysopt.wizards);
pline("Only user%s %s may access debug (wizard) mode.", pline("Only user%s %s may access debug (wizard) mode.",
index(sysopt.wizards, ' ')?"s":"", tmp); index(sysopt.wizards, ' ')?"s":"", tmp);
free(tmp); free(tmp);
} else } else
# else
pline("Only user \"%s\" may access debug (wizard) mode.",
WIZARD_NAME);
# endif
#else #else
pline("Debug mode is not available."); pline("Debug mode is not available.");
#endif #endif
@@ -675,4 +659,21 @@ get_unix_pw()
} }
return pw; return pw;
} }
#ifdef SYSCF_FILE
void
assure_syscf_file(){
/* All we really care about is the end result - can we read the file?
* So just check that directly. */
int fd;
fd = open(SYSCF_FILE, O_RDONLY);
if(fd >= 0){
/* readable */
close(fd);
return;
}
raw_printf("Unable to open SYSCF_FILE.\n");
exit(EXIT_FAILURE);
}
#endif
/*unixmain.c*/ /*unixmain.c*/

View File

@@ -371,3 +371,18 @@ gid_t
} }
#endif /* GETRES_SUPPORT */ #endif /* GETRES_SUPPORT */
/* XXX should be ifdef PANICTRACE_GDB, but there's no such symbol yet */
#ifdef PANICTRACE
boolean
file_exists(const char *path){
/* Just see if it's there - trying to figure out if we can actually
* execute it in all cases is too hard - we really just want to
* catch typos in SYSCF. */
struct stat sb;
if(stat(path, &sb)){
return FALSE;
}
return TRUE;
}
#endif