diff options
Diffstat (limited to 'networking/udhcp/common.c')
-rw-r--r-- | networking/udhcp/common.c | 142 |
1 files changed, 71 insertions, 71 deletions
diff --git a/networking/udhcp/common.c b/networking/udhcp/common.c index babd980e3..bfdc7ba8d 100644 --- a/networking/udhcp/common.c +++ b/networking/udhcp/common.c | |||
@@ -1,8 +1,9 @@ | |||
1 | /* common.c | 1 | /* common.c |
2 | * | 2 | * |
3 | * Functions to assist in the writing and removing of pidfiles. | 3 | * Functions for debugging and logging as well as some other |
4 | * simple helper functions. | ||
4 | * | 5 | * |
5 | * Russ Dill <Russ.Dill@asu.edu> Soptember 2001 | 6 | * Russ Dill <Russ.Dill@asu.edu> 2001-2003 |
6 | * Rewrited by Vladimir Oleynik <dzo@simtreas.ru> (C) 2003 | 7 | * Rewrited by Vladimir Oleynik <dzo@simtreas.ru> (C) 2003 |
7 | * | 8 | * |
8 | * This program is free software; you can redistribute it and/or modify | 9 | * This program is free software; you can redistribute it and/or modify |
@@ -26,18 +27,54 @@ | |||
26 | #include <string.h> | 27 | #include <string.h> |
27 | #include <stdlib.h> | 28 | #include <stdlib.h> |
28 | #include <signal.h> | 29 | #include <signal.h> |
30 | #include <paths.h> | ||
29 | #include <sys/socket.h> | 31 | #include <sys/socket.h> |
32 | #include <stdarg.h> | ||
30 | 33 | ||
31 | #include "common.h" | 34 | #include "common.h" |
35 | #include "pidfile.h" | ||
32 | 36 | ||
33 | 37 | ||
34 | static int daemonized; | 38 | static int daemonized; |
35 | 39 | ||
36 | #ifdef CONFIG_FEATURE_UDHCP_SYSLOG | ||
37 | 40 | ||
41 | /* | ||
42 | * This function makes sure our first socket calls | ||
43 | * aren't going to fd 1 (printf badness...) and are | ||
44 | * not later closed by daemon() | ||
45 | */ | ||
46 | static inline void sanitize_fds(void) | ||
47 | { | ||
48 | int zero; | ||
49 | if ((zero = open(_PATH_DEVNULL, O_RDWR, 0)) < 0) return; | ||
50 | while (zero < 3) zero = dup(zero); | ||
51 | close(zero); | ||
52 | } | ||
53 | |||
54 | |||
55 | void background(const char *pidfile) | ||
56 | { | ||
57 | #ifdef __uClinux__ | ||
58 | LOG(LOG_ERR, "Cannot background in uclinux (yet)"); | ||
59 | #else /* __uClinux__ */ | ||
60 | int pid_fd; | ||
61 | |||
62 | if (!pidfile) return; | ||
63 | |||
64 | pid_fd = pidfile_acquire(pidfile); /* hold lock during fork. */ | ||
65 | if (daemon(0, 0) == -1) { | ||
66 | perror("fork"); | ||
67 | exit(1); | ||
68 | } | ||
69 | daemonized++; | ||
70 | pidfile_write_release(pid_fd); | ||
71 | #endif /* __uClinux__ */ | ||
72 | } | ||
73 | |||
74 | |||
75 | #ifdef UDHCP_SYSLOG | ||
38 | void udhcp_logging(int level, const char *fmt, ...) | 76 | void udhcp_logging(int level, const char *fmt, ...) |
39 | { | 77 | { |
40 | int e = errno; | ||
41 | va_list p; | 78 | va_list p; |
42 | va_list p2; | 79 | va_list p2; |
43 | 80 | ||
@@ -46,21 +83,34 @@ void udhcp_logging(int level, const char *fmt, ...) | |||
46 | if(!daemonized) { | 83 | if(!daemonized) { |
47 | vprintf(fmt, p); | 84 | vprintf(fmt, p); |
48 | putchar('\n'); | 85 | putchar('\n'); |
49 | fflush(stdout); | ||
50 | errno = e; | ||
51 | } | 86 | } |
52 | vsyslog(level, fmt, p2); | 87 | vsyslog(level, fmt, p2); |
53 | va_end(p); | 88 | va_end(p); |
54 | } | 89 | } |
55 | 90 | ||
56 | void start_log(const char *client_server) | 91 | |
92 | void start_log_and_pid(const char *client_server, const char *pidfile) | ||
57 | { | 93 | { |
58 | openlog(bb_applet_name, LOG_PID | LOG_CONS, LOG_LOCAL0); | 94 | int pid_fd; |
95 | |||
96 | /* Make sure our syslog fd isn't overwritten */ | ||
97 | sanitize_fds(); | ||
98 | |||
99 | /* do some other misc startup stuff while we are here to save bytes */ | ||
100 | pid_fd = pidfile_acquire(pidfile); | ||
101 | pidfile_write_release(pid_fd); | ||
102 | |||
103 | /* equivelent of doing a fflush after every \n */ | ||
104 | setlinebuf(stdout); | ||
105 | |||
106 | openlog(client_server, LOG_PID | LOG_CONS, LOG_LOCAL0); | ||
59 | udhcp_logging(LOG_INFO, "%s (v%s) started", client_server, VERSION); | 107 | udhcp_logging(LOG_INFO, "%s (v%s) started", client_server, VERSION); |
60 | } | 108 | } |
61 | 109 | ||
110 | |||
62 | #else | 111 | #else |
63 | 112 | ||
113 | |||
64 | static char *syslog_level_msg[] = { | 114 | static char *syslog_level_msg[] = { |
65 | [LOG_EMERG] = "EMERGENCY!", | 115 | [LOG_EMERG] = "EMERGENCY!", |
66 | [LOG_ALERT] = "ALERT!", | 116 | [LOG_ALERT] = "ALERT!", |
@@ -71,86 +121,36 @@ static char *syslog_level_msg[] = { | |||
71 | [LOG_DEBUG] = "debug" | 121 | [LOG_DEBUG] = "debug" |
72 | }; | 122 | }; |
73 | 123 | ||
124 | |||
74 | void udhcp_logging(int level, const char *fmt, ...) | 125 | void udhcp_logging(int level, const char *fmt, ...) |
75 | { | 126 | { |
76 | int e = errno; | ||
77 | va_list p; | 127 | va_list p; |
78 | 128 | ||
79 | va_start(p, fmt); | 129 | va_start(p, fmt); |
80 | if(!daemonized) { | 130 | if(!daemonized) { |
81 | printf("%s, ", syslog_level_msg[level]); | 131 | printf("%s, ", syslog_level_msg[level]); |
82 | errno = e; | ||
83 | vprintf(fmt, p); | 132 | vprintf(fmt, p); |
84 | putchar('\n'); | 133 | putchar('\n'); |
85 | fflush(stdout); | ||
86 | } | 134 | } |
87 | va_end(p); | 135 | va_end(p); |
88 | } | 136 | } |
89 | 137 | ||
90 | void start_log(const char *client_server) | 138 | |
139 | void start_log_and_pid(const char *client_server, const char *pidfile) | ||
91 | { | 140 | { |
92 | udhcp_logging(LOG_INFO, "%s (v%s) started", client_server, VERSION); | 141 | int pid_fd; |
93 | } | ||
94 | #endif | ||
95 | 142 | ||
96 | static const char *saved_pidfile; | 143 | /* Make sure our syslog fd isn't overwritten */ |
144 | sanitize_fds(); | ||
97 | 145 | ||
98 | static void exit_fun(void) | 146 | /* do some other misc startup stuff while we are here to save bytes */ |
99 | { | 147 | pid_fd = pidfile_acquire(pidfile); |
100 | if (saved_pidfile) unlink(saved_pidfile); | 148 | pidfile_write_release(pid_fd); |
101 | } | ||
102 | 149 | ||
103 | void background(const char *pidfile) | 150 | /* equivelent of doing a fflush after every \n */ |
104 | { | 151 | setlinebuf(stdout); |
105 | #ifdef __uClinux__ | ||
106 | LOG(LOG_ERR, "Cannot background in uclinux (yet)"); | ||
107 | #else /* __uClinux__ */ | ||
108 | int pid_fd = -1; | ||
109 | |||
110 | if (pidfile) { | ||
111 | pid_fd = open(pidfile, O_CREAT | O_WRONLY, 0644); | ||
112 | if (pid_fd < 0) { | ||
113 | LOG(LOG_ERR, "Unable to open pidfile %s: %m", pidfile); | ||
114 | } else { | ||
115 | lockf(pid_fd, F_LOCK, 0); | ||
116 | if(!saved_pidfile) | ||
117 | atexit(exit_fun); /* set atexit one only */ | ||
118 | saved_pidfile = pidfile; /* but may be rewrite */ | ||
119 | } | ||
120 | } | ||
121 | while (pid_fd >= 0 && pid_fd < 3) pid_fd = dup(pid_fd); /* don't let daemon close it */ | ||
122 | if (daemon(0, 0) == -1) { | ||
123 | perror("fork"); | ||
124 | exit(1); | ||
125 | } | ||
126 | daemonized++; | ||
127 | if (pid_fd >= 0) { | ||
128 | FILE *out; | ||
129 | |||
130 | if ((out = fdopen(pid_fd, "w")) != NULL) { | ||
131 | fprintf(out, "%d\n", getpid()); | ||
132 | fclose(out); | ||
133 | } | ||
134 | lockf(pid_fd, F_UNLCK, 0); | ||
135 | close(pid_fd); | ||
136 | } | ||
137 | #endif /* __uClinux__ */ | ||
138 | } | ||
139 | 152 | ||
140 | /* Signal handler */ | 153 | udhcp_logging(LOG_INFO, "%s (v%s) started", client_server, VERSION); |
141 | int udhcp_signal_pipe[2]; | ||
142 | static void signal_handler(int sig) | ||
143 | { | ||
144 | if (send(udhcp_signal_pipe[1], &sig, sizeof(sig), MSG_DONTWAIT) < 0) { | ||
145 | LOG(LOG_ERR, "Could not send signal: %m"); | ||
146 | } | ||
147 | } | 154 | } |
155 | #endif | ||
148 | 156 | ||
149 | void udhcp_set_signal_pipe(int sig_add) | ||
150 | { | ||
151 | socketpair(AF_UNIX, SOCK_STREAM, 0, udhcp_signal_pipe); | ||
152 | signal(SIGUSR1, signal_handler); | ||
153 | signal(SIGTERM, signal_handler); | ||
154 | if(sig_add) | ||
155 | signal(sig_add, signal_handler); | ||
156 | } | ||