aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDenis Vlasenko <vda.linux@googlemail.com>2007-01-14 12:07:25 +0000
committerDenis Vlasenko <vda.linux@googlemail.com>2007-01-14 12:07:25 +0000
commit19250813a83cb4e1691810d1887658e60e2942d8 (patch)
tree0994c9573d56581db0bd44bbc89aba34eaac1c6c
parentffcef2d1f71a1707b94e235e63495178144de861 (diff)
downloadbusybox-w32-19250813a83cb4e1691810d1887658e60e2942d8.tar.gz
busybox-w32-19250813a83cb4e1691810d1887658e60e2942d8.tar.bz2
busybox-w32-19250813a83cb4e1691810d1887658e60e2942d8.zip
fakeidentd: fix daemon mode (was thinking that it is in
inetd-wait mode and dying after timeout). Minor fixes, comments are improved in places.
-rw-r--r--networking/isrv.c31
-rw-r--r--networking/isrv_identd.c19
2 files changed, 27 insertions, 23 deletions
diff --git a/networking/isrv.c b/networking/isrv.c
index 02ca1d787..5193f30f3 100644
--- a/networking/isrv.c
+++ b/networking/isrv.c
@@ -21,6 +21,8 @@
21 21
22/* Helpers */ 22/* Helpers */
23 23
24/* Even if _POSIX_MONOTONIC_CLOCK is defined, this
25 * may require librt */
24#if 0 /*def _POSIX_MONOTONIC_CLOCK*/ 26#if 0 /*def _POSIX_MONOTONIC_CLOCK*/
25static time_t monotonic_time(void) 27static time_t monotonic_time(void)
26{ 28{
@@ -194,7 +196,8 @@ static void handle_accept(isrv_state_t *state, int fd)
194 if (newfd < 0) { 196 if (newfd < 0) {
195 if (errno == EAGAIN) return; 197 if (errno == EAGAIN) return;
196 /* Most probably someone gave us wrong fd type 198 /* Most probably someone gave us wrong fd type
197 * (for example, non-socket) */ 199 * (for example, non-socket). Don't want
200 * to loop forever. */
198 bb_perror_msg_and_die("accept"); 201 bb_perror_msg_and_die("accept");
199 } 202 }
200 203
@@ -210,6 +213,7 @@ static void handle_fd_set(isrv_state_t *state, fd_set *fds, int (*h)(int, void *
210 enum { LONG_CNT = sizeof(fd_set) / sizeof(long) }; 213 enum { LONG_CNT = sizeof(fd_set) / sizeof(long) };
211 int fds_pos; 214 int fds_pos;
212 int fd, peer; 215 int fd, peer;
216 /* need to know value at _the beginning_ of this routine */
213 int fd_cnt = FD_COUNT; 217 int fd_cnt = FD_COUNT;
214 218
215 if (LONG_CNT * sizeof(long) != sizeof(fd_set)) 219 if (LONG_CNT * sizeof(long) != sizeof(fd_set))
@@ -235,10 +239,15 @@ static void handle_fd_set(isrv_state_t *state, fd_set *fds, int (*h)(int, void *
235 } 239 }
236 break; /* all words are zero */ 240 break; /* all words are zero */
237 found_fd: 241 found_fd:
238 if (fd >= fd_cnt) /* paranoia */ 242 if (fd >= fd_cnt) { /* paranoia */
243 DPRINTF("handle_fd_set: fd > fd_cnt?? (%d > %d)",
244 fd, fd_cnt);
239 break; 245 break;
246 }
240 DPRINTF("handle_fd_set: fd %d is active", fd); 247 DPRINTF("handle_fd_set: fd %d is active", fd);
241 peer = FD2PEER[fd]; 248 peer = FD2PEER[fd];
249 if (peer < 0)
250 continue; /* peer is already gone */
242 if (peer == 0) { 251 if (peer == 0) {
243 handle_accept(state, fd); 252 handle_accept(state, fd);
244 continue; 253 continue;
@@ -259,9 +268,9 @@ static void handle_timeout(isrv_state_t *state, int (*do_timeout)(void **))
259 peer = PEER_COUNT-1; 268 peer = PEER_COUNT-1;
260 /* peer 0 is not checked */ 269 /* peer 0 is not checked */
261 while (peer > 0) { 270 while (peer > 0) {
262 DPRINTF("peer %d: time diff %d", peer, (int)(CURTIME - TIMEO_TBL[peer])); 271 DPRINTF("peer %d: time diff %d", peer,
263 272 (int)(CURTIME - TIMEO_TBL[peer]));
264 if ((CURTIME - TIMEO_TBL[peer]) > TIMEOUT) { 273 if ((CURTIME - TIMEO_TBL[peer]) >= TIMEOUT) {
265 DPRINTF("peer %d: do_timeout()", peer); 274 DPRINTF("peer %d: do_timeout()", peer);
266 n = do_timeout(&PARAM_TBL[peer]); 275 n = do_timeout(&PARAM_TBL[peer]);
267 if (n) 276 if (n)
@@ -279,7 +288,7 @@ void isrv_run(
279 int (*do_wr)(int fd, void **), 288 int (*do_wr)(int fd, void **),
280 int (*do_timeout)(void **), 289 int (*do_timeout)(void **),
281 int timeout, 290 int timeout,
282 int exit_if_no_clients) 291 int linger_timeout)
283{ 292{
284 isrv_state_t *state = xzalloc(sizeof(*state)); 293 isrv_state_t *state = xzalloc(sizeof(*state));
285 state->new_peer = new_peer; 294 state->new_peer = new_peer;
@@ -300,6 +309,8 @@ void isrv_run(
300 int n; 309 int n;
301 310
302 tv.tv_sec = timeout; 311 tv.tv_sec = timeout;
312 if (PEER_COUNT <= 1)
313 tv.tv_sec = linger_timeout;
303 tv.tv_usec = 0; 314 tv.tv_usec = 0;
304 rd = state->rd; 315 rd = state->rd;
305 if (WR_COUNT) { 316 if (WR_COUNT) {
@@ -307,8 +318,9 @@ void isrv_run(
307 wrp = &wr; 318 wrp = &wr;
308 } 319 }
309 320
310 DPRINTF("run: select(FD_COUNT:%d,timeout:%d)...", FD_COUNT, timeout); 321 DPRINTF("run: select(FD_COUNT:%d,timeout:%d)...",
311 n = select(FD_COUNT, &rd, wrp, NULL, timeout ? &tv : NULL); 322 FD_COUNT, (int)tv.tv_sec);
323 n = select(FD_COUNT, &rd, wrp, NULL, tv.tv_sec ? &tv : NULL);
312 DPRINTF("run: ...select:%d", n); 324 DPRINTF("run: ...select:%d", n);
313 325
314 if (n < 0) { 326 if (n < 0) {
@@ -317,7 +329,7 @@ void isrv_run(
317 continue; 329 continue;
318 } 330 }
319 331
320 if (exit_if_no_clients && n == 0 && PEER_COUNT <= 1) 332 if (n == 0 && linger_timeout && PEER_COUNT <= 1)
321 break; 333 break;
322 334
323 if (timeout) { 335 if (timeout) {
@@ -334,4 +346,5 @@ void isrv_run(
334 } 346 }
335 } 347 }
336 DPRINTF("run: bailout"); 348 DPRINTF("run: bailout");
349 /* NB: accept socket is not closed. Caller is to decide what to do */
337} 350}
diff --git a/networking/isrv_identd.c b/networking/isrv_identd.c
index b9481f8d3..30f9a7a26 100644
--- a/networking/isrv_identd.c
+++ b/networking/isrv_identd.c
@@ -13,14 +13,6 @@
13 13
14enum { TIMEOUT = 20 }; 14enum { TIMEOUT = 20 };
15 15
16/* Why use alarm(TIMEOUT-1)?
17 * isrv's internal select() will run with timeout=TIMEOUT.
18 * If nothing happens during TIMEOUT-1 seconds (no accept/read),
19 * then ALL sessions timed out by now. Instead of closing them one-by-one
20 * (isrv calls do_timeout for each 'stale' session),
21 * SIGALRM triggered by alarm(TIMEOUT-1) will kill us, terminating them all.
22 */
23
24typedef struct identd_buf_t { 16typedef struct identd_buf_t {
25 int pos; 17 int pos;
26 int fd_flag; 18 int fd_flag;
@@ -34,8 +26,6 @@ static int new_peer(isrv_state_t *state, int fd)
34 int peer; 26 int peer;
35 identd_buf_t *buf = xzalloc(sizeof(*buf)); 27 identd_buf_t *buf = xzalloc(sizeof(*buf));
36 28
37 alarm(TIMEOUT - 1);
38
39 peer = isrv_register_peer(state, buf); 29 peer = isrv_register_peer(state, buf);
40 if (peer < 0) 30 if (peer < 0)
41 return 0; /* failure */ 31 return 0; /* failure */
@@ -53,11 +43,9 @@ static int do_rd(int fd, void **paramp)
53 char *cur, *p; 43 char *cur, *p;
54 int sz; 44 int sz;
55 45
56 alarm(TIMEOUT - 1);
57
58 cur = buf->buf + buf->pos; 46 cur = buf->buf + buf->pos;
59 47
60 fcntl(fd, F_SETFL, buf->fd_flag | O_NONBLOCK); 48 fcntl(fd, F_SETFL, buf->fd_flag);
61 sz = safe_read(fd, cur, sizeof(buf->buf) - buf->pos); 49 sz = safe_read(fd, cur, sizeof(buf->buf) - buf->pos);
62 50
63 if (sz < 0) { 51 if (sz < 0) {
@@ -95,6 +83,8 @@ static void inetd_mode(void)
95 identd_buf_t *buf = xzalloc(sizeof(*buf)); 83 identd_buf_t *buf = xzalloc(sizeof(*buf));
96 /* We do NOT want nonblocking I/O here! */ 84 /* We do NOT want nonblocking I/O here! */
97 buf->fd_flag = fcntl(0, F_GETFL, 0); 85 buf->fd_flag = fcntl(0, F_GETFL, 0);
86 do
87 alarm(TIMEOUT);
98 while (do_rd(0, (void*)&buf) == 0) /* repeat */; 88 while (do_rd(0, (void*)&buf) == 0) /* repeat */;
99} 89}
100 90
@@ -139,6 +129,7 @@ int fakeidentd_main(int argc, char **argv)
139 xlisten(fd, 5); 129 xlisten(fd, 5);
140 } 130 }
141 131
142 isrv_run(fd, new_peer, do_rd, NULL, do_timeout, TIMEOUT, 1); 132 isrv_run(fd, new_peer, do_rd, /*do_wr:*/ NULL, do_timeout,
133 TIMEOUT, (opt & OPT_inetdwait) ? TIMEOUT : 0);
143 return 0; 134 return 0;
144} 135}