Annotation of 43BSDTahoe/usr.lib/sendmail/aux/mail.c, revision 1.1.1.1

1.1       root        1: #ifndef lint
                      2: static char sccsid[] = "@(#)mail.c     4.33 (Berkeley) 2/27/88";
                      3: #endif
                      4: 
                      5: #include <sys/param.h>
                      6: #include <sys/stat.h>
                      7: #include <sys/file.h>
                      8: 
                      9: #include <ctype.h>
                     10: #include <stdio.h>
                     11: #include <pwd.h>
                     12: #include <utmp.h>
                     13: #include <signal.h>
                     14: #include <setjmp.h>
                     15: #include <sysexits.h>
                     16: 
                     17: #define SENDMAIL       "/usr/lib/sendmail"
                     18: 
                     19:        /* copylet flags */
                     20: #define REMOTE         1               /* remote mail, add rmtmsg */
                     21: #define ORDINARY       2
                     22: #define ZAP            3               /* zap header and trailing empty line */
                     23: #define        FORWARD         4
                     24: 
                     25: #define        LSIZE           256
                     26: #define        MAXLET          300             /* maximum number of letters */
                     27: #define        MAILMODE        0600            /* mode of created mail */
                     28: 
                     29: char   line[LSIZE];
                     30: char   resp[LSIZE];
                     31: struct let {
                     32:        long    adr;
                     33:        char    change;
                     34: } let[MAXLET];
                     35: int    nlet    = 0;
                     36: char   lfil[50];
                     37: long   iop, time();
                     38: char   *getenv();
                     39: char   *index();
                     40: char   lettmp[] = "/tmp/maXXXXX";
                     41: char   maildir[] = "/usr/spool/mail/";
                     42: char   mailfile[] = "/usr/spool/mail/xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx";
                     43: char   dead[] = "dead.letter";
                     44: char   forwmsg[] = " forwarded\n";
                     45: FILE   *tmpf;
                     46: FILE   *malf;
                     47: char   my_name[60];
                     48: char   *getlogin();
                     49: int    error;
                     50: int    changed;
                     51: int    forward;
                     52: char   from[] = "From ";
                     53: long   ftell();
                     54: int    delex();
                     55: char   *ctime();
                     56: int    flgf;
                     57: int    flgp;
                     58: int    delflg = 1;
                     59: int    hseqno;
                     60: jmp_buf        sjbuf;
                     61: int    rmail;
                     62: 
                     63: main(argc, argv)
                     64: char **argv;
                     65: {
                     66:        register int i;
                     67:        char *name;
                     68:        struct passwd *pwent;
                     69: 
                     70:        if (!(name = getlogin()) || !*name || !(pwent = getpwnam(name)) ||
                     71:            getuid() != pwent->pw_uid) 
                     72:                pwent = getpwuid(getuid());
                     73:        strncpy(my_name, pwent ? pwent->pw_name : "???", sizeof(my_name)-1);
                     74:        if (setjmp(sjbuf))
                     75:                done();
                     76:        for (i=SIGHUP; i<=SIGTERM; i++)
                     77:                setsig(i, delex);
                     78:        i = mkstemp(lettmp);
                     79:        tmpf = fdopen(i, "r+w");
                     80:        if (i < 0 || tmpf == NULL)
                     81:                panic("mail: %s: cannot open for writing", lettmp);
                     82:        /*
                     83:         * This protects against others reading mail from temp file and
                     84:         * if we exit, the file will be deleted already.
                     85:         */
                     86:        unlink(lettmp);
                     87:        if (argv[0][0] == 'r')
                     88:                rmail++;
                     89:        if (argv[0][0] != 'r' &&        /* no favors for rmail*/
                     90:           (argc == 1 || argv[1][0] == '-' && !any(argv[1][1], "rhd")))
                     91:                printmail(argc, argv);
                     92:        else
                     93:                bulkmail(argc, argv);
                     94:        done();
                     95: }
                     96: 
                     97: setsig(i, f)
                     98: int i;
                     99: int (*f)();
                    100: {
                    101:        if (signal(i, SIG_IGN) != SIG_IGN)
                    102:                signal(i, f);
                    103: }
                    104: 
                    105: any(c, str)
                    106:        register int c;
                    107:        register char *str;
                    108: {
                    109: 
                    110:        while (*str)
                    111:                if (c == *str++)
                    112:                        return(1);
                    113:        return(0);
                    114: }
                    115: 
                    116: printmail(argc, argv)
                    117:        char **argv;
                    118: {
                    119:        int flg, i, j, print;
                    120:        char *p, *getarg();
                    121:        struct stat statb;
                    122: 
                    123:        setuid(getuid());
                    124:        cat(mailfile, maildir, my_name);
                    125: #ifdef notdef
                    126:        if (stat(mailfile, &statb) >= 0
                    127:            && (statb.st_mode & S_IFMT) == S_IFDIR) {
                    128:                strcat(mailfile, "/");
                    129:                strcat(mailfile, my_name);
                    130:        }
                    131: #endif
                    132:        for (; argc > 1; argv++, argc--) {
                    133:                if (argv[1][0] != '-')
                    134:                        break;
                    135:                switch (argv[1][1]) {
                    136: 
                    137:                case 'p':
                    138:                        flgp++;
                    139:                        /* fall thru... */
                    140:                case 'q':
                    141:                        delflg = 0;
                    142:                        break;
                    143: 
                    144:                case 'f':
                    145:                        if (argc >= 3) {
                    146:                                strcpy(mailfile, argv[2]);
                    147:                                argv++, argc--;
                    148:                        }
                    149:                        break;
                    150: 
                    151:                case 'b':
                    152:                        forward = 1;
                    153:                        break;
                    154: 
                    155:                default:
                    156:                        panic("unknown option %c", argv[1][1]);
                    157:                        /*NOTREACHED*/
                    158:                }
                    159:        }
                    160:        malf = fopen(mailfile, "r");
                    161:        if (malf == NULL) {
                    162:                printf("No mail.\n");
                    163:                return;
                    164:        }
                    165:        flock(fileno(malf), LOCK_SH);
                    166:        copymt(malf, tmpf);
                    167:        fclose(malf);                   /* implicit unlock */
                    168:        fseek(tmpf, 0L, L_SET);
                    169: 
                    170:        changed = 0;
                    171:        print = 1;
                    172:        for (i = 0; i < nlet; ) {
                    173:                j = forward ? i : nlet - i - 1;
                    174:                if (setjmp(sjbuf)) {
                    175:                        print = 0;
                    176:                } else {
                    177:                        if (print)
                    178:                                copylet(j, stdout, ORDINARY);
                    179:                        print = 1;
                    180:                }
                    181:                if (flgp) {
                    182:                        i++;
                    183:                        continue;
                    184:                }
                    185:                setjmp(sjbuf);
                    186:                fputs("? ", stdout);
                    187:                fflush(stdout);
                    188:                if (fgets(resp, LSIZE, stdin) == NULL)
                    189:                        break;
                    190:                switch (resp[0]) {
                    191: 
                    192:                default:
                    193:                        printf("usage\n");
                    194:                case '?':
                    195:                        print = 0;
                    196:                        printf("q\tquit\n");
                    197:                        printf("x\texit without changing mail\n");
                    198:                        printf("p\tprint\n");
                    199:                        printf("s[file]\tsave (default mbox)\n");
                    200:                        printf("w[file]\tsame without header\n");
                    201:                        printf("-\tprint previous\n");
                    202:                        printf("d\tdelete\n");
                    203:                        printf("+\tnext (no delete)\n");
                    204:                        printf("m user\tmail to user\n");
                    205:                        printf("! cmd\texecute cmd\n");
                    206:                        break;
                    207: 
                    208:                case '+':
                    209:                case 'n':
                    210:                case '\n':
                    211:                        i++;
                    212:                        break;
                    213:                case 'x':
                    214:                        changed = 0;
                    215:                case 'q':
                    216:                        goto donep;
                    217:                case 'p':
                    218:                        break;
                    219:                case '^':
                    220:                case '-':
                    221:                        if (--i < 0)
                    222:                                i = 0;
                    223:                        break;
                    224:                case 'y':
                    225:                case 'w':
                    226:                case 's':
                    227:                        flg = 0;
                    228:                        if (resp[1] != '\n' && resp[1] != ' ') {
                    229:                                printf("illegal\n");
                    230:                                flg++;
                    231:                                print = 0;
                    232:                                continue;
                    233:                        }
                    234:                        if (resp[1] == '\n' || resp[1] == '\0') {
                    235:                                p = getenv("HOME");
                    236:                                if (p != 0)
                    237:                                        cat(resp+1, p, "/mbox");
                    238:                                else
                    239:                                        cat(resp+1, "", "mbox");
                    240:                        }
                    241:                        for (p = resp+1; (p = getarg(lfil, p)) != NULL; ) {
                    242:                                malf = fopen(lfil, "a");
                    243:                                if (malf == NULL) {
                    244:                                        printf("mail: %s: cannot append\n",
                    245:                                            lfil);
                    246:                                        flg++;
                    247:                                        continue;
                    248:                                }
                    249:                                copylet(j, malf, resp[0]=='w'? ZAP: ORDINARY);
                    250:                                fclose(malf);
                    251:                        }
                    252:                        if (flg)
                    253:                                print = 0;
                    254:                        else {
                    255:                                let[j].change = 'd';
                    256:                                changed++;
                    257:                                i++;
                    258:                        }
                    259:                        break;
                    260:                case 'm':
                    261:                        flg = 0;
                    262:                        if (resp[1] == '\n' || resp[1] == '\0') {
                    263:                                i++;
                    264:                                continue;
                    265:                        }
                    266:                        if (resp[1] != ' ') {
                    267:                                printf("invalid command\n");
                    268:                                flg++;
                    269:                                print = 0;
                    270:                                continue;
                    271:                        }
                    272:                        for (p = resp+1; (p = getarg(lfil, p)) != NULL; )
                    273:                                if (!sendmail(j, lfil, my_name))
                    274:                                        flg++;
                    275:                        if (flg)
                    276:                                print = 0;
                    277:                        else {
                    278:                                let[j].change = 'd';
                    279:                                changed++;
                    280:                                i++;
                    281:                        }
                    282:                        break;
                    283:                case '!':
                    284:                        system(resp+1);
                    285:                        printf("!\n");
                    286:                        print = 0;
                    287:                        break;
                    288:                case 'd':
                    289:                        let[j].change = 'd';
                    290:                        changed++;
                    291:                        i++;
                    292:                        if (resp[1] == 'q')
                    293:                                goto donep;
                    294:                        break;
                    295:                }
                    296:        }
                    297:    donep:
                    298:        if (changed)
                    299:                copyback();
                    300: }
                    301: 
                    302: /* copy temp or whatever back to /usr/spool/mail */
                    303: copyback()
                    304: {
                    305:        register int i, c;
                    306:        long oldmask;
                    307:        int fd, new = 0;
                    308:        struct stat stbuf;
                    309: 
                    310:        oldmask = sigblock(sigmask(SIGINT)|sigmask(SIGHUP)|sigmask(SIGQUIT));
                    311:        fd = open(mailfile, O_RDWR | O_CREAT, MAILMODE);
                    312:        if (fd >= 0) {
                    313:                flock(fd, LOCK_EX);
                    314:                malf = fdopen(fd, "r+w");
                    315:        }
                    316:        if (fd < 0 || malf == NULL)
                    317:                panic("can't rewrite %s", lfil);
                    318:        fstat(fd, &stbuf);
                    319:        if (stbuf.st_size != let[nlet].adr) {   /* new mail has arrived */
                    320:                fseek(malf, let[nlet].adr, L_SET);
                    321:                fseek(tmpf, let[nlet].adr, L_SET);
                    322:                while ((c = getc(malf)) != EOF)
                    323:                        putc(c, tmpf);
                    324:                let[++nlet].adr = stbuf.st_size;
                    325:                new = 1;
                    326:                fseek(malf, 0L, L_SET);
                    327:        }
                    328:        ftruncate(fd, 0L);
                    329:        for (i = 0; i < nlet; i++)
                    330:                if (let[i].change != 'd')
                    331:                        copylet(i, malf, ORDINARY);
                    332:        fclose(malf);           /* implict unlock */
                    333:        if (new)
                    334:                printf("New mail has arrived.\n");
                    335:        sigsetmask(oldmask);
                    336: }
                    337: 
                    338: /* copy mail (f1) to temp (f2) */
                    339: copymt(f1, f2)
                    340:        FILE *f1, *f2;
                    341: {
                    342:        long nextadr;
                    343: 
                    344:        nlet = nextadr = 0;
                    345:        let[0].adr = 0;
                    346:        while (fgets(line, LSIZE, f1) != NULL) {
                    347:                if (isfrom(line))
                    348:                        let[nlet++].adr = nextadr;
                    349:                nextadr += strlen(line);
                    350:                fputs(line, f2);
                    351:        }
                    352:        let[nlet].adr = nextadr;        /* last plus 1 */
                    353: }
                    354: 
                    355: copylet(n, f, type)
                    356:        FILE *f;
                    357: {
                    358:        int ch;
                    359:        long k;
                    360:        char hostname[MAXHOSTNAMELEN];
                    361: 
                    362:        fseek(tmpf, let[n].adr, L_SET);
                    363:        k = let[n+1].adr - let[n].adr;
                    364:        while (k-- > 1 && (ch = getc(tmpf)) != '\n')
                    365:                if (type != ZAP)
                    366:                        putc(ch, f);
                    367:        switch (type) {
                    368: 
                    369:        case REMOTE:
                    370:                gethostname(hostname, sizeof (hostname));
                    371:                fprintf(f, " remote from %s\n", hostname);
                    372:                break;
                    373: 
                    374:        case FORWARD:
                    375:                fprintf(f, forwmsg);
                    376:                break;
                    377: 
                    378:        case ORDINARY:
                    379:                putc(ch, f);
                    380:                break;
                    381: 
                    382:        case ZAP:
                    383:                break;
                    384: 
                    385:        default:
                    386:                panic("Bad letter type %d to copylet.", type);
                    387:        }
                    388:        while (k-- > 1) {
                    389:                ch = getc(tmpf);
                    390:                putc(ch, f);
                    391:        }
                    392:        if (type != ZAP || ch != '\n')
                    393:                putc(getc(tmpf), f);
                    394: }
                    395: 
                    396: isfrom(lp)
                    397: register char *lp;
                    398: {
                    399:        register char *p;
                    400: 
                    401:        for (p = from; *p; )
                    402:                if (*lp++ != *p++)
                    403:                        return(0);
                    404:        return(1);
                    405: }
                    406: 
                    407: bulkmail(argc, argv)
                    408: char **argv;
                    409: {
                    410:        char *truename;
                    411:        int first;
                    412:        register char *cp;
                    413:        char *newargv[1000];
                    414:        register char **ap;
                    415:        register char **vp;
                    416:        int dflag;
                    417: 
                    418:        dflag = 0;
                    419:        delflg = 0;
                    420:        if (argc < 1) {
                    421:                fprintf(stderr, "puke\n");
                    422:                return;
                    423:        }
                    424:        for (vp = argv, ap = newargv + 1; (*ap = *vp++) != 0; ap++)
                    425:                if (ap[0][0] == '-' && ap[0][1] == 'd')
                    426:                        dflag++;
                    427:        if (!dflag) {
                    428:                /* give it to sendmail, rah rah! */
                    429:                unlink(lettmp);
                    430:                ap = newargv+1;
                    431:                if (rmail)
                    432:                        *ap-- = "-s";
                    433:                *ap = "-sendmail";
                    434:                setuid(getuid());
                    435:                execv(SENDMAIL, ap);
                    436:                perror(SENDMAIL);
                    437:                exit(EX_UNAVAILABLE);
                    438:        }
                    439: 
                    440:        truename = 0;
                    441:        line[0] = '\0';
                    442: 
                    443:        /*
                    444:         * When we fall out of this, argv[1] should be first name,
                    445:         * argc should be number of names + 1.
                    446:         */
                    447: 
                    448:        while (argc > 1 && *argv[1] == '-') {
                    449:                cp = *++argv;
                    450:                argc--;
                    451:                switch (cp[1]) {
                    452:                case 'r':
                    453:                        if (argc <= 1)
                    454:                                usage();
                    455:                        truename = argv[1];
                    456:                        fgets(line, LSIZE, stdin);
                    457:                        if (strcmpn("From", line, 4) == 0)
                    458:                                line[0] = '\0';
                    459:                        argv++;
                    460:                        argc--;
                    461:                        break;
                    462: 
                    463:                case 'h':
                    464:                        if (argc <= 1)
                    465:                                usage();
                    466:                        hseqno = atoi(argv[1]);
                    467:                        argv++;
                    468:                        argc--;
                    469:                        break;
                    470: 
                    471:                case 'd':
                    472:                        break;
                    473:                
                    474:                default:
                    475:                        usage();
                    476:                }
                    477:        }
                    478:        if (argc <= 1)
                    479:                usage();
                    480:        if (truename == 0)
                    481:                truename = my_name;
                    482:        time(&iop);
                    483:        fprintf(tmpf, "%s%s %s", from, truename, ctime(&iop));
                    484:        iop = ftell(tmpf);
                    485:        flgf = first = 1;
                    486:        for (;;) {
                    487:                if (first) {
                    488:                        first = 0;
                    489:                        if (*line == '\0' && fgets(line, LSIZE, stdin) == NULL)
                    490:                                break;
                    491:                } else {
                    492:                        if (fgets(line, LSIZE, stdin) == NULL)
                    493:                                break;
                    494:                }
                    495:                if (*line == '.' && line[1] == '\n' && isatty(fileno(stdin)))
                    496:                        break;
                    497:                if (isfrom(line))
                    498:                        putc('>', tmpf);
                    499:                fputs(line, tmpf);
                    500:                flgf = 0;
                    501:        }
                    502:        putc('\n', tmpf);
                    503:        nlet = 1;
                    504:        let[0].adr = 0;
                    505:        let[1].adr = ftell(tmpf);
                    506:        if (flgf)
                    507:                return;
                    508:        while (--argc > 0)
                    509:                if (!sendmail(0, *++argv, truename))
                    510:                        error++;
                    511:        if (error && safefile(dead)) {
                    512:                setuid(getuid());
                    513:                malf = fopen(dead, "w");
                    514:                if (malf == NULL) {
                    515:                        printf("mail: cannot open %s\n", dead);
                    516:                        fclose(tmpf);
                    517:                        return;
                    518:                }
                    519:                copylet(0, malf, ZAP);
                    520:                fclose(malf);
                    521:                printf("Mail saved in %s\n", dead);
                    522:        }
                    523:        fclose(tmpf);
                    524: }
                    525: 
                    526: sendrmt(n, name)
                    527: char *name;
                    528: {
                    529:        FILE *rmf, *popen();
                    530:        register char *p;
                    531:        char rsys[64], cmd[64];
                    532:        register pid;
                    533:        int sts;
                    534: 
                    535: #ifdef notdef
                    536:        if (any('^', name)) {
                    537:                while (p = index(name, '^'))
                    538:                        *p = '!';
                    539:                if (strncmp(name, "researc", 7)) {
                    540:                        strcpy(rsys, "research");
                    541:                        if (*name != '!')
                    542:                                --name;
                    543:                        goto skip;
                    544:                }
                    545:        }
                    546: #endif
                    547:        for (p=rsys; *name!='!'; *p++ = *name++)
                    548:                if (*name=='\0')
                    549:                        return(0);      /* local address, no '!' */
                    550:        *p = '\0';
                    551:        if (name[1]=='\0') {
                    552:                printf("null name\n");
                    553:                return(0);
                    554:        }
                    555: skip:
                    556:        if ((pid = fork()) == -1) {
                    557:                fprintf(stderr, "mail: can't create proc for remote\n");
                    558:                return(0);
                    559:        }
                    560:        if (pid) {
                    561:                while (wait(&sts) != pid) {
                    562:                        if (wait(&sts)==-1)
                    563:                                return(0);
                    564:                }
                    565:                return(!sts);
                    566:        }
                    567:        setuid(getuid());
                    568:        if (any('!', name+1))
                    569:                (void)sprintf(cmd, "uux - %s!rmail \\(%s\\)", rsys, name+1);
                    570:        else
                    571:                (void)sprintf(cmd, "uux - %s!rmail %s", rsys, name+1);
                    572:        if ((rmf=popen(cmd, "w")) == NULL)
                    573:                exit(1);
                    574:        copylet(n, rmf, REMOTE);
                    575:        exit(pclose(rmf) != 0);
                    576: }
                    577: 
                    578: usage()
                    579: {
                    580: 
                    581:        fprintf(stderr, "Usage: mail [ -f ] people . . .\n");
                    582:        error = EX_USAGE;
                    583:        done();
                    584: }
                    585: 
                    586: #include <sys/socket.h>
                    587: #include <netinet/in.h>
                    588: #include <netdb.h>
                    589: 
                    590: notifybiff(msg)
                    591:        char *msg;
                    592: {
                    593:        static struct sockaddr_in addr;
                    594:        static int f = -1;
                    595: 
                    596:        if (addr.sin_family == 0) {
                    597:                struct hostent *hp = gethostbyname("localhost");
                    598:                struct servent *sp = getservbyname("biff", "udp");
                    599: 
                    600:                if (hp && sp) {
                    601:                        addr.sin_family = hp->h_addrtype;
                    602:                        bcopy(hp->h_addr, &addr.sin_addr, hp->h_length);
                    603:                        addr.sin_port = sp->s_port;
                    604:                }
                    605:        }
                    606:        if (addr.sin_family) {
                    607:                if (f < 0)
                    608:                        f = socket(AF_INET, SOCK_DGRAM, 0);
                    609:                if (f >= 0)
                    610:                        sendto(f, msg, strlen(msg)+1, 0, &addr, sizeof (addr));
                    611:        }
                    612: }
                    613: 
                    614: sendmail(n, name, fromaddr)
                    615:        int n;
                    616:        char *name, *fromaddr;
                    617: {
                    618:        char file[256];
                    619:        int mask, fd;
                    620:        struct passwd *pw;
                    621: #ifdef notdef
                    622:        struct stat statb;
                    623: #endif
                    624:        char buf[128];
                    625: 
                    626:        if (*name=='!')
                    627:                name++;
                    628:        if (any('!', name))
                    629:                return (sendrmt(n, name));
                    630:        if ((pw = getpwnam(name)) == NULL) {
                    631:                printf("mail: can't send to %s\n", name);
                    632:                return(0);
                    633:        }
                    634:        cat(file, maildir, name);
                    635: #ifdef notdef
                    636:        if (stat(file, &statb) >= 0 && (statb.st_mode & S_IFMT) == S_IFDIR) {
                    637:                strcat(file, "/");
                    638:                strcat(file, name);
                    639:        }
                    640: #endif
                    641:        if (!safefile(file))
                    642:                return(0);
                    643:        fd = open(file, O_WRONLY | O_CREAT, MAILMODE);
                    644:        if (fd >= 0) {
                    645:                flock(fd, LOCK_EX);
                    646:                malf = fdopen(fd, "a");
                    647:        }
                    648:        if (fd < 0 || malf == NULL) {
                    649:                close(fd);
                    650:                printf("mail: %s: cannot append\n", file);
                    651:                return(0);
                    652:        }
                    653:        fchown(fd, pw->pw_uid, pw->pw_gid);
                    654:        (void)sprintf(buf, "%s@%ld\n", name, ftell(malf));
                    655:        copylet(n, malf, ORDINARY);
                    656:        fclose(malf);
                    657:        notifybiff(buf);
                    658:        return(1);
                    659: }
                    660: 
                    661: delex(i)
                    662: {
                    663:        if (i != SIGINT) {
                    664:                setsig(i, SIG_DFL);
                    665:                sigsetmask(sigblock(0L) &~ sigmask(i));
                    666:        }
                    667:        putc('\n', stderr);
                    668:        if (delflg)
                    669:                longjmp(sjbuf, 1);
                    670:        if (error == 0)
                    671:                error = i;
                    672:        done();
                    673: }
                    674: 
                    675: done()
                    676: {
                    677: 
                    678:        unlink(lettmp);
                    679:        exit(error);
                    680: }
                    681: 
                    682: cat(to, from1, from2)
                    683:        char *to, *from1, *from2;
                    684: {
                    685:        register char *cp, *dp;
                    686: 
                    687:        cp = to;
                    688:        for (dp = from1; *cp = *dp++; cp++)
                    689:                ;
                    690:        for (dp = from2; *cp++ = *dp++; )
                    691:                ;
                    692: }
                    693: 
                    694: /* copy p... into s, update p */
                    695: char *
                    696: getarg(s, p)
                    697:        register char *s, *p;
                    698: {
                    699:        while (*p == ' ' || *p == '\t')
                    700:                p++;
                    701:        if (*p == '\n' || *p == '\0')
                    702:                return(NULL);
                    703:        while (*p != ' ' && *p != '\t' && *p != '\n' && *p != '\0')
                    704:                *s++ = *p++;
                    705:        *s = '\0';
                    706:        return(p);
                    707: }
                    708: 
                    709: safefile(f)
                    710:        char *f;
                    711: {
                    712:        struct stat statb;
                    713: 
                    714:        if (lstat(f, &statb) < 0)
                    715:                return (1);
                    716:        if (statb.st_nlink != 1 || (statb.st_mode & S_IFMT) == S_IFLNK) {
                    717:                fprintf(stderr,
                    718:                    "mail: %s has more than one link or is a symbolic link\n",
                    719:                    f);
                    720:                return (0);
                    721:        }
                    722:        return (1);
                    723: }
                    724: 
                    725: panic(msg, a1, a2, a3)
                    726:        char *msg;
                    727: {
                    728: 
                    729:        fprintf(stderr, "mail: ");
                    730:        fprintf(stderr, msg, a1, a2, a3);
                    731:        fprintf(stderr, "\n");
                    732:        done();
                    733: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.