Annotation of /trunk/mkinitrd-magellan/busybox/sysklogd/logread.c
Parent Directory | Revision Log
Revision 532 -
(hide annotations)
(download)
Sat Sep 1 22:45:15 2007 UTC (16 years, 8 months ago) by niro
File MIME type: text/plain
File size: 3371 byte(s)
Sat Sep 1 22:45:15 2007 UTC (16 years, 8 months ago) by niro
File MIME type: text/plain
File size: 3371 byte(s)
-import if magellan mkinitrd; it is a fork of redhats mkinitrd-5.0.8 with all magellan patches and features; deprecates magellan-src/mkinitrd
1 | niro | 532 | /* vi: set sw=4 ts=4: */ |
2 | /* | ||
3 | * circular buffer syslog implementation for busybox | ||
4 | * | ||
5 | * Copyright (C) 2000 by Gennady Feldman <gfeldman@gena01.com> | ||
6 | * | ||
7 | * Maintainer: Gennady Feldman <gfeldman@gena01.com> as of Mar 12, 2001 | ||
8 | * | ||
9 | * Licensed under GPLv2 or later, see file LICENSE in this tarball for details. | ||
10 | */ | ||
11 | |||
12 | #include "busybox.h" | ||
13 | #include <sys/ipc.h> | ||
14 | #include <sys/sem.h> | ||
15 | #include <sys/shm.h> | ||
16 | |||
17 | #define DEBUG 0 | ||
18 | |||
19 | enum { KEY_ID = 0x414e4547 }; /* "GENA" */ | ||
20 | |||
21 | static struct shbuf_ds { | ||
22 | int32_t size; // size of data written | ||
23 | int32_t head; // start of message list | ||
24 | int32_t tail; // end of message list | ||
25 | char data[1]; // data/messages | ||
26 | } *buf; // shared memory pointer | ||
27 | |||
28 | // Semaphore operation structures | ||
29 | static struct sembuf SMrup[1] = {{0, -1, IPC_NOWAIT | SEM_UNDO}}; // set SMrup | ||
30 | static struct sembuf SMrdn[2] = {{1, 0}, {0, +1, SEM_UNDO}}; // set SMrdn | ||
31 | |||
32 | |||
33 | static void error_exit(const char *str) ATTRIBUTE_NORETURN; | ||
34 | static void error_exit(const char *str) | ||
35 | { | ||
36 | //release all acquired resources | ||
37 | shmdt(buf); | ||
38 | bb_perror_msg_and_die(str); | ||
39 | } | ||
40 | |||
41 | /* | ||
42 | * sem_up - up()'s a semaphore. | ||
43 | */ | ||
44 | static void sem_up(int semid) | ||
45 | { | ||
46 | if (semop(semid, SMrup, 1) == -1) | ||
47 | error_exit("semop[SMrup]"); | ||
48 | } | ||
49 | |||
50 | static void interrupted(int sig ATTRIBUTE_UNUSED) | ||
51 | { | ||
52 | signal(SIGINT, SIG_IGN); | ||
53 | shmdt(buf); | ||
54 | exit(0); | ||
55 | } | ||
56 | |||
57 | int logread_main(int argc, char **argv) | ||
58 | { | ||
59 | int cur; | ||
60 | int log_semid; /* ipc semaphore id */ | ||
61 | int log_shmid; /* ipc shared memory id */ | ||
62 | smallint follow = getopt32(argc, argv, "f"); | ||
63 | |||
64 | log_shmid = shmget(KEY_ID, 0, 0); | ||
65 | if (log_shmid == -1) | ||
66 | bb_perror_msg_and_die("can't find syslogd buffer"); | ||
67 | |||
68 | // Attach shared memory to our char* | ||
69 | buf = shmat(log_shmid, NULL, SHM_RDONLY); | ||
70 | if (buf == NULL) | ||
71 | bb_perror_msg_and_die("can't access syslogd buffer"); | ||
72 | |||
73 | log_semid = semget(KEY_ID, 0, 0); | ||
74 | if (log_semid == -1) | ||
75 | error_exit("can't get access to semaphores for syslogd buffer"); | ||
76 | |||
77 | // attempt to redefine ^C signal | ||
78 | signal(SIGINT, interrupted); | ||
79 | |||
80 | // Suppose atomic memory move | ||
81 | cur = follow ? buf->tail : buf->head; | ||
82 | |||
83 | do { | ||
84 | #if ENABLE_FEATURE_LOGREAD_REDUCED_LOCKING | ||
85 | char *buf_data; | ||
86 | int log_len, j; | ||
87 | #endif | ||
88 | if (semop(log_semid, SMrdn, 2) == -1) | ||
89 | error_exit("semop[SMrdn]"); | ||
90 | |||
91 | if (DEBUG) | ||
92 | printf("head:%i cur:%d tail:%i size:%i\n", | ||
93 | buf->head, cur, buf->tail, buf->size); | ||
94 | |||
95 | if (buf->head == buf->tail || cur == buf->tail) { | ||
96 | if (follow) { | ||
97 | sem_up(log_semid); | ||
98 | fflush(stdout); | ||
99 | sleep(1); /* TODO: replace me with a sleep_on */ | ||
100 | continue; | ||
101 | } | ||
102 | puts("<empty syslog>"); | ||
103 | } | ||
104 | |||
105 | // Read Memory | ||
106 | #if ENABLE_FEATURE_LOGREAD_REDUCED_LOCKING | ||
107 | log_len = buf->tail - cur; | ||
108 | if (log_len < 0) | ||
109 | log_len += buf->size; | ||
110 | buf_data = xmalloc(log_len); | ||
111 | |||
112 | if (buf->tail >= cur) | ||
113 | j = log_len; | ||
114 | else | ||
115 | j = buf->size - cur; | ||
116 | memcpy(buf_data, buf->data + cur, j); | ||
117 | |||
118 | if (buf->tail < cur) | ||
119 | memcpy(buf_data + buf->size - cur, buf->data, buf->tail); | ||
120 | cur = buf->tail; | ||
121 | #else | ||
122 | while (cur != buf->tail) { | ||
123 | fputs(buf->data + cur, stdout); | ||
124 | cur += strlen(buf->data + cur) + 1; | ||
125 | if (cur >= buf->size) | ||
126 | cur = 0; | ||
127 | } | ||
128 | #endif | ||
129 | // release the lock on the log chain | ||
130 | sem_up(log_semid); | ||
131 | |||
132 | #if ENABLE_FEATURE_LOGREAD_REDUCED_LOCKING | ||
133 | for (j = 0; j < log_len; j += strlen(buf_data+j) + 1) { | ||
134 | fputs(buf_data + j, stdout); | ||
135 | } | ||
136 | free(buf_data); | ||
137 | #endif | ||
138 | } while (follow); | ||
139 | |||
140 | shmdt(buf); | ||
141 | |||
142 | fflush_stdout_and_exit(EXIT_SUCCESS); | ||
143 | } |