Annotation of researchv10no/cmd/nupas/print/edmail.c, revision 1.1

1.1     ! root        1: /*
        !             2:  *     print mail
        !             3:  */
        !             4: #include <stdio.h>
        !             5: #include <setjmp.h>
        !             6: #include <ctype.h>
        !             7: #include <signal.h>
        !             8: #include <regexp.h>
        !             9: #include "mail.h"
        !            10: #include "string.h"
        !            11: #include "message.h"
        !            12: #include "aux.h"
        !            13: #include <sys/stat.h>
        !            14: 
        !            15: /* global to this file */
        !            16: static int reverse=0;          /* ordering of mail messages */
        !            17: static jmp_buf sjbuf;
        !            18: int fflg;
        !            19: int mflg;
        !            20: int pflg;
        !            21: int eflg;
        !            22: SIG_TYP fint;                  /* what to do in case of int */
        !            23: SIG_TYP fquit;                 /* what to do in case of quit */
        !            24: SIG_TYP fpipe;                 /* what to do in case of sigpipe */
        !            25: 
        !            26: /* predeclared */
        !            27: message *addr();
        !            28: message *grange();
        !            29: message *range();
        !            30: message *research();
        !            31: message *bresearch();
        !            32: message *incraddr();
        !            33: char *getre();
        !            34: char *header();
        !            35: int edmail();
        !            36: char *doargs();
        !            37: void dumpmail();
        !            38: 
        !            39: /* imported */
        !            40: char *getlog();
        !            41: FILE *lockopen();
        !            42: FILE *lockreopen();
        !            43: 
        !            44: SIGRETURN
        !            45: done(s)
        !            46:        int s;
        !            47: {
        !            48:        cleanlocks();
        !            49:        V();
        !            50:        exit(1);
        !            51: }
        !            52: 
        !            53: main(ac, av)
        !            54:        int ac;
        !            55:        char *av[];
        !            56: {
        !            57:        char outbuf[BUFSIZ];
        !            58:        int writeable;
        !            59:        string *user = s_new();
        !            60:        char *mailfile;
        !            61:        char *logname;
        !            62: 
        !            63:        /* set signals - make sure we don't override some previous setting */
        !            64:        if ((fint=signal(SIGINT, SIG_IGN))!=SIG_DFL)
        !            65:                signal(SIGINT, fint);
        !            66:        else
        !            67:                signal(SIGINT, fint = (SIG_TYP)done);
        !            68:        if ((fquit=signal(SIGQUIT, SIG_IGN))!=SIG_DFL)
        !            69:                signal(SIGQUIT, fquit);
        !            70:        else
        !            71:                signal(SIGQUIT, fquit = (SIG_TYP)done);
        !            72:        if ((fpipe=signal(SIGPIPE, SIG_IGN))!=SIG_DFL)
        !            73:                signal(SIGPIPE, fpipe);
        !            74:        else
        !            75:                signal(SIGPIPE, fpipe = (SIG_TYP)done);
        !            76: 
        !            77:        logname = getlog();
        !            78:        if (logname == NULL) {
        !            79:                printf ("mail: cannot determine login name\n");
        !            80:                return 0;
        !            81:        }
        !            82:        s_append(user, logname);
        !            83:        setbuf(stdout, outbuf);
        !            84:        mailfile = doargs(ac, av, s_to_c(user));
        !            85:        if (!fflg)
        !            86:                writeable = P()==0;
        !            87:        else
        !            88:                writeable = 1;
        !            89:        if (eflg) {
        !            90:                int r = check_mbox(mailfile);
        !            91:                V();
        !            92:                return r;
        !            93:        }
        !            94:        if (read_mbox(mailfile, reverse)<0 || mlist == NULL) {
        !            95:                printf("No mail\n");
        !            96:                V();
        !            97:                return 0;
        !            98:        }
        !            99:        printf("%d messages\n", mlast->pos);
        !           100:        if (pflg)
        !           101:                dumpmail();
        !           102:        else{
        !           103:                while (edmail(mailfile, reverse) && writeable){
        !           104:                        if(!write_mbox(mailfile, reverse))
        !           105:                                break;
        !           106:                }
        !           107:        }
        !           108:        V();
        !           109:        return 0;
        !           110: }
        !           111: 
        !           112: /* parse arguments */
        !           113: char *
        !           114: doargs(ac, av, user)
        !           115:        int ac;
        !           116:        char *av[];
        !           117:        char *user;
        !           118: {
        !           119:        int i;
        !           120:        string *mailfile;
        !           121:        char *cp;
        !           122: 
        !           123:        /* process args */
        !           124:        mailfile = s_new();
        !           125:        abspath(user, MAILROOT, mailfile);
        !           126:        for (i = 1; i<ac; i++) {
        !           127:                if (av[i][0]!='-') {
        !           128:                        fprintf(stderr, "usage: mail [-mpre] [-f mbox]\n");
        !           129:                        exit(1);
        !           130:                }
        !           131:                for (cp = av[i]+1; *cp; cp++) {
        !           132:                        switch(*cp) {
        !           133:                        case 'r':
        !           134:                                reverse = 1;
        !           135:                                break;
        !           136:                        case 'm':
        !           137:                                mflg = 1;
        !           138:                                break;
        !           139:                        case 'p':
        !           140:                                pflg = 1;
        !           141:                                break;
        !           142:                        case 'e':
        !           143:                                eflg = 1;
        !           144:                                break;
        !           145:                        case 'f':
        !           146:                                fflg = 1;
        !           147:                                if (i+1 >= ac) {
        !           148:                                        fprintf(stderr,"mail: missing filename\n");
        !           149:                                        exit(1);
        !           150:                                }
        !           151:                                s_append(s_restart(mailfile), av[++i]);
        !           152:                                break;
        !           153:                        default:
        !           154:                                fprintf(stderr, "usage: mail [-mpre] [-f mbox]\n");
        !           155:                                exit(1);
        !           156:                        }
        !           157:                }
        !           158:        }
        !           159:        return s_to_c(mailfile);
        !           160: }
        !           161: 
        !           162: /* is the mailbox empty?  1 if yes, 0 if no */
        !           163: int
        !           164: check_mbox (mf)
        !           165:        char *mf;
        !           166: {
        !           167:        int n, r;
        !           168:        char mbuf[1000];
        !           169:        string *line;
        !           170:        FILE *fp;
        !           171: 
        !           172:        /* if file doesn't exist, no mail */
        !           173:        if ((fp = fopen(mf, "r")) == NULL)
        !           174:                return 1;
        !           175: 
        !           176:        /* if we can't read it, no mail */
        !           177:        if (fgets(mbuf, sizeof(mbuf)-2, fp)==NULL){
        !           178:                fclose(fp);
        !           179:                return 1;
        !           180:        }
        !           181:        fclose(fp);
        !           182: 
        !           183:        /* it is empty iff delivery status is abnormal */
        !           184:        n = strlen(mbuf);
        !           185:        mbuf[n++] = '\n';
        !           186:        mbuf[n++] = '\0';
        !           187:        line = s_array(mbuf, n);
        !           188:        r = delivery_status(s_restart(line)) != MF_NORMAL;
        !           189: 
        !           190:        s_free (line);
        !           191:        return r;
        !           192: }
        !           193: 
        !           194: /* mesage dump */
        !           195: void
        !           196: dumpmail()
        !           197: {
        !           198:        message *mp;
        !           199: 
        !           200:        for (mp=mlist; mp!=NULL; mp=mp->next) {
        !           201:                m_print(mp, stdout, 1, 1);
        !           202:        }
        !           203: }
        !           204: 
        !           205: SIGRETURN
        !           206: catchint(s)
        !           207:        int s;
        !           208: {
        !           209:        signal(SIGINT, catchint);
        !           210:        clearerr(stdin);
        !           211:        clearerr(stdout);
        !           212:        longjmp(sjbuf, 1);
        !           213: }
        !           214: 
        !           215: notatnl(cp)
        !           216:        char *cp;
        !           217: {
        !           218:        if (*cp=='\n') {
        !           219:                fprintf(stderr, "!argument expected\n");
        !           220:                return -1;
        !           221:        }
        !           222:        return 0;
        !           223: }
        !           224: 
        !           225: int
        !           226: atblank(cp)
        !           227: char *cp;
        !           228: {
        !           229:        if (*cp!='\n' && *(cp-1)!=' ' && *(cp-1)!='\t') {
        !           230:                fprintf(stderr, "newline or space expected\n");
        !           231:                return -1;
        !           232:        }
        !           233:        return 0;
        !           234: }
        !           235: 
        !           236: atnl(cp)
        !           237:        char *cp;
        !           238: {
        !           239:        if (*cp!='\n') {
        !           240:                fprintf(stderr, "!newline expected\n");
        !           241:                return -1;
        !           242:        }
        !           243:        return 0;
        !           244: }
        !           245: 
        !           246: zero(mp)
        !           247:        message *mp;
        !           248: {
        !           249:        if (mp==mzero) {
        !           250:                fprintf(stderr, "!message 0\n");
        !           251:                return -1;
        !           252:        }
        !           253:        return 0;
        !           254: }
        !           255: 
        !           256: #define s_skipwhite(s) for (; *s->ptr==' ' || *s->ptr=='\t'; s->ptr++);
        !           257: 
        !           258: /* ed style interface */
        !           259: edmail(mailfile, reverse)
        !           260:        char *mailfile;
        !           261:        int reverse;
        !           262: {
        !           263:        message *dot;
        !           264:        message *extent;
        !           265:        string *cmd=s_new();
        !           266:        char *cp;
        !           267:        int cmdc;
        !           268:        int i, abort=0, nopr, change=1;
        !           269:        int del;
        !           270: 
        !           271:        extent = dot = mzero;
        !           272:        nopr = mflg;
        !           273:        for(;;) {
        !           274:                extent = dot;   /* in case of interrupt */
        !           275:                if (!nopr) {
        !           276:                        /* advance only if we want to print next message */
        !           277:                        if(dot->next!=NULL)
        !           278:                                dot = dot->next;
        !           279:                        else
        !           280:                                nopr = 1;
        !           281:                }
        !           282:                if (setjmp(sjbuf)) {
        !           283:                        /* come here after interrupt */
        !           284:                        if (extent!=NULL)
        !           285:                                dot = extent;
        !           286:                        nopr = 1;
        !           287:                        printf("\n");
        !           288:                }
        !           289:                if (fint==(SIG_TYP)done)
        !           290:                        signal(SIGINT, catchint);
        !           291:                if (!nopr&&dot!=mzero) {
        !           292:                        /* print next message */
        !           293:                        extent = dot;   /* in case of interrupt */
        !           294:                        print(dot);
        !           295:                        nopr = 1;
        !           296:                }
        !           297:                abort = 0;
        !           298:                nopr = 1;
        !           299:                change = 1;
        !           300:                printf("?");
        !           301:                fflush(stdout);
        !           302:                if(s_read_line(stdin, s_restart(cmd)) == NULL) {
        !           303:                        signal(SIGINT, fint);   /* bacause of the setjmp */
        !           304:                        return 1;
        !           305:                }
        !           306:                s_restart(cmd);
        !           307:                s_skipwhite(cmd);
        !           308:                if (!mflg && *cmd->ptr=='\n' && dot==mlast) {
        !           309:                        signal(SIGINT, fint);   /* bacause of the setjmp */
        !           310:                        return 1;
        !           311:                }
        !           312:                extent = range(dot, cmd);
        !           313:                s_skipwhite(cmd);
        !           314:                del = 0;
        !           315: compoundcmd:
        !           316:                /* hack to catch a common mistake */
        !           317:                if (strncmp(cmd->ptr, "mail", 4)==0)
        !           318:                        cmdc = -1;
        !           319:                else
        !           320:                        cmdc = *cmd->ptr++;
        !           321:                s_skipwhite(cmd);
        !           322:                cp = cmd->ptr;
        !           323:                for(; extent!=NULL && !abort; extent=extent->extent) {
        !           324:                        switch(cmdc){
        !           325:                        case 'b':
        !           326:                                abort = atnl(cp)||(del&&delete(extent));
        !           327:                                if (!abort)
        !           328:                                        if (extent!=mzero)
        !           329:                                                prheader(extent);
        !           330:                                for(i=0; extent->next!=NULL&&i<9; i++){
        !           331:                                        extent = extent->next;
        !           332:                                        prheader(extent);
        !           333:                                }
        !           334:                                break;
        !           335:                        case 'h':
        !           336:                                abort = atnl(cp)||zero(extent)
        !           337:                                        ||(del&&delete(extent))
        !           338:                                        ||prheader(extent);
        !           339:                                break;
        !           340:                        case 'd':
        !           341:                                if(*cp=='\n' || *cp==0){
        !           342:                                        abort = zero(extent)||delete(extent);
        !           343:                                        nopr = abort||mflg;
        !           344:                                        break;
        !           345:                                }
        !           346:                                del = 1;
        !           347:                                goto compoundcmd;
        !           348:                        case 's':
        !           349:                                abort = atblank(cp)||zero(extent)||store(extent, cp, 1)
        !           350:                                        ||(del&&delete(extent));
        !           351:                                nopr = abort||mflg||!del;
        !           352:                                break;
        !           353:                        case 'w':
        !           354:                                abort = atblank(cp)||zero(extent)||notatnl(cp)
        !           355:                                        ||store(extent, cp, 0)
        !           356:                                        ||(del&&delete(extent));
        !           357:                                nopr = abort||mflg||!del;
        !           358:                                break;
        !           359:                        case 'm':
        !           360:                                abort = atblank(cp)||zero(extent)||notatnl(cp)
        !           361:                                        ||remail(extent, cp, 0)
        !           362:                                        ||(del&&delete(extent));
        !           363:                                nopr = abort||mflg||!del;
        !           364:                                break;
        !           365:                        case 'M':
        !           366:                                abort = atblank(cp)||zero(extent)||notatnl(cp)
        !           367:                                        ||remail(extent, cp, 1)
        !           368:                                        ||(del&&delete(extent));
        !           369:                                nopr = abort||mflg||!del;
        !           370:                                break;
        !           371:                        case '\n':
        !           372:                                abort = zero(extent)||print(extent);
        !           373:                                break;
        !           374:                        case 'p':
        !           375:                                if(del){
        !           376:                                        nopr = abort = atnl(cp)||zero(extent)
        !           377:                                                ||(del&&delete(extent));
        !           378:                                        break;
        !           379:                                }
        !           380:                                abort = atnl(cp)||zero(extent)||print(extent);
        !           381:                                break;
        !           382:                        case 'r':
        !           383:                                abort = zero(extent)||atnl(cp)||reply(extent, 0)
        !           384:                                        ||(del&&delete(extent));
        !           385:                                nopr = abort||mflg||!del;
        !           386:                                break;
        !           387:                        case 'R':
        !           388:                                abort = zero(extent)||atnl(cp)||reply(extent, 1)
        !           389:                                        ||(del&&delete(extent));
        !           390:                                nopr = abort||mflg||!del;
        !           391:                                break;
        !           392:                        case 'q':
        !           393:                                abort=atnl(cp)
        !           394:                                    ||(del&&(zero(extent)||delete(extent)));
        !           395:                                if(abort)
        !           396:                                        break;
        !           397:                                signal(SIGINT, fint);   /* bacause of the setjmp */
        !           398:                                return 1;
        !           399:                        case '|':
        !           400:                                abort = zero(extent)||notatnl(cp)
        !           401:                                        ||pipemail(extent, cp, 0)
        !           402:                                        ||(del&&delete(extent));
        !           403:                                nopr = abort||mflg||!del;
        !           404:                                break;
        !           405:                        case '=':
        !           406:                                abort = atnl(cp)||(del&&delete(extent))
        !           407:                                        ||whereis(extent);
        !           408:                                change = 0;
        !           409:                                break;
        !           410:                        case '!':
        !           411:                                abort=del&&(zero(extent)||delete(extent));
        !           412:                                if(abort)
        !           413:                                        break;
        !           414:                                escape(cp);
        !           415:                                break;
        !           416:                        case 'u':
        !           417:                                abort = zero(extent)||atnl(cp)||undelete(extent);
        !           418:                                break;
        !           419:                        case 'x':
        !           420:                                signal(SIGINT, fint);   /* bacause of the setjmp */
        !           421:                                return 0;
        !           422:                        case '?':
        !           423:                                abort = atnl(cp)
        !           424:                                        ||del&&(zero(extent)||delete(extent));
        !           425:                                if(abort)
        !           426:                                        break;
        !           427:                                help();
        !           428:                                nopr = abort = 1;
        !           429:                                break;
        !           430:                        case 'i':
        !           431:                                abort = atnl(cp)
        !           432:                                        ||(del&&(zero(extent)||delete(extent)));
        !           433:                                if(abort)
        !           434:                                        break;
        !           435:                                reread_mbox(mailfile, reverse);
        !           436:                                nopr = abort = 1;
        !           437:                                break;
        !           438:                        default:
        !           439:                                printf("!unknown command (type ? for help)\n");
        !           440:                                nopr = abort = 1;
        !           441:                                break;
        !           442:                        }
        !           443:                        if (!abort&&change&&extent!=NULL)
        !           444:                                dot = extent;
        !           445:                }
        !           446:        }
        !           447: }
        !           448: 
        !           449: /* parse an address range */
        !           450: message *
        !           451: range(dot, cmd)
        !           452:        message *dot;
        !           453:        string *cmd;
        !           454: {
        !           455:        message *first, *last;
        !           456: 
        !           457:        s_skipwhite(cmd);
        !           458: 
        !           459:        /* get first address in range */
        !           460:        switch(*cmd->ptr) {
        !           461:        case 'g':
        !           462:                cmd->ptr++;
        !           463:                return grange(cmd);
        !           464:        case ',':
        !           465:                first = mlist;
        !           466:                break;
        !           467:        case '0': case '1': case '2': case '3': case '4':
        !           468:        case '5': case '6': case '7': case '8': case '9':
        !           469:                first = addr((message *)NULL, cmd);
        !           470:                break;
        !           471:        case '?':
        !           472:                if (*(cmd->ptr+1)=='\n') {
        !           473:                        if(dot!=NULL)
        !           474:                                dot->extent = NULL;
        !           475:                        return dot;
        !           476:                }
        !           477:        case '\\': case '/': case '+': case '-': case '$': case '.':
        !           478:                first = addr(dot, cmd);
        !           479:                break;
        !           480:        case '\n':
        !           481:                first = dot->next;
        !           482:                if (first==NULL)
        !           483:                        fprintf(stderr, "!address\n");
        !           484:                break;
        !           485:        default:
        !           486:                if(dot!=NULL)
        !           487:                        dot->extent = NULL;
        !           488:                return dot;
        !           489:        }
        !           490:        if (first == NULL)
        !           491:                return NULL;
        !           492:        while(*cmd->ptr == ' ' || *cmd->ptr == '\t')
        !           493:                cmd->ptr++;
        !           494:        if (*cmd->ptr != ',') {
        !           495:                first->extent = NULL;
        !           496:                return first;
        !           497:        }
        !           498: 
        !           499:        /* get second address in range */
        !           500:        cmd->ptr++;
        !           501:        while(*cmd->ptr == ' ' || *cmd->ptr == '\t')
        !           502:                cmd->ptr++;
        !           503:        switch(*cmd->ptr) {
        !           504:        case '\\': case '/': case '?': case '+': case '-': case '$':
        !           505:                last = addr(first, cmd);
        !           506:                break;
        !           507:        case '.':
        !           508:                last = addr(dot, cmd);
        !           509:                break;
        !           510:        case '0': case '1': case '2': case '3': case '4':
        !           511:        case '5': case '6': case '7': case '8': case '9':
        !           512:                last = addr((message *)NULL, cmd);
        !           513:                break;
        !           514:        default:
        !           515:                last = mlast;
        !           516:                break;
        !           517:        }
        !           518:        if (last==NULL)
        !           519:                return NULL;
        !           520: 
        !           521:        /* fill in the range */
        !           522:        for(dot=first; dot!=last && dot!=NULL; dot=dot->next)
        !           523:                dot->extent = dot->next;
        !           524:        if (dot==NULL) {
        !           525:                fprintf(stderr, "!addresses out of order\n");
        !           526:                return NULL;
        !           527:        }
        !           528:        last->extent = NULL;
        !           529:        return first;
        !           530: }
        !           531: 
        !           532: /* parse a global range */
        !           533: message *
        !           534: grange(cmd)
        !           535:        string *cmd;
        !           536: {
        !           537:        char *re;
        !           538:        message *first, *last, *next;
        !           539:        regexp *pp;
        !           540: 
        !           541:        if (*cmd->ptr == '/') {
        !           542:                re = getre(cmd);
        !           543:                if (re == NULL)
        !           544:                        return NULL;
        !           545:                if ((pp = regcomp(re))==NULL)
        !           546:                        return NULL;
        !           547:                first = NULL;
        !           548:                for(next=mlist; next!=NULL; next=next->next)
        !           549:                        if (regexec(pp, header(next), 0, 0)) {
        !           550:                                if (first==NULL)
        !           551:                                        first = last = next;
        !           552:                                else {
        !           553:                                        last->extent = next;
        !           554:                                        last = next;
        !           555:                                }
        !           556:                                last->extent = NULL;
        !           557:                        }
        !           558:                if (first==NULL)
        !           559:                        fprintf(stderr, "!match\n");
        !           560:                free((char *)pp);
        !           561:                return first;
        !           562:        } else if (*cmd->ptr == '\\') {
        !           563:                re = getre(cmd);
        !           564:                if (re == NULL)
        !           565:                        return NULL;
        !           566:                if ((pp = regcomp(re))==NULL)
        !           567:                        return NULL;
        !           568:                first = NULL;
        !           569:                for(next=mlist; next!=NULL; next=next->next){
        !           570:                        s_to_c(next->body)[next->size-1]='\0';
        !           571:                        if (regexec(pp, s_to_c(next->body), 0, 0)) {
        !           572:                                if (first==NULL)
        !           573:                                        first = last = next;
        !           574:                                else {
        !           575:                                        last->extent = next;
        !           576:                                        last = next;
        !           577:                                }
        !           578:                                last->extent = NULL;
        !           579:                        }
        !           580:                }
        !           581:                if (first==NULL)
        !           582:                        fprintf(stderr, "!match\n");
        !           583:                free((char *)pp);
        !           584:                return first;
        !           585:        } else {
        !           586:                /* fill in the range */
        !           587:                for(next=mlist; next!=NULL; next=next->next)
        !           588:                        next->extent = next->next;
        !           589:                mlast->extent = NULL;
        !           590:                return mlist;
        !           591:        }
        !           592: }
        !           593: 
        !           594: /* parse an address */
        !           595: message *
        !           596: addr(base, cmd)
        !           597:        message *base;          /* where to compute +/- from */
        !           598:        string *cmd;
        !           599: {
        !           600:        int forward = -1;
        !           601: 
        !           602:        /* get direction */
        !           603:        switch(*cmd->ptr) {
        !           604:        case '+':
        !           605:                forward = 1;
        !           606:                cmd->ptr++;
        !           607:                break;
        !           608:        case '-':
        !           609:                forward = 0;
        !           610:                cmd->ptr++;
        !           611:                break;
        !           612:        }
        !           613:        while(*cmd->ptr == ' ' || *cmd->ptr == '\t')
        !           614:                cmd->ptr++;
        !           615:        switch(*cmd->ptr) {
        !           616:        case '0': case '1': case '2': case '3': case '4':
        !           617:        case '5': case '6': case '7': case '8': case '9':
        !           618:                base = incraddr(base, getnumb(cmd), forward);
        !           619:                if (base==NULL)
        !           620:                        break;
        !           621:                return addr(base, cmd);
        !           622:        case '?':
        !           623:                forward = !forward;
        !           624:        case '/':
        !           625:                base = research(base, getre(cmd), forward);
        !           626:                if (base==NULL) {
        !           627:                        fprintf(stderr, "!search\n");
        !           628:                        return NULL;
        !           629:                }
        !           630:                return addr(base, cmd);
        !           631:        case '\\':
        !           632:                base = bresearch(base, getre(cmd), forward);
        !           633:                if (base==NULL) {
        !           634:                        fprintf(stderr, "!search\n");
        !           635:                        return NULL;
        !           636:                }
        !           637:                return addr(base, cmd);
        !           638:        case '.':
        !           639:                cmd->ptr++;
        !           640:                return addr(base, cmd);;
        !           641:        case '$':
        !           642:                cmd->ptr++;
        !           643:                return addr(mlast, cmd);
        !           644:        default:
        !           645:                /* default increment is 1 */
        !           646:                if (forward != -1) {
        !           647:                        base = incraddr(base, 1, forward);
        !           648:                        return addr(base, cmd);
        !           649:                }
        !           650:                break;
        !           651:        }
        !           652:        if (base==NULL)
        !           653:                fprintf(stderr, "!address\n");
        !           654:        return base;
        !           655: }
        !           656: 
        !           657: /* increment the base address by offset */
        !           658: message *
        !           659: incraddr(base, offset, forward)
        !           660:        message *base;
        !           661:        int offset;
        !           662:        int forward;
        !           663: {
        !           664:        if (base==NULL) {
        !           665:                base = mzero;
        !           666:        }
        !           667:        for(; offset > 0 && base != NULL; offset--)
        !           668:                base = forward?(base->next):(base->prev);
        !           669:        return base;
        !           670: }
        !           671: 
        !           672: /* look for the message header after base that matches the reg exp */
        !           673: message *
        !           674: research(base, rp, forward)
        !           675:        message *base;
        !           676:        char *rp;
        !           677:        int forward;
        !           678: {
        !           679:        regexp *pp;
        !           680:        message *mp;
        !           681: 
        !           682:        if (rp == NULL) 
        !           683:                return NULL;
        !           684:        if ((pp = regcomp(rp))==NULL)
        !           685:                return NULL;
        !           686:        mp = base;
        !           687:        base = (base==mzero)?(forward?(mp->prev):(mp->next)):base;
        !           688:        do {
        !           689:                mp = forward?(mp->next):(mp->prev);
        !           690:                if (mp==NULL)
        !           691:                        mp = forward?mlist:mlast;
        !           692:                if (regexec(pp, header(mp), 0, 0)) {
        !           693:                        free((char *)pp);
        !           694:                        return mp;
        !           695:                }
        !           696:        } while (mp!=base);
        !           697:        free((char *)pp);
        !           698:        return NULL;
        !           699: }
        !           700: 
        !           701: /* look for the message after base that matches the reg exp */
        !           702: message *
        !           703: bresearch(base, rp, forward)
        !           704:        message *base;
        !           705:        char *rp;
        !           706:        int forward;
        !           707: {
        !           708:        regexp *pp;
        !           709:        message *mp;
        !           710: 
        !           711:        if (rp == NULL) 
        !           712:                return NULL;
        !           713:        if ((pp = regcomp(rp))==NULL)
        !           714:                return NULL;
        !           715:        mp = base = (base==mzero)?mzero->next:base;
        !           716:        do {
        !           717:                mp = forward?(mp->next):(mp->prev);
        !           718:                if (mp==NULL)
        !           719:                        mp = forward?mlist:mlast;
        !           720:                s_to_c(mp->body)[mp->size-1]='\0';
        !           721:                if (regexec(pp, s_to_c(mp->body), 0, 0)) {
        !           722:                        free((char *)pp);
        !           723:                        return mp;
        !           724:                }
        !           725:        } while (mp!=base);
        !           726:        free((char *)pp);
        !           727:        return NULL;
        !           728: }
        !           729: 
        !           730: /* get a number out of the command */
        !           731: int
        !           732: getnumb(cmd)
        !           733:        string *cmd;
        !           734: {
        !           735:        int offset=0;
        !           736:        while (isdigit(*cmd->ptr))
        !           737:                offset = offset*10 + *cmd->ptr++ - '0';
        !           738:        return offset;
        !           739: }
        !           740: 
        !           741: /* get a regular exression out of the command */
        !           742: char *
        !           743: getre(cmd)
        !           744:        string *cmd;
        !           745: {
        !           746:        static char re[80];
        !           747:        char *cp=re;
        !           748:        char term = *cmd->ptr++;
        !           749: 
        !           750:        while (*cmd->ptr!='\0' && *cmd->ptr!='\n' && *cmd->ptr!=term)
        !           751:                *cp++ = *cmd->ptr++;
        !           752:        if (*cmd->ptr == term)
        !           753:                cmd->ptr++;
        !           754:        if (cp == re) {
        !           755:                if (*re == '\0') {
        !           756:                        fprintf(stderr, "!no previous regular expression\n");
        !           757:                        return NULL;
        !           758:                }
        !           759:        } else
        !           760:                *cp = '\0';
        !           761:        return re;
        !           762: }
        !           763: 
        !           764: regerror(msg)  
        !           765:        char *msg;
        !           766: {
        !           767:        fprintf(stderr, "!illegal address: %s\n", msg);
        !           768: }

unix.superglobalmegacorp.com

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