|
|
1.1 ! root 1: # include "sendmail.h" ! 2: ! 3: SCCSID(@(#)readcf.c 4.2 8/28/83); ! 4: ! 5: /* ! 6: ** READCF -- read control file. ! 7: ** ! 8: ** This routine reads the control file and builds the internal ! 9: ** form. ! 10: ** ! 11: ** The file is formatted as a sequence of lines, each taken ! 12: ** atomically. The first character of each line describes how ! 13: ** the line is to be interpreted. The lines are: ! 14: ** Dxval Define macro x to have value val. ! 15: ** Cxword Put word into class x. ! 16: ** Fxfile [fmt] Read file for lines to put into ! 17: ** class x. Use scanf string 'fmt' ! 18: ** or "%s" if not present. Fmt should ! 19: ** only produce one string-valued result. ! 20: ** Hname: value Define header with field-name 'name' ! 21: ** and value as specified; this will be ! 22: ** macro expanded immediately before ! 23: ** use. ! 24: ** Sn Use rewriting set n. ! 25: ** Rlhs rhs Rewrite addresses that match lhs to ! 26: ** be rhs. ! 27: ** Mn p f s r a Define mailer. n - internal name, ! 28: ** p - pathname, f - flags, s - rewriting ! 29: ** ruleset for sender, s - rewriting ruleset ! 30: ** for recipients, a - argument vector. ! 31: ** Oxvalue Set option x to value. ! 32: ** Pname=value Set precedence name to value. ! 33: ** ! 34: ** Parameters: ! 35: ** cfname -- control file name. ! 36: ** safe -- set if this is a system configuration file. ! 37: ** Non-system configuration files can not do ! 38: ** certain things (e.g., leave the SUID bit on ! 39: ** when executing mailers). ! 40: ** ! 41: ** Returns: ! 42: ** none. ! 43: ** ! 44: ** Side Effects: ! 45: ** Builds several internal tables. ! 46: */ ! 47: ! 48: readcf(cfname, safe) ! 49: char *cfname; ! 50: bool safe; ! 51: { ! 52: FILE *cf; ! 53: int ruleset = 0; ! 54: char *q; ! 55: char **pv; ! 56: struct rewrite *rwp = NULL; ! 57: char buf[MAXLINE]; ! 58: register char *p; ! 59: extern char **prescan(); ! 60: extern char **copyplist(); ! 61: char exbuf[MAXLINE]; ! 62: extern char *fgetfolded(); ! 63: extern char *munchstring(); ! 64: ! 65: cf = fopen(cfname, "r"); ! 66: if (cf == NULL) ! 67: { ! 68: syserr("cannot open %s", cfname); ! 69: exit(EX_OSFILE); ! 70: } ! 71: ! 72: FileName = cfname; ! 73: LineNumber = 0; ! 74: while (fgetfolded(buf, sizeof buf, cf) != NULL) ! 75: { ! 76: switch (buf[0]) ! 77: { ! 78: case '\0': ! 79: case '#': /* comment */ ! 80: break; ! 81: ! 82: case 'R': /* rewriting rule */ ! 83: for (p = &buf[1]; *p != '\0' && *p != '\t'; p++) ! 84: continue; ! 85: ! 86: if (*p == '\0') ! 87: { ! 88: syserr("invalid rewrite line \"%s\"", buf); ! 89: break; ! 90: } ! 91: ! 92: /* allocate space for the rule header */ ! 93: if (rwp == NULL) ! 94: { ! 95: RewriteRules[ruleset] = rwp = ! 96: (struct rewrite *) xalloc(sizeof *rwp); ! 97: } ! 98: else ! 99: { ! 100: rwp->r_next = (struct rewrite *) xalloc(sizeof *rwp); ! 101: rwp = rwp->r_next; ! 102: } ! 103: rwp->r_next = NULL; ! 104: ! 105: /* expand and save the LHS */ ! 106: *p = '\0'; ! 107: expand(&buf[1], exbuf, &exbuf[sizeof exbuf], CurEnv); ! 108: rwp->r_lhs = prescan(exbuf, '\t'); ! 109: if (rwp->r_lhs != NULL) ! 110: rwp->r_lhs = copyplist(rwp->r_lhs, TRUE); ! 111: ! 112: /* expand and save the RHS */ ! 113: while (*++p == '\t') ! 114: continue; ! 115: q = p; ! 116: while (*p != '\0' && *p != '\t') ! 117: p++; ! 118: *p = '\0'; ! 119: expand(q, exbuf, &exbuf[sizeof exbuf], CurEnv); ! 120: rwp->r_rhs = prescan(exbuf, '\t'); ! 121: if (rwp->r_rhs != NULL) ! 122: rwp->r_rhs = copyplist(rwp->r_rhs, TRUE); ! 123: break; ! 124: ! 125: case 'S': /* select rewriting set */ ! 126: ruleset = atoi(&buf[1]); ! 127: if (ruleset >= MAXRWSETS || ruleset < 0) ! 128: { ! 129: syserr("bad ruleset %d (%d max)", ruleset, MAXRWSETS); ! 130: ruleset = 0; ! 131: } ! 132: rwp = NULL; ! 133: break; ! 134: ! 135: case 'D': /* macro definition */ ! 136: define(buf[1], newstr(munchstring(&buf[2])), CurEnv); ! 137: break; ! 138: ! 139: case 'H': /* required header line */ ! 140: (void) chompheader(&buf[1], TRUE); ! 141: break; ! 142: ! 143: case 'C': /* word class */ ! 144: case 'F': /* word class from file */ ! 145: /* read list of words from argument or file */ ! 146: if (buf[0] == 'F') ! 147: { ! 148: /* read from file */ ! 149: for (p = &buf[2]; *p != '\0' && !isspace(*p); p++) ! 150: continue; ! 151: if (*p == '\0') ! 152: p = "%s"; ! 153: else ! 154: { ! 155: *p = '\0'; ! 156: while (isspace(*++p)) ! 157: continue; ! 158: } ! 159: fileclass(buf[1], &buf[2], p); ! 160: break; ! 161: } ! 162: ! 163: /* scan the list of words and set class for all */ ! 164: for (p = &buf[2]; *p != '\0'; ) ! 165: { ! 166: register char *wd; ! 167: char delim; ! 168: ! 169: while (*p != '\0' && isspace(*p)) ! 170: p++; ! 171: wd = p; ! 172: while (*p != '\0' && !isspace(*p)) ! 173: p++; ! 174: delim = *p; ! 175: *p = '\0'; ! 176: if (wd[0] != '\0') ! 177: setclass(buf[1], wd); ! 178: *p = delim; ! 179: } ! 180: break; ! 181: ! 182: case 'M': /* define mailer */ ! 183: makemailer(&buf[1], safe); ! 184: break; ! 185: ! 186: case 'O': /* set option */ ! 187: setoption(buf[1], &buf[2], safe, FALSE); ! 188: break; ! 189: ! 190: case 'P': /* set precedence */ ! 191: if (NumPriorities >= MAXPRIORITIES) ! 192: { ! 193: toomany('P', MAXPRIORITIES); ! 194: break; ! 195: } ! 196: for (p = &buf[1]; *p != '\0' && *p != '=' && *p != '\t'; p++) ! 197: continue; ! 198: if (*p == '\0') ! 199: goto badline; ! 200: *p = '\0'; ! 201: Priorities[NumPriorities].pri_name = newstr(&buf[1]); ! 202: Priorities[NumPriorities].pri_val = atoi(++p); ! 203: NumPriorities++; ! 204: break; ! 205: ! 206: case 'T': /* trusted user(s) */ ! 207: p = &buf[1]; ! 208: while (*p != '\0') ! 209: { ! 210: while (isspace(*p)) ! 211: p++; ! 212: q = p; ! 213: while (*p != '\0' && !isspace(*p)) ! 214: p++; ! 215: if (*p != '\0') ! 216: *p++ = '\0'; ! 217: if (*q == '\0') ! 218: continue; ! 219: for (pv = TrustedUsers; *pv != NULL; pv++) ! 220: continue; ! 221: if (pv >= &TrustedUsers[MAXTRUST]) ! 222: { ! 223: toomany('T', MAXTRUST); ! 224: break; ! 225: } ! 226: *pv = newstr(q); ! 227: } ! 228: break; ! 229: ! 230: default: ! 231: badline: ! 232: syserr("unknown control line \"%s\"", buf); ! 233: } ! 234: } ! 235: FileName = NULL; ! 236: } ! 237: /* ! 238: ** TOOMANY -- signal too many of some option ! 239: ** ! 240: ** Parameters: ! 241: ** id -- the id of the error line ! 242: ** maxcnt -- the maximum possible values ! 243: ** ! 244: ** Returns: ! 245: ** none. ! 246: ** ! 247: ** Side Effects: ! 248: ** gives a syserr. ! 249: */ ! 250: ! 251: toomany(id, maxcnt) ! 252: char id; ! 253: int maxcnt; ! 254: { ! 255: syserr("too many %c lines, %d max", id, maxcnt); ! 256: } ! 257: /* ! 258: ** FILECLASS -- read members of a class from a file ! 259: ** ! 260: ** Parameters: ! 261: ** class -- class to define. ! 262: ** filename -- name of file to read. ! 263: ** fmt -- scanf string to use for match. ! 264: ** ! 265: ** Returns: ! 266: ** none ! 267: ** ! 268: ** Side Effects: ! 269: ** ! 270: ** puts all lines in filename that match a scanf into ! 271: ** the named class. ! 272: */ ! 273: ! 274: fileclass(class, filename, fmt) ! 275: int class; ! 276: char *filename; ! 277: char *fmt; ! 278: { ! 279: register FILE *f; ! 280: char buf[MAXLINE]; ! 281: ! 282: f = fopen(filename, "r"); ! 283: if (f == NULL) ! 284: { ! 285: syserr("cannot open %s", filename); ! 286: return; ! 287: } ! 288: ! 289: while (fgets(buf, sizeof buf, f) != NULL) ! 290: { ! 291: register STAB *s; ! 292: char wordbuf[MAXNAME+1]; ! 293: ! 294: if (sscanf(buf, fmt, wordbuf) != 1) ! 295: continue; ! 296: s = stab(wordbuf, ST_CLASS, ST_ENTER); ! 297: setbitn(class, s->s_class); ! 298: } ! 299: ! 300: (void) fclose(f); ! 301: } ! 302: /* ! 303: ** MAKEMAILER -- define a new mailer. ! 304: ** ! 305: ** Parameters: ! 306: ** line -- description of mailer. This is in labeled ! 307: ** fields. The fields are: ! 308: ** P -- the path to the mailer ! 309: ** F -- the flags associated with the mailer ! 310: ** A -- the argv for this mailer ! 311: ** S -- the sender rewriting set ! 312: ** R -- the recipient rewriting set ! 313: ** E -- the eol string ! 314: ** The first word is the canonical name of the mailer. ! 315: ** safe -- set if this is a safe configuration file. ! 316: ** ! 317: ** Returns: ! 318: ** none. ! 319: ** ! 320: ** Side Effects: ! 321: ** enters the mailer into the mailer table. ! 322: */ ! 323: ! 324: makemailer(line, safe) ! 325: char *line; ! 326: bool safe; ! 327: { ! 328: register char *p; ! 329: register struct mailer *m; ! 330: register STAB *s; ! 331: int i; ! 332: char fcode; ! 333: extern int NextMailer; ! 334: extern char **makeargv(); ! 335: extern char *munchstring(); ! 336: extern char *DelimChar; ! 337: extern long atol(); ! 338: ! 339: /* allocate a mailer and set up defaults */ ! 340: m = (struct mailer *) xalloc(sizeof *m); ! 341: bzero((char *) m, sizeof *m); ! 342: m->m_mno = NextMailer; ! 343: m->m_eol = "\n"; ! 344: ! 345: /* collect the mailer name */ ! 346: for (p = line; *p != '\0' && *p != ',' && !isspace(*p); p++) ! 347: continue; ! 348: if (*p != '\0') ! 349: *p++ = '\0'; ! 350: m->m_name = newstr(line); ! 351: ! 352: /* now scan through and assign info from the fields */ ! 353: while (*p != '\0') ! 354: { ! 355: while (*p != '\0' && (*p == ',' || isspace(*p))) ! 356: p++; ! 357: ! 358: /* p now points to field code */ ! 359: fcode = *p; ! 360: while (*p != '\0' && *p != '=' && *p != ',') ! 361: p++; ! 362: if (*p++ != '=') ! 363: { ! 364: syserr("`=' expected"); ! 365: return; ! 366: } ! 367: while (isspace(*p)) ! 368: p++; ! 369: ! 370: /* p now points to the field body */ ! 371: p = munchstring(p); ! 372: ! 373: /* install the field into the mailer struct */ ! 374: switch (fcode) ! 375: { ! 376: case 'P': /* pathname */ ! 377: m->m_mailer = newstr(p); ! 378: break; ! 379: ! 380: case 'F': /* flags */ ! 381: for (; *p != '\0'; p++) ! 382: setbitn(*p, m->m_flags); ! 383: if (!safe) ! 384: clrbitn(M_RESTR, m->m_flags); ! 385: break; ! 386: ! 387: case 'S': /* sender rewriting ruleset */ ! 388: case 'R': /* recipient rewriting ruleset */ ! 389: i = atoi(p); ! 390: if (i < 0 || i >= MAXRWSETS) ! 391: { ! 392: syserr("invalid rewrite set, %d max", MAXRWSETS); ! 393: return; ! 394: } ! 395: if (fcode == 'S') ! 396: m->m_s_rwset = i; ! 397: else ! 398: m->m_r_rwset = i; ! 399: break; ! 400: ! 401: case 'E': /* end of line string */ ! 402: m->m_eol = newstr(p); ! 403: break; ! 404: ! 405: case 'A': /* argument vector */ ! 406: m->m_argv = makeargv(p); ! 407: break; ! 408: ! 409: case 'M': /* maximum message size */ ! 410: m->m_maxsize = atol(p); ! 411: break; ! 412: } ! 413: ! 414: p = DelimChar; ! 415: } ! 416: ! 417: /* now store the mailer away */ ! 418: if (NextMailer >= MAXMAILERS) ! 419: { ! 420: syserr("too many mailers defined (%d max)", MAXMAILERS); ! 421: return; ! 422: } ! 423: Mailer[NextMailer++] = m; ! 424: s = stab(m->m_name, ST_MAILER, ST_ENTER); ! 425: s->s_mailer = m; ! 426: } ! 427: /* ! 428: ** MUNCHSTRING -- translate a string into internal form. ! 429: ** ! 430: ** Parameters: ! 431: ** p -- the string to munch. ! 432: ** ! 433: ** Returns: ! 434: ** the munched string. ! 435: ** ! 436: ** Side Effects: ! 437: ** Sets "DelimChar" to point to the string that caused us ! 438: ** to stop. ! 439: */ ! 440: ! 441: char * ! 442: munchstring(p) ! 443: register char *p; ! 444: { ! 445: register char *q; ! 446: bool backslash = FALSE; ! 447: bool quotemode = FALSE; ! 448: static char buf[MAXLINE]; ! 449: extern char *DelimChar; ! 450: ! 451: for (q = buf; *p != '\0'; p++) ! 452: { ! 453: if (backslash) ! 454: { ! 455: /* everything is roughly literal */ ! 456: backslash = FALSE; ! 457: switch (*p) ! 458: { ! 459: case 'r': /* carriage return */ ! 460: *q++ = '\r'; ! 461: continue; ! 462: ! 463: case 'n': /* newline */ ! 464: *q++ = '\n'; ! 465: continue; ! 466: ! 467: case 'f': /* form feed */ ! 468: *q++ = '\f'; ! 469: continue; ! 470: ! 471: case 'b': /* backspace */ ! 472: *q++ = '\b'; ! 473: continue; ! 474: } ! 475: *q++ = *p; ! 476: } ! 477: else ! 478: { ! 479: if (*p == '\\') ! 480: backslash = TRUE; ! 481: else if (*p == '"') ! 482: quotemode = !quotemode; ! 483: else if (quotemode || *p != ',') ! 484: *q++ = *p; ! 485: else ! 486: break; ! 487: } ! 488: } ! 489: ! 490: DelimChar = p; ! 491: *q++ = '\0'; ! 492: return (buf); ! 493: } ! 494: /* ! 495: ** MAKEARGV -- break up a string into words ! 496: ** ! 497: ** Parameters: ! 498: ** p -- the string to break up. ! 499: ** ! 500: ** Returns: ! 501: ** a char **argv (dynamically allocated) ! 502: ** ! 503: ** Side Effects: ! 504: ** munges p. ! 505: */ ! 506: ! 507: char ** ! 508: makeargv(p) ! 509: register char *p; ! 510: { ! 511: char *q; ! 512: int i; ! 513: char **avp; ! 514: char *argv[MAXPV + 1]; ! 515: ! 516: /* take apart the words */ ! 517: i = 0; ! 518: while (*p != '\0' && i < MAXPV) ! 519: { ! 520: q = p; ! 521: while (*p != '\0' && !isspace(*p)) ! 522: p++; ! 523: while (isspace(*p)) ! 524: *p++ = '\0'; ! 525: argv[i++] = newstr(q); ! 526: } ! 527: argv[i++] = NULL; ! 528: ! 529: /* now make a copy of the argv */ ! 530: avp = (char **) xalloc(sizeof *avp * i); ! 531: bmove((char *) argv, (char *) avp, sizeof *avp * i); ! 532: ! 533: return (avp); ! 534: } ! 535: /* ! 536: ** PRINTRULES -- print rewrite rules (for debugging) ! 537: ** ! 538: ** Parameters: ! 539: ** none. ! 540: ** ! 541: ** Returns: ! 542: ** none. ! 543: ** ! 544: ** Side Effects: ! 545: ** prints rewrite rules. ! 546: */ ! 547: ! 548: # ifdef DEBUG ! 549: ! 550: printrules() ! 551: { ! 552: register struct rewrite *rwp; ! 553: register int ruleset; ! 554: ! 555: for (ruleset = 0; ruleset < 10; ruleset++) ! 556: { ! 557: if (RewriteRules[ruleset] == NULL) ! 558: continue; ! 559: printf("\n----Rule Set %d:", ruleset); ! 560: ! 561: for (rwp = RewriteRules[ruleset]; rwp != NULL; rwp = rwp->r_next) ! 562: { ! 563: printf("\nLHS:"); ! 564: printav(rwp->r_lhs); ! 565: printf("RHS:"); ! 566: printav(rwp->r_rhs); ! 567: } ! 568: } ! 569: } ! 570: ! 571: # endif DEBUG ! 572: /* ! 573: ** SETOPTION -- set global processing option ! 574: ** ! 575: ** Parameters: ! 576: ** opt -- option name. ! 577: ** val -- option value (as a text string). ! 578: ** safe -- if set, this came from a system configuration file. ! 579: ** sticky -- if set, don't let other setoptions override ! 580: ** this value. ! 581: ** ! 582: ** Returns: ! 583: ** none. ! 584: ** ! 585: ** Side Effects: ! 586: ** Sets options as implied by the arguments. ! 587: */ ! 588: ! 589: static BITMAP StickyOpt; /* set if option is stuck */ ! 590: extern char *WizWord; /* the stored wizard password */ ! 591: ! 592: setoption(opt, val, safe, sticky) ! 593: char opt; ! 594: char *val; ! 595: bool safe; ! 596: bool sticky; ! 597: { ! 598: extern bool atobool(); ! 599: extern time_t convtime(); ! 600: extern int QueueLA; ! 601: extern int RefuseLA; ! 602: ! 603: # ifdef DEBUG ! 604: if (tTd(37, 1)) ! 605: printf("setoption %c=%s", opt, val); ! 606: # endif DEBUG ! 607: ! 608: /* ! 609: ** See if this option is preset for us. ! 610: */ ! 611: ! 612: if (bitnset(opt, StickyOpt)) ! 613: { ! 614: # ifdef DEBUG ! 615: if (tTd(37, 1)) ! 616: printf(" (ignored)\n"); ! 617: # endif DEBUG ! 618: return; ! 619: } ! 620: #ifdef DEBUG ! 621: else if (tTd(37, 1)) ! 622: printf("\n"); ! 623: #endif DEBUG ! 624: if (sticky) ! 625: setbitn(opt, StickyOpt); ! 626: ! 627: if (getruid() == 0) ! 628: safe = TRUE; ! 629: ! 630: switch (opt) ! 631: { ! 632: case 'A': /* set default alias file */ ! 633: if (val[0] == '\0') ! 634: AliasFile = "aliases"; ! 635: else ! 636: AliasFile = newstr(val); ! 637: break; ! 638: ! 639: case 'a': /* look for "@:@" in alias file */ ! 640: SafeAlias = atobool(val); ! 641: break; ! 642: ! 643: case 'c': /* don't connect to "expensive" mailers */ ! 644: NoConnect = atobool(val); ! 645: break; ! 646: ! 647: case 'd': /* delivery mode */ ! 648: switch (*val) ! 649: { ! 650: case '\0': ! 651: SendMode = SM_DELIVER; ! 652: break; ! 653: ! 654: case SM_QUEUE: /* queue only */ ! 655: #ifndef QUEUE ! 656: syserr("need QUEUE to set -odqueue"); ! 657: #endif QUEUE ! 658: /* fall through..... */ ! 659: ! 660: case SM_DELIVER: /* do everything */ ! 661: case SM_FORK: /* fork after verification */ ! 662: SendMode = *val; ! 663: break; ! 664: ! 665: default: ! 666: syserr("Unknown delivery mode %c", *val); ! 667: exit(EX_USAGE); ! 668: } ! 669: break; ! 670: ! 671: case 'D': /* rebuild alias database as needed */ ! 672: AutoRebuild = atobool(val); ! 673: break; ! 674: ! 675: case 'e': /* set error processing mode */ ! 676: switch (*val) ! 677: { ! 678: case EM_QUIET: /* be silent about it */ ! 679: case EM_MAIL: /* mail back */ ! 680: case EM_BERKNET: /* do berknet error processing */ ! 681: case EM_WRITE: /* write back (or mail) */ ! 682: HoldErrs = TRUE; ! 683: /* fall through... */ ! 684: ! 685: case EM_PRINT: /* print errors normally (default) */ ! 686: ErrorMode = *val; ! 687: break; ! 688: } ! 689: break; ! 690: ! 691: case 'F': /* file mode */ ! 692: FileMode = atooct(val); ! 693: break; ! 694: ! 695: case 'f': /* save Unix-style From lines on front */ ! 696: SaveFrom = atobool(val); ! 697: break; ! 698: ! 699: case 'g': /* default gid */ ! 700: if (safe) ! 701: DefGid = atoi(val); ! 702: break; ! 703: ! 704: case 'H': /* help file */ ! 705: if (val[0] == '\0') ! 706: HelpFile = "sendmail.hf"; ! 707: else ! 708: HelpFile = newstr(val); ! 709: break; ! 710: ! 711: case 'i': /* ignore dot lines in message */ ! 712: IgnrDot = atobool(val); ! 713: break; ! 714: ! 715: case 'L': /* log level */ ! 716: LogLevel = atoi(val); ! 717: break; ! 718: ! 719: case 'M': /* define macro */ ! 720: define(val[0], newstr(&val[1]), CurEnv); ! 721: break; ! 722: ! 723: case 'm': /* send to me too */ ! 724: MeToo = atobool(val); ! 725: break; ! 726: ! 727: case 'o': /* assume old style headers */ ! 728: if (atobool(val)) ! 729: CurEnv->e_flags |= EF_OLDSTYLE; ! 730: else ! 731: CurEnv->e_flags &= ~EF_OLDSTYLE; ! 732: break; ! 733: ! 734: case 'Q': /* queue directory */ ! 735: if (val[0] == '\0') ! 736: QueueDir = "mqueue"; ! 737: else ! 738: QueueDir = newstr(val); ! 739: break; ! 740: ! 741: case 'r': /* read timeout */ ! 742: ReadTimeout = convtime(val); ! 743: break; ! 744: ! 745: case 'S': /* status file */ ! 746: if (val[0] == '\0') ! 747: StatFile = "sendmail.st"; ! 748: else ! 749: StatFile = newstr(val); ! 750: break; ! 751: ! 752: case 's': /* be super safe, even if expensive */ ! 753: SuperSafe = atobool(val); ! 754: break; ! 755: ! 756: case 'T': /* queue timeout */ ! 757: TimeOut = convtime(val); ! 758: break; ! 759: ! 760: case 't': /* time zone name */ ! 761: # ifdef V6 ! 762: StdTimezone = newstr(val); ! 763: DstTimezone = index(StdTimeZone, ','); ! 764: if (DstTimezone == NULL) ! 765: syserr("bad time zone spec"); ! 766: else ! 767: *DstTimezone++ = '\0'; ! 768: # endif V6 ! 769: break; ! 770: ! 771: case 'u': /* set default uid */ ! 772: if (safe) ! 773: DefUid = atoi(val); ! 774: break; ! 775: ! 776: case 'v': /* run in verbose mode */ ! 777: Verbose = atobool(val); ! 778: break; ! 779: ! 780: # ifdef DEBUG ! 781: case 'W': /* set the wizards password */ ! 782: if (safe) ! 783: WizWord = newstr(val); ! 784: break; ! 785: # endif DEBUG ! 786: ! 787: case 'x': /* load avg at which to auto-queue msgs */ ! 788: QueueLA = atoi(val); ! 789: break; ! 790: ! 791: case 'X': /* load avg at which to auto-reject connections */ ! 792: RefuseLA = atoi(val); ! 793: break; ! 794: ! 795: default: ! 796: break; ! 797: } ! 798: return; ! 799: } ! 800: /* ! 801: ** SETCLASS -- set a word into a class ! 802: ** ! 803: ** Parameters: ! 804: ** class -- the class to put the word in. ! 805: ** word -- the word to enter ! 806: ** ! 807: ** Returns: ! 808: ** none. ! 809: ** ! 810: ** Side Effects: ! 811: ** puts the word into the symbol table. ! 812: */ ! 813: ! 814: setclass(class, word) ! 815: int class; ! 816: char *word; ! 817: { ! 818: register STAB *s; ! 819: ! 820: s = stab(word, ST_CLASS, ST_ENTER); ! 821: setbitn(class, s->s_class); ! 822: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.