Annotation of 43BSDReno/contrib/mh/uip/dropsbr.c, revision 1.1.1.1

1.1       root        1: /* dropsbr.c - write to a mailbox */
                      2: 
                      3: #include <stdio.h>
                      4: #ifndef        MMDFONLY
                      5: #include "../h/mh.h"
                      6: #include "../h/dropsbr.h"
                      7: #include "../zotnet/mts.h"
                      8: #else  MMDFONLY
                      9: #include "dropsbr.h"
                     10: #include "strings.h"
                     11: #include "mmdfonly.h"
                     12: #endif MMDFONLY
                     13: #include <errno.h>
                     14: #include <sys/types.h>
                     15: #include <sys/stat.h>
                     16: 
                     17: 
                     18: #define        MMDF    1
                     19: #define        UUCP    2
                     20: 
                     21: /*  */
                     22: 
                     23: static int     mbx_style = MMDF;
                     24: 
                     25: 
                     26: extern int  errno;
                     27: 
                     28: 
                     29: long   lseek ();
                     30: 
                     31: static int mbx_create(), mbx_chk(), map_open();
                     32: 
                     33: /*  */
                     34: 
                     35: int     mbx_mmdf () {
                     36:     int     style = mbx_style;
                     37: 
                     38:     mbx_style = MMDF;
                     39:     return style;
                     40: }
                     41: 
                     42: 
                     43: int     mbx_uucp () {
                     44:     int     style = mbx_style;
                     45: 
                     46:     mbx_style = UUCP;
                     47:     return style;
                     48: }
                     49: 
                     50: /*  */
                     51: 
                     52: int     mbx_open (file, uid, gid, mode)
                     53: char   *file;
                     54: int     uid,
                     55:         gid,
                     56:        mode;
                     57: {
                     58:     int     clear,
                     59:             fd;
                     60: 
                     61:     if ((fd = mbx_Xopen (file, uid, gid, mode, &clear)) == NOTOK)
                     62:        return fd;
                     63: 
                     64:     if (!clear)
                     65:        switch (mbx_style) {
                     66:            case MMDF: 
                     67:            default: 
                     68:                if (mbx_chk (fd) == NOTOK) {
                     69:                    (void) close (fd);
                     70:                    return NOTOK;
                     71:                }
                     72:                break;
                     73: 
                     74:            case UUCP: 
                     75:                if (lseek (fd, 0L, 2) == (long) NOTOK) {
                     76:                    (void) close (fd);
                     77:                    return NOTOK;
                     78:                }
                     79:                break;
                     80:        }
                     81: 
                     82:     return fd;
                     83: }
                     84: 
                     85: /*  */
                     86: 
                     87: int    mbx_Xopen (file, uid, gid, mode, clear)
                     88: char   *file;
                     89: int    uid,
                     90:        gid,
                     91:        mode,
                     92:        *clear;
                     93: {
                     94:     register int j;
                     95:     int            count,
                     96:             fd;
                     97:     struct stat st;
                     98: 
                     99:     for (*clear = 0, count = 4, j = 0; count > 0; count--)
                    100:        if ((fd = lkopen (file, 6)) == NOTOK)
                    101:            switch (errno) {
                    102:                case ENOENT: 
                    103:                    if (mbx_create (file, uid, gid, mode) == NOTOK)
                    104:                        return NOTOK;
                    105:                    (*clear)++;
                    106:                    break;
                    107: 
                    108: #ifdef BSD42
                    109:                case EWOULDBLOCK:
                    110: #endif BSD42
                    111:                case ETXTBSY: 
                    112:                    j = errno;
                    113:                    sleep (5);
                    114:                    break;
                    115: 
                    116:                default: 
                    117:                    return NOTOK;
                    118:            }
                    119:        else {
                    120:            *clear = fstat (fd, &st) != NOTOK && st.st_size == 0L;
                    121:            break;
                    122:        }
                    123: 
                    124:     errno = j;
                    125:     return fd;
                    126: }
                    127: 
                    128: /*  */
                    129: 
                    130: static int  mbx_create (file, uid, gid, mode)
                    131: char   *file;
                    132: int     uid,
                    133:         gid,
                    134:        mode;
                    135: {
                    136:     int     fd;
                    137: 
                    138:     if ((fd = creat (file, 0600)) == NOTOK)
                    139:        return NOTOK;
                    140: 
                    141:     (void) close (fd);
                    142:     (void) chown (file, uid, gid);
                    143:     (void) chmod (file, mode);
                    144: 
                    145:     return OK;
                    146: }
                    147: 
                    148: 
                    149: static int  mbx_chk (fd)
                    150: int     fd;
                    151: {
                    152:     int     count;
                    153:     char    ldelim[BUFSIZ];
                    154: 
                    155:     count = strlen (mmdlm2);
                    156: 
                    157:     if (lseek (fd, (long) (-count), 2) == (long) NOTOK
                    158:            || read (fd, ldelim, count) != count)
                    159:        return NOTOK;
                    160:     ldelim[count] = NULL;
                    161: 
                    162:     if (strcmp (ldelim, mmdlm2)
                    163:            && write (fd, "\n", 1) != 1
                    164:            && write (fd, mmdlm2, count) != count)
                    165:        return NOTOK;
                    166: 
                    167:     return OK;
                    168: }
                    169: 
                    170: /*  */
                    171: 
                    172: int    mbx_read (fp, pos, drops, noisy)
                    173: register FILE  *fp;
                    174: register long  pos;
                    175: struct drop **drops;
                    176: int    noisy;
                    177: {
                    178:     register int    len,
                    179:                     size;
                    180:     long    ld1,
                    181:             ld2;
                    182:     register char  *bp;
                    183:     char    buffer[BUFSIZ];
                    184:     register struct drop   *cp,
                    185:                            *dp,
                    186:                            *ep,
                    187:                            *pp;
                    188: 
                    189:     pp = (struct drop  *) calloc ((unsigned) (len = MAXFOLDER), sizeof *dp);
                    190:     if (pp == NULL) {
                    191:        if (noisy)
                    192:            admonish (NULLCP, "unable to allocate drop storage");
                    193:        return NOTOK;
                    194:     }
                    195: 
                    196:     ld1 = (long) strlen (mmdlm1);
                    197:     ld2 = (long) strlen (mmdlm2);
                    198: 
                    199:     (void) fseek (fp, pos, 0);
                    200:     for (ep = (dp = pp) + len - 1; fgets (buffer, sizeof buffer, fp);) {
                    201:        size = 0;
                    202:        if (strcmp (buffer, mmdlm1) == 0)
                    203:            pos += ld1, dp -> d_start = pos;
                    204:        else {
                    205:            dp -> d_start = pos, pos += (long) strlen (buffer);
                    206:            for (bp = buffer; *bp; bp++, size++)
                    207:                if (*bp == '\n')
                    208:                    size++;
                    209:        }
                    210: 
                    211:        while (fgets (buffer, sizeof buffer, fp) != NULL)
                    212:            if (strcmp (buffer, mmdlm2) == 0)
                    213:                break;
                    214:            else {
                    215:                pos += (long) strlen (buffer);
                    216:                for (bp = buffer; *bp; bp++, size++)
                    217:                    if (*bp == '\n')
                    218:                        size++;
                    219:            }
                    220: 
                    221:        if (dp -> d_start != pos) {
                    222:            dp -> d_id = 0;
                    223:            dp -> d_size = size;
                    224:            dp -> d_stop = pos;
                    225:            dp++;
                    226:        }
                    227:        pos += ld2;
                    228: 
                    229:        if (dp >= ep) {
                    230:            register int    curlen = dp - pp;
                    231: 
                    232:            cp = (struct drop  *) realloc ((char *) pp,
                    233:                                    (unsigned) (len += MAXFOLDER) * sizeof *pp);
                    234:            if (cp == NULL) {
                    235:                if (noisy)
                    236:                    admonish (NULLCP, "unable to allocate drop storage");
                    237:                free ((char *) pp);
                    238:                return 0;
                    239:            }
                    240:            dp = cp + curlen, ep = (pp = cp) + len - 1;
                    241:        }
                    242:     }
                    243: 
                    244:     if (dp == pp)
                    245:        free ((char *) pp);
                    246:     else
                    247:        *drops = pp;
                    248:     return (dp - pp);
                    249: }
                    250: 
                    251: /*  */
                    252: 
                    253: int    mbx_write (mailbox, md, fp, id, pos, stop, mapping, noisy)
                    254: char   *mailbox;
                    255: register FILE *fp;
                    256: int     md,
                    257:        id,
                    258:        mapping,
                    259:        noisy;
                    260: register long  pos,
                    261:                stop;
                    262: {
                    263:     register int    i,
                    264:                     j,
                    265:                     size;
                    266:     register long   start,
                    267:                     off;
                    268:     register char  *cp;
                    269:     char    buffer[BUFSIZ];
                    270: 
                    271:     off = lseek (md, 0L, 1);
                    272:     j = strlen (mmdlm1);
                    273:     if (write (md, mmdlm1, j) != j)
                    274:        return NOTOK;
                    275:     start = lseek (md, 0L, 1);
                    276:     size = 0;
                    277: 
                    278:     (void) fseek (fp, pos, 0);
                    279:     while (fgets (buffer, sizeof buffer, fp) != NULL && pos < stop) {
                    280:        i = strlen (buffer);
                    281:        for (j = 0; (j = stringdex (mmdlm1, buffer)) >= 0; buffer[j]++)
                    282:            continue;
                    283:        for (j = 0; (j = stringdex (mmdlm2, buffer)) >= 0; buffer[j]++)
                    284:            continue;
                    285:        if (write (md, buffer, i) != i)
                    286:            return NOTOK;
                    287:        pos += (long) i;
                    288:        if (mapping)
                    289:            for (cp = buffer; i-- > 0; size++)
                    290:                if (*cp++ == '\n')
                    291:                    size++;
                    292:     }
                    293: 
                    294:     stop = lseek (md, 0L, 1);
                    295:     j = strlen (mmdlm2);
                    296:     if (write (md, mmdlm2, j) != j)
                    297:        return NOTOK;
                    298:     if (mapping)
                    299:        (void) map_write (mailbox, md, id, start, stop, off, size, noisy);
                    300: 
                    301:     return OK;
                    302: }
                    303: 
                    304: /*  */
                    305: 
                    306: int     mbx_copy (mailbox, md, fd, mapping, text, noisy)
                    307: char   *mailbox;
                    308: int     md,
                    309:         fd,
                    310:        mapping,
                    311:        noisy;
                    312: char   *text;
                    313: {
                    314:     register int    i,
                    315:                     j,
                    316:                     size;
                    317:     register long   start,
                    318:                     stop,
                    319:                     pos;
                    320:     register char  *cp;
                    321:     char    buffer[BUFSIZ];
                    322:     register FILE  *fp;
                    323: 
                    324:     pos = lseek (md, 0L, 1);
                    325:     size = 0;
                    326: 
                    327:     switch (mbx_style) {
                    328:        case MMDF: 
                    329:        default: 
                    330:            j = strlen (mmdlm1);
                    331:            if (write (md, mmdlm1, j) != j)
                    332:                return NOTOK;
                    333:            start = lseek (md, 0L, 1);
                    334: 
                    335:            if (text) {
                    336:                i = strlen (text);
                    337:                if (write (md, text, i) != i)
                    338:                    return NOTOK;
                    339:                for (cp = text; *cp++; size++)
                    340:                    if (*cp == '\n')
                    341:                        size++;
                    342:            }
                    343:                    
                    344:            while ((i = read (fd, buffer, sizeof buffer)) > 0) {
                    345:                for (j = 0;
                    346:                        (j = stringdex (mmdlm1, buffer)) >= 0;
                    347:                        buffer[j]++)
                    348:                    continue;
                    349:                for (j = 0;
                    350:                        (j = stringdex (mmdlm2, buffer)) >= 0;
                    351:                        buffer[j]++)
                    352:                    continue;
                    353:                if (write (md, buffer, i) != i)
                    354:                    return NOTOK;
                    355:                if (mapping)
                    356:                    for (cp = buffer; i-- > 0; size++)
                    357:                        if (*cp++ == '\n')
                    358:                            size++;
                    359:            }
                    360: 
                    361:            stop = lseek (md, 0L, 1);
                    362:            j = strlen (mmdlm2);
                    363:            if (write (md, mmdlm2, j) != j)
                    364:                return NOTOK;
                    365:            if (mapping)
                    366:                (void) map_write (mailbox, md, 0, start, stop, pos, size, noisy);
                    367: 
                    368:            return (i != NOTOK ? OK : NOTOK);
                    369: 
                    370:        case UUCP:              /* I hate this... */
                    371:            if ((j = dup (fd)) == NOTOK)
                    372:                return NOTOK;
                    373:            if ((fp = fdopen (j, "r")) == NULL) {
                    374:                (void) close (j);
                    375:                return NOTOK;
                    376:            }
                    377:            start = lseek (md, 0L, 1);
                    378: 
                    379:            if (text) {
                    380:                i = strlen (text);
                    381:                if (write (md, text, i) != i)
                    382:                    return NOTOK;
                    383:                for (cp = text; *cp++; size++)
                    384:                    if (*cp == '\n')
                    385:                        size++;
                    386:            }
                    387:                    
                    388:            for (j = 0; fgets (buffer, sizeof buffer, fp) != NULL; j++) {
                    389:                if (j != 0 && strncmp (buffer, "From ", 5) == 0) {
                    390:                    (void) write (fd, ">", 1);
                    391:                    size++;
                    392:                }
                    393:                i = strlen (buffer);
                    394:                if (write (md, buffer, i) != i) {
                    395:                    (void) fclose (fp);
                    396:                    return NOTOK;
                    397:                }
                    398:                if (mapping)
                    399:                    for (cp = buffer; i-- > 0; size++)
                    400:                        if (*cp++ == '\n')
                    401:                            size++;
                    402:            }
                    403: 
                    404:            (void) fclose (fp);
                    405:            (void) lseek (fd, 0L, 2);
                    406:            stop = lseek (md, 0L, 1);
                    407:            if (mapping)
                    408:                (void) map_write (mailbox, md, 0, start, stop, pos, size,
                    409:                            noisy);
                    410: 
                    411:            return OK;
                    412:     }
                    413: }
                    414: 
                    415: /*  */
                    416: 
                    417: int    mbx_size (md, start, stop)
                    418: int    md;
                    419: long   start,
                    420:        stop;
                    421: {
                    422:     register int    i,
                    423:                     fd;
                    424:     register long   pos;
                    425:     register FILE  *fp;
                    426: 
                    427:     if ((fd = dup (md)) == NOTOK || (fp = fdopen (fd, "r")) == NULL) {
                    428:        if (fd != NOTOK)
                    429:            (void) close (fd);
                    430:        return NOTOK;
                    431:     }
                    432: 
                    433:     (void) fseek (fp, start, 0);
                    434:     for (i = 0, pos = stop - start; pos-- > 0; i++)
                    435:        if (fgetc (fp) == '\n')
                    436:            i++;
                    437: 
                    438:     (void) fclose (fp);
                    439: 
                    440:     return i;
                    441: }
                    442: 
                    443: /*  */
                    444: 
                    445: int     mbx_close (mailbox, md)
                    446: char   *mailbox;
                    447: int     md;
                    448: {
                    449:     (void) lkclose (md, mailbox);
                    450: 
                    451:     return OK;
                    452: }
                    453: 
                    454: /*  */
                    455: 
                    456: /* This function is performed implicitly by getbbent.c:
                    457: 
                    458:                bb -> bb_map = map_name (bb -> bb_file);
                    459: */
                    460: 
                    461: char    *map_name (file)
                    462: register char  *file;
                    463: {
                    464:     register char  *cp,
                    465:                    *dp;
                    466:     static char buffer[BUFSIZ];
                    467: 
                    468:     if ((dp = index (cp = r1bindex (file, '/'), '.')) == NULL)
                    469:        dp = cp + strlen (cp);
                    470:     if (cp == file)
                    471:        (void) sprintf (buffer, ".%.*s%s", dp - cp, cp, ".map");
                    472:     else
                    473:        (void) sprintf (buffer, "%.*s.%.*s%s", cp - file, file, dp - cp,
                    474:                cp, ".map");
                    475: 
                    476:     return buffer;
                    477: }
                    478: 
                    479: /*  */
                    480: 
                    481: int    map_read (file, pos, drops, noisy)
                    482: char   *file;
                    483: long   pos;
                    484: struct drop **drops;
                    485: int    noisy;
                    486: {
                    487:     register int    i,
                    488:                     md,
                    489:                     msgp;
                    490:     register char  *cp;
                    491:     struct drop d;
                    492:     register struct drop   *mp,
                    493:                            *dp;
                    494: 
                    495:     if ((md = open (cp = map_name (file), 0)) == NOTOK
                    496:            || map_chk (cp, md, mp = &d, pos, noisy)) {
                    497:        if (md != NOTOK)
                    498:            (void) close (md);
                    499:        return 0;
                    500:     }
                    501: 
                    502:     msgp = mp -> d_id;
                    503:     dp = (struct drop  *) calloc ((unsigned) msgp, sizeof *dp);
                    504:     if (dp == NULL) {
                    505:        (void) close (md);
                    506:        return 0;
                    507:     }
                    508: 
                    509:     (void) lseek (md, (long) sizeof *mp, 0);
                    510:     if ((i = read (md, (char *) dp, msgp * sizeof *dp)) < sizeof *dp) {
                    511:        i = 0;
                    512:        free ((char *) dp);
                    513:     }
                    514:     else
                    515:        *drops = dp;
                    516: 
                    517:     (void) close (md);
                    518: 
                    519:     return (i / sizeof *dp);
                    520: }
                    521: 
                    522: /*  */
                    523: 
                    524: int     map_write (mailbox, md, id, start, stop, pos, size, noisy)
                    525: register char   *mailbox;
                    526: int     md,
                    527:         id,
                    528:        size,
                    529:        noisy;
                    530: long    start,
                    531:         stop,
                    532:         pos;
                    533: {
                    534:     register int    i;
                    535:     int     clear,
                    536:             fd,
                    537:             td;
                    538:     char   *file;
                    539:     register struct drop   *dp;
                    540:     struct drop    d1,
                    541:                   d2,
                    542:                   *rp;
                    543:     register FILE *fp;
                    544: 
                    545:     if ((fd = map_open (file = map_name (mailbox), &clear, md)) == NOTOK)
                    546:        return NOTOK;
                    547: 
                    548:     if (!clear && map_chk (file, fd, &d1, pos, noisy)) {
                    549:        (void) unlink (file);
                    550:        (void) mbx_close (file, fd);
                    551:        if ((fd = map_open (file, &clear, md)) == NOTOK)
                    552:            return NOTOK;
                    553:        clear++;
                    554:     }
                    555: 
                    556:     if (clear) {
                    557:        if ((td = dup (md)) == NOTOK || (fp = fdopen (td, "r")) == NULL) {
                    558:            if (noisy)
                    559:                admonish (file, "unable to %s", td != NOTOK ? "fdopen" : "dup");
                    560:            if (td != NOTOK)
                    561:                (void) close (td);
                    562:            (void) mbx_close (file, fd);
                    563:            return NOTOK;
                    564:        }
                    565: 
                    566:        switch (i = mbx_read (fp, 0L, &rp, noisy)) {
                    567:            case NOTOK:
                    568:                (void) fclose (fp);
                    569:                (void) mbx_close (file, fd);
                    570:                return NOTOK;
                    571: 
                    572:            case OK:
                    573:                break;
                    574: 
                    575:            default:
                    576:                d1.d_id = 0;
                    577:                for (dp = rp; i-- >0; dp++) {
                    578:                    if (dp -> d_start == start)
                    579:                        dp -> d_id = id;
                    580:                    (void) lseek (fd, (long) (++d1.d_id * sizeof *dp), 0);
                    581:                    if (write (fd, (char *) dp, sizeof *dp) != sizeof *dp) {
                    582:                        if (noisy)
                    583:                            admonish (file, "write error");
                    584:                        (void) mbx_close (file, fd);
                    585:                        (void) fclose (fp);
                    586:                        return NOTOK;
                    587:                    }
                    588:                }
                    589:                free ((char *) rp);
                    590:                break;
                    591:        }
                    592:     }
                    593:     else {
                    594:        dp = &d2;
                    595:        dp -> d_id = id;
                    596:        dp -> d_size = size ? size : mbx_size (fd, start, stop);
                    597:        dp -> d_start = start;
                    598:        dp -> d_stop = stop;
                    599:        (void) lseek (fd, (long) (++d1.d_id * sizeof *dp), 0);
                    600:        if (write (fd, (char *) dp, sizeof *dp) != sizeof *dp) {
                    601:            if (noisy)
                    602:                admonish (file, "write error");
                    603:            (void) mbx_close (file, fd);
                    604:            return NOTOK;
                    605:        }
                    606:     }
                    607: 
                    608:     dp = &d1;
                    609:     dp -> d_size = DRVRSN;
                    610:     dp -> d_start = DRMAGIC;
                    611:     dp -> d_stop = lseek (md, 0L, 1);
                    612:     (void) lseek (fd, 0L, 0);
                    613:     if (write (fd, (char *) dp, sizeof *dp) != sizeof *dp) {
                    614:        if (noisy)
                    615:            admonish (file, "write error");
                    616:        (void) mbx_close (file, fd);
                    617:        return NOTOK;
                    618:     }
                    619: 
                    620:     (void) mbx_close (file, fd);
                    621: 
                    622:     return OK;
                    623: }
                    624: 
                    625: /*  */
                    626: 
                    627: static int  map_open (file, clear, md)
                    628: char   *file;
                    629: int    *clear,
                    630:        md;
                    631: {
                    632:     int            mode;
                    633:     struct  stat st;
                    634: 
                    635:     mode = fstat (md, &st) != NOTOK ? (int) (st.st_mode & 0777) : m_gmprot ();
                    636:     return mbx_Xopen (file, st.st_uid, st.st_gid, mode, clear);
                    637: }
                    638: 
                    639: /*  */
                    640: 
                    641: int  map_chk (file, fd, dp, pos, noisy)
                    642: char   *file;
                    643: int     fd,
                    644:        noisy;
                    645: register struct drop *dp;
                    646: long   pos;
                    647: {
                    648:     long    count;
                    649:     struct drop d;
                    650:     register struct drop    *dl;
                    651: 
                    652:     if (read (fd, (char *) dp, sizeof *dp) != sizeof *dp) {
                    653: #ifdef notdef
                    654:        admonish (NULLCP, "%s: missing or partial index", file);
                    655: #endif notdef
                    656:        return NOTOK;
                    657:     }
                    658:     if (dp -> d_size != DRVRSN) {
                    659:        if (noisy)
                    660:            admonish (NULLCP, "%s: version mismatch", file);
                    661:        return NOTOK;
                    662:     }
                    663:     if (dp -> d_start != DRMAGIC) {
                    664:        if (noisy)
                    665:            admonish (NULLCP, "%s: bad magic number", file);
                    666:        return NOTOK;
                    667:     }
                    668:     if (dp -> d_stop != pos) {
                    669:        if (noisy && pos != 0L)
                    670:            admonish (NULLCP,
                    671:                    "%s: pointer mismatch or incomplete index (%ld!=%ld)", 
                    672:                    file, dp -> d_stop, pos);
                    673:        return NOTOK;
                    674:     }
                    675: 
                    676:     if ((long) ((dp -> d_id + 1) * sizeof *dp) != lseek (fd, 0L, 2)) {
                    677:        if (noisy)
                    678:            admonish (NULLCP, "%s: corrupt index(1)", file);
                    679:        return NOTOK;
                    680:     }
                    681: 
                    682:     dl = &d;
                    683:     count = (long) strlen (mmdlm2);
                    684:     (void) lseek (fd, (long) (dp -> d_id * sizeof *dp), 0);
                    685:     if (read (fd, (char *) dl, sizeof *dl) != sizeof *dl
                    686:            || (dl -> d_stop != dp -> d_stop
                    687:                && dl -> d_stop + count != dp -> d_stop)) {
                    688:        if (noisy)
                    689:            admonish (NULLCP, "%s: corrupt index(2)", file);
                    690:        return NOTOK;
                    691:     }
                    692: 
                    693:     return OK;
                    694: }

unix.superglobalmegacorp.com

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