1*12742Ssam #ifndef lint 2*12742Ssam static char SccsId[] = "@(#)syslog.c 4.1 (Berkeley) 05/27/83"; 3*12742Ssam #endif 4*12742Ssam 5*12742Ssam /* 6*12742Ssam * SYSLOG -- print message on log file 7*12742Ssam * 8*12742Ssam * This routine looks a lot like printf, except that it 9*12742Ssam * outputs to the log file instead of the standard output. 10*12742Ssam * Also, it prints the module name in front of lines, 11*12742Ssam * and has some other formatting types (or will sometime). 12*12742Ssam * Also, it adds a newline on the end of messages. 13*12742Ssam * 14*12742Ssam * The output of this routine is intended to be read by 15*12742Ssam * /etc/syslog, which will add timestamps. 16*12742Ssam */ 17*12742Ssam #include <sys/types.h> 18*12742Ssam #include <sys/socket.h> 19*12742Ssam #include <netinet/in.h> 20*12742Ssam 21*12742Ssam #include <syslog.h> 22*12742Ssam #include <netdb.h> 23*12742Ssam 24*12742Ssam #define MAXLINE 1024 /* max message size */ 25*12742Ssam #define BUFSLOP 20 /* space to allow for "extra stuff" */ 26*12742Ssam #define NULL 0 /* manifest */ 27*12742Ssam 28*12742Ssam int LogFile = -1; /* fd for log */ 29*12742Ssam int LogStat = 0; /* status bits, set by initlog */ 30*12742Ssam char *LogTag = NULL; /* string to tag the entry with */ 31*12742Ssam int LogMask = LOG_DEBUG; /* lowest priority to be logged */ 32*12742Ssam 33*12742Ssam struct sockaddr_in SyslogAddr; 34*12742Ssam static char *SyslogHost = LOG_HOST; 35*12742Ssam 36*12742Ssam extern int errno, sys_nerr; 37*12742Ssam extern char *sys_errlist[]; 38*12742Ssam 39*12742Ssam syslog(pri, fmt, p0, p1, p2, p3, p4) 40*12742Ssam int pri; 41*12742Ssam char *fmt; 42*12742Ssam { 43*12742Ssam char buf[MAXLINE+BUFSLOP], outline[MAXLINE + 1]; 44*12742Ssam register char *b, *f; 45*12742Ssam 46*12742Ssam if (LogFile < 0) 47*12742Ssam openlog(0, 0); 48*12742Ssam /* see if we should just throw out this message */ 49*12742Ssam if (pri > LogMask) 50*12742Ssam return; 51*12742Ssam for (b = buf, f = fmt; f && *f; b = buf) { 52*12742Ssam register char c; 53*12742Ssam 54*12742Ssam if (pri > 0 && (LogStat & LOG_COOLIT) == 0) { 55*12742Ssam sprintf(b, "<%d>", pri); 56*12742Ssam b += strlen(b); 57*12742Ssam } 58*12742Ssam if (LogStat & LOG_PID) { 59*12742Ssam sprintf(b, "%d ", getpid()); 60*12742Ssam b += strlen(b); 61*12742Ssam } 62*12742Ssam if (LogTag) { 63*12742Ssam sprintf(b, "%s: ", LogTag); 64*12742Ssam b += strlen(b); 65*12742Ssam } 66*12742Ssam while ((c = *f++) != '\0' && c != '\n' && b < buf + MAXLINE) { 67*12742Ssam if (c != '%') { 68*12742Ssam *b++ = c; 69*12742Ssam continue; 70*12742Ssam } 71*12742Ssam c = *f++; 72*12742Ssam if (c != 'm') { 73*12742Ssam *b++ = '%', *b++ = c, *b++ = '\0'; 74*12742Ssam continue; 75*12742Ssam } 76*12742Ssam if ((unsigned)errno > sys_nerr) 77*12742Ssam sprintf(b, "error %d", errno); 78*12742Ssam else 79*12742Ssam strcat(b, sys_errlist[errno]); 80*12742Ssam b += strlen(b); 81*12742Ssam } 82*12742Ssam if (c == '\0') 83*12742Ssam f--; 84*12742Ssam *b++ = '\n', *b = '\0'; 85*12742Ssam sprintf(outline, buf, p0, p1, p2, p3, p4); 86*12742Ssam errno = 0; 87*12742Ssam if (LogStat & LOG_DGRAM) 88*12742Ssam (void) sendto(LogFile, outline, strlen(outline), 0, 89*12742Ssam &SyslogAddr, sizeof SyslogAddr); 90*12742Ssam else 91*12742Ssam (void) write(LogFile, outline, strlen(outline)); 92*12742Ssam if (errno) 93*12742Ssam perror("syslog: sendto"); 94*12742Ssam } 95*12742Ssam } 96*12742Ssam 97*12742Ssam /* 98*12742Ssam * OPENLOG -- open system log 99*12742Ssam */ 100*12742Ssam openlog(ident, logstat) 101*12742Ssam char *ident; 102*12742Ssam int logstat; 103*12742Ssam { 104*12742Ssam struct servent *sp; 105*12742Ssam struct hostent *hp; 106*12742Ssam 107*12742Ssam LogTag = ident; 108*12742Ssam LogStat = logstat; 109*12742Ssam if (LogFile >= 0) 110*12742Ssam return; 111*12742Ssam sp = getservbyname("syslog", "udp"); 112*12742Ssam hp = gethostbyname(SyslogHost); 113*12742Ssam if (sp == NULL || hp == NULL) 114*12742Ssam goto bad; 115*12742Ssam LogFile = socket(AF_INET, SOCK_DGRAM, 0); 116*12742Ssam if (LogFile < 0) { 117*12742Ssam perror("syslog: socket"); 118*12742Ssam goto bad; 119*12742Ssam } 120*12742Ssam bzero(&SyslogAddr, sizeof SyslogAddr); 121*12742Ssam SyslogAddr.sin_family = hp->h_addrtype; 122*12742Ssam bcopy(hp->h_addr, (char *)&SyslogAddr.sin_addr, hp->h_length); 123*12742Ssam SyslogAddr.sin_port = sp->s_port; 124*12742Ssam LogStat |= LOG_DGRAM; 125*12742Ssam return; 126*12742Ssam bad: 127*12742Ssam LogStat |= LOG_COOLIT; 128*12742Ssam LogStat &= ~LOG_DGRAM; 129*12742Ssam LogMask = LOG_CRIT; 130*12742Ssam LogFile = open("/dev/console", 1); 131*12742Ssam if (LogFile < 0) { 132*12742Ssam perror("syslog: /dev/console"); 133*12742Ssam LogFile = 2; 134*12742Ssam } 135*12742Ssam } 136*12742Ssam 137*12742Ssam /* 138*12742Ssam * CLOSELOG -- close the system log 139*12742Ssam */ 140*12742Ssam closelog() 141*12742Ssam { 142*12742Ssam 143*12742Ssam (void) close(LogFile); 144*12742Ssam LogFile = -1; 145*12742Ssam } 146