|
|
1.1 root 1: /* mhconfig.c - configure MH */
2:
3: #include "../h/strings.h"
4: #include <ctype.h>
5: #include <stdio.h>
6:
7:
8: #define BANNER "This is %s, for generic UNIX (MH.6 configuration program)\n\n"
9:
10:
11: #define SED "config.sed"
12: #define SEDOC "doc/config.sed"
13: #define MFIL(f) "makefiles/f", "f"
14: #define MMFIL(f,g) "makefiles/f", "g"
15: #define MAKE "../%s/Makefile"
16:
17: #define WARNING "This file is automatically generated. Do not edit!"
18:
19: #define NOTOK (-1)
20:
21: #define NULLCP ((char *) 0)
22:
23: #define SVAL(s) (s ? s : "")
24:
25: #define QUOTE '\\'
26:
27: /* */
28:
29: static int smtp = 0;
30:
31: static int sedP = 1;
32: static int filesP = 1;
33: static int docP = 1;
34: static int makeP = 1;
35:
36: static char *myname = "mhconfig";
37:
38: static char *myopts = NULL;
39:
40: static char *binpath = "/usr/local";
41: static char *bbhome = "/usr/spool/bboards";
42: static char *bboards = "off";
43: static char *ccoptions = NULL;
44: static char *chownpath = "/etc/chown";
45: static char *curses = "-lcurses -ltermlib";
46: static char *debug = "off";
47: static char *editor = "prompter";
48: static char *etcpath = "/usr/local/lib/mh";
49: static char *ldoptions = NULL;
50: static char *ldoptlibs = NULL;
51: static char *mailpath = "/usr/spool/mail";
52: static char *maildir = NULL;
53: static char *mailfile = NULL;
54: static char *mandir = "/usr/man";
55: static char *manuals = "standard";
56: static char *mf = "off";
57: static char *mts = "sendmail";
58: static char *remove = "mv -f";
59: static char *oldload = "off";
60: static char *options = NULL;
61: static char *pop = "off";
62: static char *popbboards = "off";
63: static char *ranlib = "on";
64: static char *tma = "off";
65:
66: #define unknown 0
67: #define mmdf 1
68: #define mmdf2 2
69: #define mh 3
70: #define sendmail 4
71: static int mtsnum = unknown;
72:
73: static struct mtsopt {
74: char *mtskey;
75: char *optval;
76: int code;
77: int mtsflags;
78: #define NOFLAGS 0x00
79: #define DOSMTP 0x01
80: #define NOMF 0x02
81: } mtsopts[] = {
82: "mmdf", "MMDFMTS MMDFI", mmdf, NOFLAGS,
83: "mmdf/smtp", "SENDMTS SMTP", mmdf, DOSMTP,
84: "mmdf2", "MMDFMTS MMDFII", mmdf2, NOFLAGS,
85: "mmdf2/smtp", "SENDMTS MMDFII SMTP", mmdf2, DOSMTP,
86: "mh", "MHMTS", mh, NOFLAGS,
87: "sendmail", "SENDMTS", sendmail, NOMF,
88: "sendmail/smtp", "SENDMTS SMTP", sendmail, NOMF,
89: NULL, NULL, unknown, NOFLAGS
90: };
91:
92: static struct bind {
93: char *keyword;
94:
95: char **value;
96:
97: int flags;
98: #define BD_NIL 0x00
99: #define BD_ADD 0x01
100: } binds[] = {
101: "bin", &binpath, BD_NIL,
102: "bbhome", &bbhome, BD_NIL,
103: "bboards", &bboards, BD_NIL,
104: "ccoptions", &ccoptions, BD_ADD,
105: "chown", &chownpath, BD_NIL,
106: "curses", &curses, BD_NIL,
107: "debug", &debug, BD_NIL,
108: "editor", &editor, BD_NIL,
109: "etc", &etcpath, BD_NIL,
110: "ldoptions", &ldoptions, BD_ADD,
111: "ldoptlibs", &ldoptlibs, BD_ADD,
112: "mail", &mailpath, BD_NIL,
113: "mandir", &mandir, BD_NIL,
114: "manuals", &manuals, BD_NIL,
115: "mf", &mf, BD_NIL,
116: "mts", &mts, BD_NIL,
117: "oldload", &oldload, BD_NIL,
118: "options", &options, BD_ADD,
119: "pop", &pop, BD_NIL,
120: "popbboards", &popbboards, BD_NIL,
121: "ranlib", &ranlib, BD_NIL,
122: "remove", &remove, BD_NIL,
123: "tma", &tma, BD_NIL,
124: NULL
125: };
126:
127:
128: char *files[] = {
129: "../support/bboards/bboards.daily",
130: "../support/bboards/bboards.weekly",
131: "../support/bboards/crontab",
132: "../support/bboards/MakeBBoards",
133: "../config/config.c",
134: "../zotnet/mts/mts.c",
135: "../zotnet/mts/mtstailor",
136: "../support/general/MailAliases",
137: "../mts/sendmail/bboardsMH.m4",
138: "../mts/sendmail/popMH.m4",
139: NULL
140: };
141:
142: static struct pair {
143: char *infile;
144: char *outfile;
145: } makefiles[] = {
146: MFIL (config),
147: MFIL (dist),
148: MFIL (doc),
149: MMFIL (mtsM,mts),
150: MFIL (mts/mh),
151: MFIL (mts/mmdf),
152: MFIL (mts/sendmail),
153: MFIL (papers),
154: MFIL (sbr),
155: MMFIL (supportM,support),
156: MFIL (support/bboards),
157: MFIL (support/general),
158: MFIL (support/pop),
159: MFIL (uip),
160: MMFIL (zotnetM,zotnet),
161: MFIL (zotnet/bboards),
162: MFIL (zotnet/mf),
163: MFIL (zotnet/mts),
164: MFIL (zotnet/tws),
165: NULL
166: };
167:
168:
169: char *stradd (), *strdup (), *tail ();
170:
171: long time ();
172:
173: /* */
174:
175: /* ARGSUSED */
176:
177: main (argc, argv, envp)
178: int argc;
179: char **argv,
180: **envp;
181: {
182: arginit (argv);
183:
184: if (sedP)
185: do_sed ();
186: if (filesP)
187: do_files ();
188: if (docP)
189: do_doc ();
190: if (makeP)
191: do_make ();
192:
193: if (filesP || makeP)
194: printf ("Don't forget to run \"make clean\" before proceeding\n");
195:
196: exit (0);
197: }
198:
199: /* */
200:
201: static do_sed () {
202: do_sedfile (SED, 0);
203: do_sedfile (SEDOC, smtp);
204: }
205:
206:
207: static do_sedfile (sed, flag)
208: char *sed;
209: int flag;
210: {
211: int i;
212: FILE * fp;
213:
214: if ((fp = fopen (sed, "w")) == NULL)
215: adios (sed, "unable to write");
216: printf ("generating %s\n", sed);
217:
218: fprintf (fp, "s%%@(MHWARNING)%%%s%%g\n", WARNING);
219: fprintf (fp, "s%%@(MHBINPATH)%%%s%%g\n", SVAL (binpath));
220: fprintf (fp, "s%%@(MHETCPATH)%%%s%%g\n", SVAL (etcpath));
221: fprintf (fp, "s%%@(MHCHOWNPATH)%%%s%%g\n", SVAL (chownpath));
222: fprintf (fp, "s%%@(MHDROPATH)%%%s%%g\n", SVAL (maildir));
223: fprintf (fp, "s%%@(MHDROPFIL)%%%s%%g\n", SVAL (mailfile));
224: if (maildir)
225: fprintf (fp, "s%%@(MHDROPLOC)%%%s/$USER%%g\n", SVAL (maildir));
226: else
227: fprintf (fp, "s%%@(MHDROPLOC)%%$HOME/%s%%g\n", SVAL (mailfile));
228: fprintf (fp, "s%%@(MHDROPHAK)%%%s%%g\n",/* HACK */
229: maildir ? maildir : "/usr/spool/mail");
230:
231: fprintf (fp, "s%%@(MHMANDIR)%%%s%%g\n", mandir);
232: if (strcmp (manuals, "standard") == 0 || strcmp (manuals, "gen") == 0)
233: for (i = 1; i <= 8; i++) {
234: fprintf (fp, "s%%@(MHMANDIR%d)%%man%d%%g\n", i, i);
235: fprintf (fp, "s%%@(MHMANEXT%d)%%%d%%g\n", i, i);
236: }
237: else
238: for (i = 1; i <= 8; i++) {
239: fprintf (fp, "s%%@(MHMANDIR%d)%%man%c%%g\n", i,
240: strcmp (manuals, "new") == 0 ? 'n'
241: : strcmp (manuals, "old") == 0 ? 'o'
242: : 'l');
243: fprintf (fp, "s%%@(MHMANEXT%d)%%%c%%g\n", i,
244: strcmp (manuals, "new") == 0 ? 'n'
245: : strcmp (manuals, "old") == 0 ? 'o'
246: : 'l');
247: }
248: if (strcmp (manuals, "gen") == 0)
249: fprintf (fp, "s%%@(MHMANGEN)%%%s%%g\n", "#"); /* comment char */
250: else
251: fprintf (fp, "s%%@(MHMANGEN)%%%s%%g\n", "");
252:
253: fprintf (fp, "s%%@(MHEDITOR)%%%s%%g\n", SVAL (editor));
254: fprintf (fp, "s%%@(MHCONFIG)%%%s%%g\n", SVAL (myopts));
255: if (ccoptions)
256: fprintf (fp, "s%%@(MHOPTIONS)%%%s %s%%g\n",
257: SVAL (options), SVAL (ccoptions));
258: else
259: fprintf (fp, "s%%@(MHOPTIONS)%%%s%%g\n", SVAL (options));
260: fprintf (fp, "s%%@(LDOPTIONS)%%%s%%g\n", SVAL (ldoptions));
261: fprintf (fp, "s%%@(LDOPTLIB)%%%s%%g\n", SVAL (ldoptlibs));
262: fprintf (fp, "s%%@(LDCURSES)%%%s%%g\n", SVAL (curses));
263:
264: if (strcmp (bboards, "on") == 0)
265: fprintf (fp, "/^@BEGIN: BBOARDS$/d\n/^@END: BBOARDS$/d\n");
266: else
267: fprintf (fp, "/^@BEGIN: BBOARDS$/,/^@END: BBOARDS$/d\n");
268: fprintf (fp, "s%%@(BBHOME)%%%s%%g\n", SVAL (bbhome));
269:
270: if (strcmp (debug, "on") == 0) {
271: fprintf (fp, "/^@BEGIN: DEBUG$/d\n/^@END: DEBUG$/d\n");
272: fprintf (fp, "/^@BEGIN: OPTIM$/,/^@END: OPTIM$/d\n");
273: }
274: else {
275: fprintf (fp, "/^@BEGIN: DEBUG$/,/^@END: DEBUG$/d\n");
276: fprintf (fp, "/^@BEGIN: OPTIM$/d\n/^@END: OPTIM$/d\n");
277: }
278:
279: if (strcmp (oldload, "on") == 0) {
280: fprintf (fp, "/^@BEGIN: OLDLOAD$/d\n/^@END: OLDLOAD$/d\n");
281: fprintf (fp, "/^@BEGIN: NEWLOAD$/,/^@END: NEWLOAD$/d\n");
282: }
283: else {
284: fprintf (fp, "/^@BEGIN: NEWLOAD$/d\n/^@END: NEWLOAD$/d\n");
285: fprintf (fp, "/^@BEGIN: OLDLOAD$/,/^@END: OLDLOAD$/d\n");
286: }
287:
288: if (strcmp (ranlib, "on") == 0) {
289: fprintf (fp, "/^@BEGIN: RANLIB$/d\n/^@END: RANLIB$/d\n");
290: fprintf (fp, "/^@BEGIN: LORDER$/,/^@END: LORDER$/d\n");
291: }
292: else {
293: fprintf (fp, "/^@BEGIN: LORDER$/d\n/^@END: LORDER$/d\n");
294: fprintf (fp, "/^@BEGIN: RANLIB$/,/^@END: RANLIB$/d\n");
295: }
296:
297: if (strcmp (tma, "on") == 0)
298: fprintf (fp, "/^@BEGIN: TMA$/d\n/^@END: TMA$/d\n");
299: else
300: fprintf (fp, "/^@BEGIN: TMA$/,/^@END: TMA$/d\n");
301: if (flag || ((mtsnum == mmdf || mtsnum == mmdf2) && !smtp)) {
302: fprintf (fp, "/^@BEGIN: MMDFMTS$/d\n/^@END: MMDFMTS$/d\n");
303: if (mtsnum == mmdf)
304: fprintf (fp, "/^@BEGIN: MMDFIMTS$/d\n/^@END: MMDFIMTS$/d\n");
305: else
306: fprintf (fp, "/^@BEGIN: MMDFIMTS$/,/^@END: MMDFIMTS$/d\n");
307: if (mtsnum == mmdf2)
308: fprintf (fp, "/^@BEGIN: MMDFIIMTS$/d\n/^@END: MMDFIIMTS$/d\n");
309: else
310: fprintf (fp, "/^@BEGIN: MMDFIIMTS$/,/^@END: MMDFIIMTS$/d\n");
311: }
312: else {
313: fprintf (fp, "/^@BEGIN: MMDFMTS$/,/^@END: MMDFMTS$/d\n");
314: fprintf (fp, "/^@BEGIN: MMDFIMTS$/,/^@END: MMDFIMTS$/d\n");
315: fprintf (fp, "/^@BEGIN: MMDFIIMTS$/,/^@END: MMDFIIMTS$/d\n");
316: }
317:
318: if (mtsnum == mh)
319: fprintf (fp, "/^@BEGIN: MHMTS$/d\n/^@END: MHMTS$/d\n");
320: else
321: fprintf (fp, "/^@BEGIN: MHMTS$/,/^@END: MHMTS$/d\n");
322:
323: if (!flag && (mtsnum == sendmail || smtp))
324: fprintf (fp, "/^@BEGIN: SENDMTS$/d\n/^@END: SENDMTS$/d\n");
325: else
326: fprintf (fp, "/^@BEGIN: SENDMTS$/,/^@END: SENDMTS$/d\n");
327:
328: switch (mtsnum) {
329: case mh:
330: case sendmail:
331: case mmdf:
332: fprintf (fp, "/^@BEGIN: SENDMTSHACK$/d\n/^@END: SENDMTSHACK$/d\n");
333: break;
334:
335: default:
336: fprintf (fp, "/^@BEGIN: SENDMTSHACK$/,/^@END: SENDMTSHACK$/d\n");
337: break;
338: }
339:
340: if (smtp)
341: fprintf (fp, "/^@BEGIN: SMTP$/d\n/^@END: SMTP$/d\n");
342: else
343: fprintf (fp, "/^@BEGIN: SMTP$/,/^@END: SMTP$/d\n");
344:
345: if (strcmp (pop, "on") == 0)
346: fprintf (fp, "/^@BEGIN: POP$/d\n/^@END: POP$/d\n");
347: else
348: fprintf (fp, "/^@BEGIN: POP$/,/^@END: POP$/d\n");
349:
350: if (strcmp (popbboards, "on") == 0)
351: fprintf (fp, "/^@BEGIN: BPOP$/d\n/^@END: BPOP$/d\n");
352: else
353: fprintf (fp, "/^@BEGIN: BPOP$/,/^@END: BPOP$/d\n");
354:
355: if (strcmp (mf, "on") == 0)
356: fprintf (fp, "/^@BEGIN: MF$/d\n/^@END: MF$/d\n");
357: else
358: fprintf (fp, "/^@BEGIN: MF$/,/^@END: MF$/d\n");
359:
360: fprintf (fp, "s%%@(MHREMOVE)%%%s%%g\n", SVAL (remove));
361:
362: (void) fclose (fp);
363: }
364:
365: /* */
366:
367: static do_files () {
368: char **pp;
369:
370: for (pp = files; *pp; pp++)
371: shell ("rm -f %s; sed -f %s < config/%s > %s",
372: *pp, SED, tail (*pp), *pp);
373: }
374:
375:
376: static do_doc () {
377: shell ("mhdoc");
378: }
379:
380:
381: static do_make () {
382: char buffer[BUFSIZ];
383: struct pair *pp;
384:
385: for (pp = makefiles; pp -> infile; pp++) {
386: (void) sprintf (buffer, MAKE, pp -> outfile);
387: shell ("rm -f %s; sed -f %s < %s > %s",
388: buffer, SED, pp -> infile, buffer);
389: }
390: }
391:
392: /* */
393:
394: /* VARARGS */
395:
396: static shell (fmt, a, b, c, d)
397: char *fmt,
398: *a,
399: *b,
400: *c,
401: *d;
402: {
403: char buffer[BUFSIZ];
404:
405: (void) sprintf (buffer, fmt, a, b, c, d);
406: printf ("%s\n", buffer);
407: (void) fflush (stdout);
408:
409: if (system (buffer))
410: adios (NULLCP, "failed");
411: }
412:
413: /* */
414:
415: static arginit (vec)
416: char **vec;
417: {
418: int i;
419: char *ap,
420: *cp,
421: *dp,
422: *config,
423: buffer[BUFSIZ];
424: struct bind *bp;
425: FILE * fp;
426:
427: myname = tail (*vec);
428: printf (BANNER, myname);
429: (void) fflush (stdout);
430:
431: for (vec++;; vec++) {
432: if (strcmp (*vec, "-s") == 0) {
433: sedP = !sedP;
434: continue;
435: }
436: if (strcmp (*vec, "-f") == 0) {
437: filesP = !filesP;
438: continue;
439: }
440: if (strcmp (*vec, "-d") == 0) {
441: docP = !docP;
442: continue;
443: }
444: if (strcmp (*vec, "-m") == 0) {
445: makeP = !makeP;
446: continue;
447: }
448: break;
449: }
450: if ((config = *vec++) == NULL || *vec != NULL)
451: adios (NULLCP, "usage: %s file", myname);
452:
453: if ((fp = fopen (config, "r")) == NULL)
454: adios (config, "unable to read");
455:
456: while (fgets (buffer, sizeof buffer, fp)) {
457: if (ap = index (buffer, '\n'))
458: *ap-- = NULL;
459: else
460: ap = &buffer[strlen (buffer) - 1];
461: while (ap >= buffer)
462: if (isspace (*ap))
463: *ap = NULL;
464: else
465: break;
466: for (cp = buffer; isspace (*cp); cp++)
467: continue;
468: if (*cp == NULL || *cp == '#')
469: continue;
470: for (ap = cp; *ap; ap++)
471: if (isspace (*ap)) {
472: *ap++ = NULL;
473: while (isspace (*ap))
474: ap++;
475: break;
476: }
477: for (bp = binds; bp -> keyword; bp++)
478: if (strcmp (bp -> keyword, cp) == 0)
479: break;
480: if (bp -> keyword == NULL)
481: adios (NULLCP, "unknown option %s in %s", cp, config);
482: else
483: if (*(bp -> value) == NULL || !(bp -> flags & BD_ADD))
484: *(bp -> value) = strdup (ap);
485: else
486: *(bp -> value) = stradd (ap, stradd (" ", *(bp -> value)));
487: }
488:
489: (void) fclose (fp);
490:
491: /* */
492:
493: if (binpath == NULL)
494: adios (NULLCP, "bin must be specified in %s", config);
495: trim (binpath);
496:
497: if (strcmp (bboards, "on") && strcmp (bboards, "off"))
498: adios (NULLCP, "bboards should be either \"on\" or \"off\", not %s",
499: bboards);
500: if (bbhome == NULL)
501: adios (NULLCP, "bbhome must be specified in %s", config);
502: trim (bbhome);
503:
504: if (strcmp (debug, "on") && strcmp (debug, "off"))
505: adios (NULLCP, "debug should be either \"on\" or \"off\", not %s",
506: debug);
507:
508: if (etcpath == NULL)
509: adios (NULLCP, "etc must be specified in %s", config);
510: trim (etcpath);
511:
512: if (mailpath == NULL)
513: adios (NULLCP, "mail must be specified in %s", config);
514: trim (mailpath);
515: if (*mailpath == '/')
516: maildir = mailpath;
517: else
518: mailfile = mailpath;
519:
520: if (strcmp (manuals, "standard")
521: && strcmp (manuals, "local")
522: && strcmp (manuals, "new")
523: && strcmp (manuals, "old")
524: && strcmp (manuals, "gen")
525: && strcmp (manuals, "none"))
526: adios (NULLCP,"invalid manuals setting: %s",manuals);
527:
528: if (mts == NULL)
529: adios (NULLCP, "mts must be specified in %s", config);
530: for (i = 0; mtsopts[i].mtskey; i++)
531: if (strcmp (mts, mtsopts[i].mtskey) == 0)
532: break;
533: if ((mtsnum = mtsopts[i].code) == unknown)
534: adios (NULLCP, "invalid mts setting: %s", mts);
535: add_option (mtsopts[i].optval);
536: smtp = mtsopts[i].mtsflags & DOSMTP;
537: if (mtsopts[i].mtsflags & NOMF)
538: mf = "off"; /* hack... */
539:
540: if (strcmp (pop, "on") && strcmp (pop, "off"))
541: adios (NULLCP, "pop should be either \"on\" or \"off\", not %s", pop);
542: if (strcmp (pop, "on") == 0)
543: add_option ("POP");
544:
545: if (strcmp (popbboards, "on") && strcmp (popbboards, "off"))
546: adios (NULLCP, "popbboards should be either \"on\" or \"off\", not %s",
547: popbboards);
548: if (strcmp (popbboards, "on") == 0) {
549: add_option ("BPOP");
550: if (strcmp (bboards, "on") || strcmp (pop, "on"))
551: adios (NULLCP,
552: "popbboards \"on\" requires both bboards and pop \"on\"");
553: }
554:
555: if (strcmp (mf, "on") && strcmp (mf, "off"))
556: adios (NULLCP, "mf should be either \"on\" or \"off\", not %s", mf);
557: if (strcmp (mf, "on") == 0)
558: add_option ("MF");
559:
560: if (strcmp (tma, "on") && strcmp (tma, "off"))
561: adios (NULLCP, "tma should be either \"on\" or \"off\", not %s", tma);
562: if (strcmp (tma, "on") == 0)
563: add_option ("TMA");
564:
565: begin_myopt ();
566: if (cp = options) {
567: for (ap = cp; *ap; ap++)
568: if (isspace (*ap))
569: *ap = ' ';
570: options = NULL;
571: for (ap = cp; dp = index (ap, ' '); ap = dp) {
572: *dp++ = NULL;
573: add_myopt (ap);
574: (void) sprintf (buffer, "%s-D%s", options ? " " : "", ap);
575: ap = buffer;
576: options = stradd (ap, options);
577: while (isspace (*dp))
578: dp++;
579: }
580: if (*ap) {
581: add_myopt (ap);
582: (void) sprintf (buffer, "%s-D%s", options ? " " : "", ap);
583: ap = buffer;
584: options = stradd (ap, options);
585: }
586: free (cp);
587: }
588: end_myopt ();
589: }
590:
591: /* */
592:
593: static add_option (s)
594: char *s;
595: {
596: options = options ? stradd (s, stradd (" ", options)) : strdup (s);
597: }
598:
599:
600: begin_myopt () {
601: myopts = strdup ("char *options[] = {");
602: }
603:
604:
605: add_myopt (s)
606: char *s;
607: {
608: int len;
609: char *bp,
610: buffer[BUFSIZ];
611: static int nameoutput = 0;
612: static int linepos = 0;
613: static int outputlinelen = 72;
614:
615: if (!nameoutput) {
616: printf ("%s: ", bp = "options");
617: linepos += (nameoutput = strlen (bp) + 2);
618: }
619: len = strlen (s);
620: if (linepos != nameoutput)
621: if (len + linepos + 3 > outputlinelen)
622: printf ("\n%*s", linepos = nameoutput, "");
623: else
624: printf (" "), linepos++;
625: printf ("[%s]", s);
626: linepos += len + 2;
627: (void) fflush (stdout);
628:
629: bp = buffer;
630: *bp++ = '"';
631: while (*s) {
632: if (*s == '"')
633: *bp++ = QUOTE, *bp++ = QUOTE;
634: *bp++ = *s++;
635: }
636: (void) strcpy (bp, "\", ");
637: myopts = stradd (buffer, myopts);
638: }
639:
640:
641: end_myopt () {
642: printf ("\n");
643: (void) fflush (stdout);
644:
645: myopts = stradd ("NULL};", myopts);
646: }
647:
648: /* */
649:
650: static trim (s)
651: char *s;
652: {
653: char *p;
654:
655: if (s == NULL || (p = rindex (s, '/')) == NULL)
656: return;
657: if (*++p == NULL)
658: *--p = NULL;
659: }
660:
661:
662: static char *tail (s)
663: char *s;
664: {
665: char *p;
666:
667: if (p = rindex (s, '/'))
668: p++;
669: return ((p == NULL || *p == NULL) ? s : p);
670: }
671:
672: /* */
673:
674: static char *stradd (s1, s2)
675: char *s1,
676: *s2;
677: {
678: char *p;
679:
680: if (s1 == NULL || *s1 == NULL)
681: return s2;
682: if (s2 == NULL)
683: return strdup (s1);
684: if ((p = malloc ((unsigned) (strlen (s1) + strlen (s2) + 2))) == NULL)
685: adios (NULLCP, "insufficient memory");
686:
687: (void) sprintf (p, "%s%s", s2, s1);
688: if (s2)
689: free (s2);
690: return p;
691: }
692:
693:
694: static char *strdup (s)
695: char *s;
696: {
697: char *p;
698:
699: if ((p = malloc ((unsigned) (strlen (s) + 1))) == NULL)
700: adios (NULLCP, "insufficient memory");
701:
702: (void) strcpy (p, s);
703: return p;
704: }
705:
706: /* */
707:
708: static char *index (s, c)
709: char *s,
710: c;
711: {
712: char i;
713:
714: while (i = *s++)
715: if (i == c)
716: return (s - 1);
717:
718: return NULL;
719: }
720:
721:
722: static char *rindex (s, c)
723: char *s,
724: c;
725: {
726: char i,
727: *t;
728:
729: t = NULL;
730: while (i = *s++)
731: if (i == c)
732: t = s - 1;
733:
734: return t;
735: }
736:
737: /* */
738:
739: /* VARARGS */
740:
741: adios (what, fmt, a, b, c)
742: char *what,
743: *fmt,
744: *a,
745: *b,
746: *c;
747: {
748: (void) fflush (stdout);
749:
750: fprintf (stderr, "%s: ", myname);
751: fprintf (stderr, fmt, a, b, c);
752: if (what) {
753: (void) fputc (' ', stderr);
754: perror (what);
755: }
756: else
757: (void) fputc ('\n', stderr);
758:
759: exit (1);
760: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.