| OLD | NEW |
| 1 #include <stdarg.h> | 1 #include <stdarg.h> |
| 2 #include <sys/socket.h> | 2 #include <sys/socket.h> |
| 3 #include <stdio.h> | 3 #include <stdio.h> |
| 4 #include <unistd.h> | 4 #include <unistd.h> |
| 5 #include <syslog.h> | 5 #include <syslog.h> |
| 6 #include <time.h> | 6 #include <time.h> |
| 7 #include <signal.h> | 7 #include <signal.h> |
| 8 #include <string.h> | 8 #include <string.h> |
| 9 #include <pthread.h> | 9 #include <pthread.h> |
| 10 #include <errno.h> | 10 #include <errno.h> |
| 11 #include <fcntl.h> | 11 #include <fcntl.h> |
| 12 #include "libc.h" | 12 #include "libc.h" |
| 13 | 13 |
| 14 static volatile int lock[2]; | 14 static volatile int lock[2]; |
| 15 static char log_ident[32]; | 15 static char log_ident[32]; |
| 16 static int log_opt; | 16 static int log_opt; |
| 17 static int log_facility = LOG_USER; | 17 static int log_facility = LOG_USER; |
| 18 static int log_mask = 0xff; | 18 static int log_mask = 0xff; |
| 19 static int log_fd = -1; | 19 static int log_fd = -1; |
| 20 | 20 |
| 21 int setlogmask(int maskpri) | 21 int setlogmask(int maskpri) { |
| 22 { | 22 LOCK(lock); |
| 23 » LOCK(lock); | 23 int ret = log_mask; |
| 24 » int ret = log_mask; | 24 if (maskpri) |
| 25 » if (maskpri) log_mask = maskpri; | 25 log_mask = maskpri; |
| 26 » UNLOCK(lock); | 26 UNLOCK(lock); |
| 27 » return ret; | 27 return ret; |
| 28 } | 28 } |
| 29 | 29 |
| 30 static const struct { | 30 static const struct { |
| 31 » short sun_family; | 31 short sun_family; |
| 32 » char sun_path[9]; | 32 char sun_path[9]; |
| 33 } log_addr = { | 33 } log_addr = {AF_UNIX, "/dev/log"}; |
| 34 » AF_UNIX, | |
| 35 » "/dev/log" | |
| 36 }; | |
| 37 | 34 |
| 38 void closelog(void) | 35 void closelog(void) { |
| 39 { | 36 int cs; |
| 40 » int cs; | 37 pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &cs); |
| 41 » pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &cs); | 38 LOCK(lock); |
| 42 » LOCK(lock); | 39 close(log_fd); |
| 43 » close(log_fd); | 40 log_fd = -1; |
| 44 » log_fd = -1; | 41 UNLOCK(lock); |
| 45 » UNLOCK(lock); | 42 pthread_setcancelstate(cs, 0); |
| 46 » pthread_setcancelstate(cs, 0); | |
| 47 } | 43 } |
| 48 | 44 |
| 49 static void __openlog() | 45 static void __openlog() { |
| 50 { | 46 log_fd = socket(AF_UNIX, SOCK_DGRAM | SOCK_CLOEXEC, 0); |
| 51 » log_fd = socket(AF_UNIX, SOCK_DGRAM|SOCK_CLOEXEC, 0); | 47 if (log_fd >= 0) |
| 52 » if (log_fd >= 0) connect(log_fd, (void *)&log_addr, sizeof log_addr); | 48 connect(log_fd, (void*)&log_addr, sizeof log_addr); |
| 53 } | 49 } |
| 54 | 50 |
| 55 void openlog(const char *ident, int opt, int facility) | 51 void openlog(const char* ident, int opt, int facility) { |
| 56 { | 52 int cs; |
| 57 » int cs; | 53 pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &cs); |
| 58 » pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &cs); | 54 LOCK(lock); |
| 59 » LOCK(lock); | |
| 60 | 55 |
| 61 » if (ident) { | 56 if (ident) { |
| 62 » » size_t n = strnlen(ident, sizeof log_ident - 1); | 57 size_t n = strnlen(ident, sizeof log_ident - 1); |
| 63 » » memcpy(log_ident, ident, n); | 58 memcpy(log_ident, ident, n); |
| 64 » » log_ident[n] = 0; | 59 log_ident[n] = 0; |
| 65 » } else { | 60 } else { |
| 66 » » log_ident[0] = 0; | 61 log_ident[0] = 0; |
| 67 » } | 62 } |
| 68 » log_opt = opt; | 63 log_opt = opt; |
| 69 » log_facility = facility; | 64 log_facility = facility; |
| 70 | 65 |
| 71 » if ((opt & LOG_NDELAY) && log_fd<0) __openlog(); | 66 if ((opt & LOG_NDELAY) && log_fd < 0) |
| 67 __openlog(); |
| 72 | 68 |
| 73 » UNLOCK(lock); | 69 UNLOCK(lock); |
| 74 » pthread_setcancelstate(cs, 0); | 70 pthread_setcancelstate(cs, 0); |
| 75 } | 71 } |
| 76 | 72 |
| 77 static int is_lost_conn(int e) | 73 static int is_lost_conn(int e) { |
| 78 { | 74 return e == ECONNREFUSED || e == ECONNRESET || e == ENOTCONN || e == EPIPE; |
| 79 » return e==ECONNREFUSED || e==ECONNRESET || e==ENOTCONN || e==EPIPE; | |
| 80 } | 75 } |
| 81 | 76 |
| 82 static void _vsyslog(int priority, const char *message, va_list ap) | 77 static void _vsyslog(int priority, const char* message, va_list ap) { |
| 83 { | 78 char timebuf[16]; |
| 84 » char timebuf[16]; | 79 time_t now; |
| 85 » time_t now; | 80 struct tm tm; |
| 86 » struct tm tm; | 81 char buf[1024]; |
| 87 » char buf[1024]; | 82 int errno_save = errno; |
| 88 » int errno_save = errno; | 83 int pid; |
| 89 » int pid; | 84 int l, l2; |
| 90 » int l, l2; | 85 int hlen; |
| 91 » int hlen; | 86 int fd; |
| 92 » int fd; | |
| 93 | 87 |
| 94 » if (log_fd < 0) __openlog(); | 88 if (log_fd < 0) |
| 89 __openlog(); |
| 95 | 90 |
| 96 » if (!(priority & LOG_FACMASK)) priority |= log_facility; | 91 if (!(priority & LOG_FACMASK)) |
| 92 priority |= log_facility; |
| 97 | 93 |
| 98 » now = time(NULL); | 94 now = time(NULL); |
| 99 » gmtime_r(&now, &tm); | 95 gmtime_r(&now, &tm); |
| 100 » strftime(timebuf, sizeof timebuf, "%b %e %T", &tm); | 96 strftime(timebuf, sizeof timebuf, "%b %e %T", &tm); |
| 101 | 97 |
| 102 » pid = (log_opt & LOG_PID) ? getpid() : 0; | 98 pid = (log_opt & LOG_PID) ? getpid() : 0; |
| 103 » l = snprintf(buf, sizeof buf, "<%d>%s %n%s%s%.0d%s: ", | 99 l = snprintf(buf, sizeof buf, "<%d>%s %n%s%s%.0d%s: ", priority, timebuf, |
| 104 » » priority, timebuf, &hlen, log_ident, | 100 &hlen, log_ident, pid ? "[" : "", pid, pid ? "]" : ""); |
| 105 » » pid ? "[" : "", pid, pid ? "]" : ""); | 101 errno = errno_save; |
| 106 » errno = errno_save; | 102 l2 = vsnprintf(buf + l, sizeof buf - l, message, ap); |
| 107 » l2 = vsnprintf(buf+l, sizeof buf - l, message, ap); | 103 if (l2 >= 0) { |
| 108 » if (l2 >= 0) { | 104 if (l2 >= sizeof buf - l) |
| 109 » » if (l2 >= sizeof buf - l) l = sizeof buf - 1; | 105 l = sizeof buf - 1; |
| 110 » » else l += l2; | 106 else |
| 111 » » if (buf[l-1] != '\n') buf[l++] = '\n'; | 107 l += l2; |
| 112 » » if (send(log_fd, buf, l, 0) < 0 && (!is_lost_conn(errno) | 108 if (buf[l - 1] != '\n') |
| 113 » » || connect(log_fd, (void *)&log_addr, sizeof log_addr) < 0 | 109 buf[l++] = '\n'; |
| 114 » » || send(log_fd, buf, l, 0) < 0) | 110 if (send(log_fd, buf, l, 0) < 0 && |
| 115 » » && (log_opt & LOG_CONS)) { | 111 (!is_lost_conn(errno) || |
| 116 » » » fd = open("/dev/console", O_WRONLY|O_NOCTTY|O_CLOEXEC); | 112 connect(log_fd, (void*)&log_addr, sizeof log_addr) < 0 || |
| 117 » » » if (fd >= 0) { | 113 send(log_fd, buf, l, 0) < 0) && |
| 118 » » » » dprintf(fd, "%.*s", l-hlen, buf+hlen); | 114 (log_opt & LOG_CONS)) { |
| 119 » » » » close(fd); | 115 fd = open("/dev/console", O_WRONLY | O_NOCTTY | O_CLOEXEC); |
| 120 » » » } | 116 if (fd >= 0) { |
| 121 » » } | 117 dprintf(fd, "%.*s", l - hlen, buf + hlen); |
| 122 » » if (log_opt & LOG_PERROR) dprintf(2, "%.*s", l-hlen, buf+hlen); | 118 close(fd); |
| 123 » } | 119 } |
| 120 } |
| 121 if (log_opt & LOG_PERROR) |
| 122 dprintf(2, "%.*s", l - hlen, buf + hlen); |
| 123 } |
| 124 } | 124 } |
| 125 | 125 |
| 126 void __vsyslog(int priority, const char *message, va_list ap) | 126 void __vsyslog(int priority, const char* message, va_list ap) { |
| 127 { | 127 int cs; |
| 128 » int cs; | 128 if (!(log_mask & LOG_MASK(priority & 7)) || (priority & ~0x3ff)) |
| 129 » if (!(log_mask & LOG_MASK(priority&7)) || (priority&~0x3ff)) return; | 129 return; |
| 130 » pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &cs); | 130 pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &cs); |
| 131 » LOCK(lock); | 131 LOCK(lock); |
| 132 » _vsyslog(priority, message, ap); | 132 _vsyslog(priority, message, ap); |
| 133 » UNLOCK(lock); | 133 UNLOCK(lock); |
| 134 » pthread_setcancelstate(cs, 0); | 134 pthread_setcancelstate(cs, 0); |
| 135 } | 135 } |
| 136 | 136 |
| 137 void syslog(int priority, const char *message, ...) | 137 void syslog(int priority, const char* message, ...) { |
| 138 { | 138 va_list ap; |
| 139 » va_list ap; | 139 va_start(ap, message); |
| 140 » va_start(ap, message); | 140 __vsyslog(priority, message, ap); |
| 141 » __vsyslog(priority, message, ap); | 141 va_end(ap); |
| 142 » va_end(ap); | |
| 143 } | 142 } |
| 144 | 143 |
| 145 weak_alias(__vsyslog, vsyslog); | 144 weak_alias(__vsyslog, vsyslog); |
| OLD | NEW |