/********************************************************************
* wilkinson
* 3.10VMS
* 1995/09/25 14:25
* gopher_root1:[gopher.g2.vms2_13.gopherd]error.c,v
* Exp
*
* Paul Lindner, University of Minnesota CIS.
*
* Copyright 1991, 1992 by the Regents of the University of Minnesota
* see the file "Copyright" in the distribution for conditions of use.
*********************************************************************
* MODULE: error.c
* Error handling/logging routines.
*********************************************************************
* Revision History:
* error.c,v
* Revision 3.10VMS 1995/09/24 14:25 wilkinson
* Consolodate VMS/Unix source code for server as well as client
* - VMS Syslog.h is private
*
* Revision 3.10 1995/02/07 07:12:32 lindner
* oops!
*
* Revision 3.9 1995/02/07 07:04:29 lindner
* performance fixes
*
* Revision 3.8 1994/07/19 20:28:08 lindner
* Fix for syslog problem with WAIS
*
* Revision 3.7 1994/01/20 06:37:43 lindner
* Fix for stdc declaration for err_quit()
*
* Revision 3.6 1993/10/11 04:40:49 lindner
* Changes to allow logging via daemon.info syslogd facility
*
* Revision 3.5 1993/07/30 17:19:53 lindner
* Fix for NeXTs
*
* Revision 3.4 1993/07/20 23:58:01 lindner
* LOGGopher mods
*
* Revision 3.3 1993/07/10 04:21:55 lindner
* mods for solaris2.2
*
* Revision 3.2 1993/07/07 19:39:09 lindner
* fix for linux
*
* Revision 3.1.1.1 1993/02/11 18:02:50 lindner
* Gopher+1.2beta release
*
* Revision 1.1 1992/12/10 23:13:27 lindner
* gopher 1.1 release
*
*
*********************************************************************/
/*
* Error handling routines from Stevens: UNIX network programming
* pp 722-731
*/
/*
* Error handling routines.
*
* The functions in this file are independent of any application
* variables, and may be used in any C program. Either of the names
* CLIENT of SERVER may be defined when compiling this function.
* If neither are defined, we assume SERVER.
*/
#include "gopherd.h"
void my_perror();
#ifndef NULL
#define NULL ((void *) 0)
#endif
extern char *pname;
#ifndef NOSYSLOG
/*
* Under useful OS's, these server routines use the syslog(3) facility.
* They don't append a newline for example.
*/
#ifndef VMS_SERVER
/*
* Get around the existance of syslog.h in the wais source code...
* Arghhh!!!
*/
#ifdef WAISSEARCH
#include "/usr/include/syslog.h"
#else
#include <syslog.h>
#endif
#else
/*
* VMS implementations require their own syslog.h file
*/
#ifdef MULTINET
#include "syslog.h"
#endif
#endif
#else /* no syslog() */
/*
* There really ought to be a better way to handle server logging
* under System V
*/
#ifndef VMS_SERVER
#define syslog(a,b) fprintf(stderr, "%s\n", (b))
#define openlog(a,b,c) fprintf(stderr, "%s\n", (a))
#else
#define syslog(a,b) VMS$fprintf(stderr, "%s\n", (b))
#define openlog(a,b,c) VMS$fprintf(stderr, "%s\n", (a))
#endif
#endif /* NOSYSLOG */
#if defined(__STDC__) && !defined(NeXT)
#define __stdc__
#endif
#if defined(__stdc__)
#include <stdarg.h>
#else
#include <varargs.h>
#endif
char emesgstr[255] = {0}; /* used by all server routines */
/*
* Identify ourselves, for syslog() messages.
*
* LOG_PID is an option that says prepend each message with our pid.
* LOG_CONS is an option that says write to the console if unable to
* send the message to syslogd.
* LOG_DAEMON is our facility.
*/
void
err_init()
{
#ifndef VMS_SERVER
/* have to be able to reopen, since daemon_start keeps closing us */
closelog(); /* in case we've been closed by daemon_start */
#endif
#ifdef LOG_DAEMON
openlog("gopherd", (LOG_PID|LOG_CONS), LOG_DAEMON);
setlogmask(LOG_UPTO(LOG_INFO));
#else
/* old old syslog - probably Ultrix */
openlog("gopherd", LOG_PID);
#endif
}
/*
* Fatal error. Print a message and terminate.
* Don't print the system's errno value.
*
* err_quit(str, arg1, arg2, ...)
*/
#ifdef __stdc__
void err_quit(char *va_alist, ...)
#else
/*VARARGS1*/
void
err_quit(va_alist)
va_dcl
#endif
{
va_list args;
char *fmt;
#ifdef __stdc__
fmt = va_alist;
va_start(args, va_alist);
#else
va_start(args);
fmt = va_arg(args, char *);
#endif
(void) vsprintf(emesgstr, fmt, args);
va_end(args);
syslog(LOG_ERR, emesgstr);
LOGGopher(-1, "%s", emesgstr);
#ifndef VMS_SERVER
exit(1);
#else
gopherd_exit(1);
#endif
}
/*
* Fatal error related to a system call. Print the message and terminate.
* Don't dump core, but do print the systems errno value and its associated
* message.
*/
#ifdef __stdc__
void err_sys(char *va_alist, ...)
#else
/*VARARGS*/
void
err_sys(va_alist)
va_dcl
#endif
{
va_list args;
char *fmt;
#ifdef __stdc__
fmt = va_alist;
va_start(args,va_alist);
#else
va_start(args);
fmt = va_arg(args, char *);
#endif
(void) vsprintf(emesgstr, fmt, args);
va_end(args);
my_perror();
syslog(LOG_ERR, emesgstr);
LOGGopher(-1, "%s", emesgstr);
#ifndef VMS_SERVER
exit(1);
#else
gopherd_exit(1);
#endif
}
/*
* Recoverable error. Print a message, and return to caller.
*/
#ifdef __stdc__
void err_ret(char *va_alist, ...)
#else
/*VARARGS1*/
void
err_ret(va_alist)
va_dcl
#endif
{
va_list args;
char *fmt;
#ifdef __stdc__
fmt = va_alist;
va_start(args, va_alist);
#else
va_start(args);
fmt = va_arg(args, char *);
#endif
(void) vsprintf(emesgstr, fmt, args);
va_end(args);
my_perror();
syslog(LOG_ERR, emesgstr);
LOGGopher(-1, "%s", emesgstr);
return;
}
/*
* Fatal error. Print a message, dump core and terminate.
*/
#ifdef __stdc__
void err_dump(char *va_alist, ...)
#else
/*VARARGS1*/
void
err_dump(va_alist)
va_dcl
#endif
{
va_list args;
char *fmt;
#ifdef __stdc__
fmt = va_alist;
va_start(args, va_alist);
#else
va_start(args);
fmt = va_arg(args, char *);
#endif
(void) vsprintf(emesgstr, fmt, args);
va_end(args);
my_perror();
syslog(LOG_ERR, emesgstr);
LOGGopher(-1, "%s", emesgstr);
abort();
}
/*
* Print the UNIX errno value.
* We just append it the the end of the emesgstr[] array.
*/
void my_perror()
{
int len;
char *sys_err_str();
len = strlen(emesgstr);
sprintf(emesgstr + len, " %s", sys_err_str());
}
extern int errno; /* UNIX error number */
extern int sys_nerr; /* # of error message strings in sys table */
#ifndef VMS_SERVER
extern char *sys_errlist[]; /* the system error message table */
#endif
#ifdef SYS5
int t_errno;
int t_nerr;
char *t_errlist[1];
#endif
/*
* Return a string containing some additional operating system
* dependent information.
* Note that different versions of UNIX assign different meanings
* to the same value of "errno". This means that if an error
* condition is being sent ot another UNIX system, we must interpret
* the errno value on the system that generated the error, and not
* just send the decimal value of errno to the other system.
*/
char *
sys_err_str()
{
static char msgstr[200];
if (errno != 0) {
if (errno >0 && errno < sys_nerr)
#ifndef VMS_SERVER
sprintf(msgstr, "(%s)", sys_errlist[errno]);
#else
sprintf(msgstr, "(%s)", strerror(errno));
#endif
else
sprintf(msgstr, "(errno = %d)", errno);
} else {
msgstr[0] = '\0';
}
#ifdef SYS5
if (t_errno != 0) {
char tmsgstr[100];
if (t_errno > 0 && t_errno < sys_nerr)
sprintf(tmsgstr, " (%s)", t_errlist[t_errno]);
else
sprintf(tmsgstr, ", (t_errno = %d)", t_errno);
strcat(msgstr, tmsgstr);
}
#endif
return(msgstr);
}
.
Response:
text/plain