|
|
1.1 root 1: /* bbexp.c - expunge the BBoards area */
2:
3: #include "../h/mh.h"
4: #include "../h/dropsbr.h"
5: #include "../zotnet/bboards.h"
6: #include <pwd.h>
7: #include <signal.h>
8: #include <stdio.h>
9: #include <sys/types.h>
10: #include <sys/stat.h>
11:
12:
13: #define FIRST 12
14: #define SECOND 20
15:
16:
17: static int broken_pipe;
18:
19: int pipeser ();
20:
21:
22: struct passwd *getpwnam ();
23:
24: /* */
25:
26: /* ARGSUSED */
27:
28: main (argc, argv)
29: int argc;
30: char **argv;
31: {
32: int first = FIRST,
33: second = SECOND;
34: char *cp;
35: struct bboard *bb;
36: struct passwd *pw;
37:
38: invo_name = r1bindex (*argv++, '/');
39: m_foil (NULLCP);
40:
41: if ((pw = getpwnam (BBOARDS)) == NULL)
42: adios (NULLCP, "no entry for ~%s", BBOARDS);
43: if (pw -> pw_uid != geteuid ())
44: adios (NULLCP, "not running setuid to %s", BBOARDS);
45:
46: if (*argv && **argv == '-') {
47: if ((first = atoi (*argv + 1)) < 1)
48: first = FIRST;
49: argv++;
50: }
51: if (*argv && **argv == '-') {
52: if ((second = atoi (*argv + 1)) < 1)
53: second = SECOND;
54: argv++;
55: }
56:
57: (void) setbbent (SB_STAY);
58: if (*argv == NULL)
59: while (bb = getbbent ()) {
60: if ((bb -> bb_flags & BB_ARCH) & (BB_ASAV | BB_AREM))
61: process (bb, pw, first, second);
62: }
63: else
64: while (cp = *argv++)
65: if ((bb = getbbnam (cp)) || (bb = getbbaka (cp))) {
66: if ((bb -> bb_flags & BB_ARCH) & (BB_ASAV | BB_AREM))
67: process (bb, pw, first, second);
68: }
69: else
70: advise (NULLCP, "no such BBoard as %s", cp);
71: (void) endbbent ();
72:
73: exit (0);
74: }
75:
76: /* */
77:
78: static process (bb, pw, first, second)
79: struct bboard *bb;
80: struct passwd *pw;
81: int first,
82: second;
83: {
84: int fd,
85: td;
86: char *cp,
87: command[BUFSIZ],
88: tmpfil[BUFSIZ];
89: FILE *pf;
90: struct stat st;
91:
92: if ((fd = lkopen (bb -> bb_file, 6)) == NOTOK) {
93: advise (bb -> bb_file, "unable to lock and open");
94: return;
95: }
96:
97: (void) sprintf (tmpfil, "%s/#bbexpXXXXXX", pw -> pw_dir);
98: (void) unlink (mktemp (tmpfil));
99: if ((td = creat (tmpfil, 0600)) == NOTOK) {
100: advise (tmpfil, "unable to create");
101: goto out1;
102: }
103: (void) close (td);
104: if ((td = creat (cp = map_name (tmpfil), 0600)) == NOTOK) {
105: advise (cp, "unable to create");
106: goto out2;
107: }
108: (void) close (td);
109:
110: if ((bb -> bb_flags & BB_ARCH)
111: && stat (bb -> bb_archive, &st) == NOTOK
112: && stat (bb -> bb_file, &st) != NOTOK
113: && (td = creat (bb -> bb_archive, (int) (st.st_mode & 0777))) != NOTOK)
114: (void) close (td);
115:
116: (void) sprintf (command, "%s %s%s", mshproc, bb -> bb_file,
117: isatty (fileno (stdout)) ? " 2>&1 | cat" : "");
118: printf ("%s (%s old messages)\n", command,
119: (bb -> bb_flags & BB_ARCH) == BB_ASAV ? "archive" : "remove");
120: (void) fflush (stdout);
121: if ((pf = popen (command, "w")) == NULL) {
122: advise (NULLCP, "unable to popen \"%s\" for writing", command);
123: goto out3;
124: }
125: (void) signal (SIGPIPE, pipeser);
126: broken_pipe = 0;
127:
128: fprintf (pf, "pick %s -before -%d -sequence select -zero\n",
129: "-datefield BB-Posted", first);
130: fprintf (pf, "pick -before -%d -sequence select -nozero\n", second);
131: fprintf (pf, "scan select\n");
132: if ((bb -> bb_flags & BB_ARCH) == BB_ASAV)
133: fprintf (pf, "pack select -file %s\n", bb -> bb_archive);
134: fprintf (pf, "rmm select\n");
135: fprintf (pf, "packf all -file %s\n", tmpfil);
136: #ifdef notdef /* want real EOF to end it */
137: fprintf (pf, "quit\n");
138: #endif notdef
139: if (td = pclose (pf))
140: advise (NULLCP, "msh returns %d", td);
141: (void) signal (SIGPIPE, SIG_DFL);
142:
143: if (move (tmpfil, bb -> bb_file) != NOTOK)
144: (void) move (cp, bb -> bb_map);
145:
146: out3: ;
147: (void) unlink (cp);
148: out2: ;
149: (void) unlink (tmpfil);
150: out1: ;
151: (void) lkclose (fd, bb -> bb_file);
152: }
153:
154: /* */
155:
156: static int move (input, output)
157: char *input,
158: *output;
159: {
160: int i,
161: in,
162: out;
163: struct stat st1,
164: st2;
165:
166: if ((in = open (input, 0)) == NOTOK) {
167: advise (input, "unable to re-open");
168: return NOTOK;
169: }
170:
171: i = stat (output, &st1);
172: if ((out = creat (output, BBMODE)) == NOTOK) {
173: advise (output, "unable to re-create");
174: return NOTOK;
175: }
176: if (i != NOTOK && chmod (output, (int) (st1.st_mode & 0777)) == NOTOK)
177: admonish (output, "unable to change mode of");
178: if (i != NOTOK && stat (output, &st2) != NOTOK && st2.st_gid != st1.st_gid)
179: chgrp (output, st1.st_gid);
180:
181: cpydata (in, out, input, output);
182:
183: (void) close (in);
184: (void) close (out);
185:
186: return OK;
187: }
188:
189: /* */
190:
191: static chgrp (file, gid)
192: char *file;
193: short gid;
194: {
195: int child_id;
196: char group[BUFSIZ];
197:
198: switch (child_id = fork ()) {
199: case NOTOK:
200: admonish ("fork", "unable to");
201: return;
202:
203: case OK:
204: (void) setuid (geteuid ());
205: (void) sprintf (group, "%d", gid);
206: execlp ("/bin/chgrp", chgrp, group, file, NULLCP);
207: fprintf (stderr, "unable to exec ");
208: perror ("/bin/chgrp");
209: _exit (1);
210:
211: default:
212: (void) pidwait (child_id, OK);
213: break;
214: }
215: }
216:
217: /* */
218:
219: /* ARGSUSED */
220:
221: static int pipeser (i)
222: int i;
223: {
224: #ifndef BSD42
225: (void) signal (SIGPIPE, pipeser);
226: #endif not BSD42
227:
228: if (!broken_pipe++)
229: advise (NULLCP, "broken pipe");
230: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.