• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /* logger.c - Log messages.
2  *
3  * Copyright 2013 Ilya Kuzmich <ilya.kuzmich@gmail.com>
4  *
5  * See http://pubs.opengroup.org/onlinepubs/9699919799/utilities/logger.html
6  *
7  * Deviations from posix: specified manner and format, defined implementation.
8 
9 USE_LOGGER(NEWTOY(logger, "t:p:s", TOYFLAG_USR|TOYFLAG_BIN))
10 
11 config LOGGER
12   bool "logger"
13   default y
14   help
15     usage: logger [-s] [-t TAG] [-p [FACILITY.]PRIORITY] [MESSAGE...]
16 
17     Log message (or stdin) to syslog.
18 
19     -s	Also write message to stderr
20     -t	Use TAG instead of username to identify message source
21     -p	Specify PRIORITY with optional FACILITY. Default is "user.notice"
22 */
23 
24 #define FOR_logger
25 #include "toys.h"
26 
27 GLOBALS(
28   char *p, *t;
29 
30   int priority;
31 )
32 
33 // find str in names[], accepting unambiguous short matches
34 // returns offset into array of match, or -1 if no match
35 // TODO: move to lib?
arrayfind(char * str,char * names[],int len)36 static int arrayfind(char *str, char *names[], int len)
37 {
38   int j, i, ll = 0, maybe = -1;
39 
40   for (j = 0; j<len; j++) for (i=0; ; i++) {
41     if (!str[i]) {
42       if (!names[j][i]) return j;
43       if (i>ll) maybe = j;
44       else if (i==ll) maybe = -1;
45       break;
46     }
47     if (!names[j][i] || toupper(str[i])!=toupper(names[j][i])) break;
48   }
49 
50   return maybe;
51 }
52 
syslog_line(char ** pline,long len)53 static void syslog_line(char **pline, long len)
54 {
55   if (!pline) return;
56   syslog(TT.priority, "%s", *pline);
57 }
58 
logger_main(void)59 void logger_main(void)
60 {
61   int facility = LOG_USER, len = 0;
62   char *s1, *s2, **arg,
63     *priorities[] = {"emerg", "alert", "crit", "error", "warning", "notice",
64                      "info", "debug"},
65     *facilities[] = {"kern", "user", "mail", "daemon", "auth", "syslog",
66                      "lpr", "news", "uucp", "cron", "authpriv", "ftp"};
67 
68   if (!TT.t) TT.t = xgetpwuid(geteuid())->pw_name;
69   TT.priority = LOG_NOTICE;
70   if (TT.p) {
71     if (!(s1 = strchr(TT.p, '.'))) s1 = TT.p;
72     else {
73       *s1++ = 0;
74       facility = arrayfind(TT.p, facilities, ARRAY_LEN(facilities));
75       if (facility<0) {
76         if (sscanf(TT.p, "local%d", &facility)>0 && !(facility&~7))
77           facility += 16;
78         else error_exit("bad facility: %s", TT.p);
79       }
80       facility *= 8;
81     }
82 
83     TT.priority = arrayfind(s1, priorities, ARRAY_LEN(priorities));
84     if (TT.priority<0) error_exit("bad priority: %s", s1);
85   }
86 
87   openlog(TT.t, LOG_PERROR*FLAG(s), facility);
88   if (toys.optc) {
89     for (arg = toys.optargs; *arg; arg++) len += strlen(*arg)+1;
90     s1 = s2 = xmalloc(len);
91     for (arg = toys.optargs; *arg; arg++) {
92       if (arg != toys.optargs) *s2++ = ' ';
93       s2 = stpcpy(s2, *arg);
94     }
95     syslog(TT.priority, "%s", s1);
96   } else do_lines(0, '\n', syslog_line);
97   closelog();
98 }
99