Annotation of 43BSD/contrib/mh/uip/bbl.c, revision 1.1.1.1

1.1       root        1: /* bbl.c - ease the tasks of a BBleader */
                      2: 
                      3: #include "../h/mh.h"
                      4: #include "../zotnet/bboards.h"
                      5: #include <ctype.h>
                      6: #include <pwd.h>
                      7: #include <stdio.h>
                      8: #include <sys/types.h>
                      9: #ifndef        BSD42
                     10: #ifndef        SYS5
                     11: #include <ndir.h>
                     12: #else  SYS5
                     13: #include <dir.h>
                     14: #endif SYS5
                     15: #else  BSD42
                     16: #include <sys/dir.h>
                     17: #endif BSD42
                     18: #include <sys/stat.h>
                     19: 
                     20: /*  */
                     21: 
                     22: static struct swit switches[] = {
                     23: #define        SHELLSW 0
                     24:     "shell program", 0,
                     25: 
                     26: #define        VERBSW  1
                     27:     "verbose", 0,
                     28: #define        NVERBSW 2
                     29:     "noverbose", 0,
                     30: 
                     31: #define        HELPSW  3
                     32:     "help", 4,
                     33: 
                     34:     NULL, NULL
                     35: };
                     36: 
                     37: /*  */
                     38: 
                     39: static int     verbosw = 0;
                     40: 
                     41: static int     sub_ok = 0;
                     42: 
                     43: static char   *bboards = BBOARDS;
                     44: 
                     45: static char   *cwd = NULL;
                     46: 
                     47: static char   *current_folder = NULL;
                     48: 
                     49: static char   *bbfolder = NULL;
                     50: static char    subfolder[BUFSIZ];
                     51: 
                     52: static struct stat bbstat;
                     53: static struct stat substat;
                     54: 
                     55: static char   *shell = "/bin/sh";
                     56: 
                     57: static struct bboard  *bb = NULL;
                     58: 
                     59: 
                     60: #ifdef SYS5
                     61: struct passwd  *getpwnam (), *getpwuid ();
                     62: #endif SYS5
                     63: 
                     64: /*  */
                     65: 
                     66: /* ARGSUSED */
                     67: 
                     68: main (argc, argv)
                     69: int     argc;
                     70: char  **argv;
                     71: {
                     72:     char   *cp,
                     73:           **ap,
                     74:           **argp,
                     75:             buffer[80],
                     76:            *arguments[MAXARGS];
                     77:     struct passwd  *pw;
                     78: 
                     79:     invo_name = r1bindex (argv[0], '/');
                     80:     if ((cp = m_find (invo_name)) != NULL) {
                     81:        ap = brkstring (cp = getcpy (cp), " ", "\n");
                     82:        ap = copyip (ap, arguments);
                     83:     }
                     84:     else
                     85:        ap = arguments;
                     86:     (void) copyip (argv + 1, ap);
                     87:     argp = arguments;
                     88: 
                     89:     if ((shell = getenv ("SHELL")) == NULL)
                     90:        if ((pw = getpwuid (getuid ())) != NULL
                     91:                && pw -> pw_shell
                     92:                && *pw -> pw_shell)
                     93:            shell = getcpy (pw -> pw_shell);
                     94: 
                     95:     if ((pw = getpwnam (bboards)) == NULL)
                     96:        adios (NULLCP, "no entry for ~%s", bboards);
                     97:     if (pw -> pw_uid != geteuid ())
                     98:        adios (NULLCP, "not running setuid to %s", bboards);
                     99: 
                    100:     current_folder = (cp = m_find (pfolder)) ? getcpy (cp) : defalt;
                    101: 
                    102: /*  */
                    103: 
                    104:     while (cp = *argp++) {
                    105:        if (*cp == '-')
                    106:            switch (smatch (++cp, switches)) {
                    107:                case AMBIGSW: 
                    108:                    ambigsw (cp, switches);
                    109:                    done (1);
                    110:                case UNKWNSW: 
                    111:                    adios (NULLCP, "-%s unknown", cp);
                    112:                case HELPSW: 
                    113:                    (void) sprintf (buffer, "%s [+folder] [switches] bboard",
                    114:                            invo_name);
                    115:                    help (buffer, switches);
                    116:                    done (1);
                    117: 
                    118:                case SHELLSW: 
                    119:                    if (!(shell = *argp++) || *shell == '-')
                    120:                        adios (NULLCP, "missing argument to %s", argp[-2]);
                    121:                    continue;
                    122: 
                    123:                case VERBSW: 
                    124:                    verbosw++;
                    125:                    continue;
                    126:                case NVERBSW: 
                    127:                    verbosw = 0;
                    128:                    continue;
                    129:            }
                    130:        if (*cp == '+')
                    131:            if (bbfolder)
                    132:                adios (NULLCP, "only one folder at a time!");
                    133:            else
                    134:                bbfolder = cp;
                    135:        else
                    136:            if (bb != NULL)
                    137:                adios (NULLCP, "only one BBoard a time!");
                    138:            else
                    139:                if ((bb = getbbnam (cp)) == NULL
                    140:                        && (bb = getbbaka (cp)) == NULL)
                    141:                    adios (NULLCP, "no such BBoard as '%s'", cp);
                    142:     }
                    143: 
                    144: /*  */
                    145: 
                    146:     if (!bb)
                    147:        adios (NULLCP, "no BBoard specified");
                    148:     if (!bbfolder)
                    149:        bbfolder = "+bbl";
                    150:     (void) sprintf (subfolder, "%s/arc", bbfolder);
                    151: 
                    152:     if (!m_find ("path"))
                    153:        free (path ("./", TFOLDER));
                    154:     cwd = getcpy (pwd ());
                    155: 
                    156:     process ();
                    157: 
                    158:     m_replace (pfolder, current_folder);
                    159:     m_update ();
                    160: 
                    161:     done (0);
                    162: }
                    163: 
                    164: /*  */
                    165: 
                    166: process () {
                    167:     int     child_id;
                    168:     char    buffer[BUFSIZ];
                    169: 
                    170:     if (!ldrbb (bb) && !ldrchk (bb))
                    171:        return;
                    172: 
                    173:     if (stat (bb -> bb_file, &bbstat) == NOTOK)
                    174:        adios (NULLCP, "no such file as %s", bb -> bb_file);
                    175: 
                    176:     if (stat (bb -> bb_archive, &substat) != NOTOK
                    177:            && substat.st_size > 0)
                    178:        sub_ok++;
                    179: /*  else */
                    180:     substat.st_mode = bbstat.st_mode;/* archive should always match */
                    181:     substat.st_gid = bbstat.st_gid;/* actual bboard mode & gid */
                    182: 
                    183: /* do subfolder first, since you will lose otherwise... */
                    184:     (void) sprintf (buffer, "Remove messages currently in %s? ", subfolder);
                    185:     if (check_folder (subfolder) && getanswer (buffer))
                    186:        rmf (subfolder);
                    187: 
                    188:     (void) sprintf (buffer, "Remove messages currently in %s? ", bbfolder);
                    189:     if (check_folder (bbfolder) && getanswer (buffer))
                    190:        rmf (bbfolder);
                    191: 
                    192:     switch (child_id = fork ()) {
                    193:        case NOTOK: 
                    194:            adios ("fork", "unable to");
                    195: 
                    196:        case OK: 
                    197:            do_child ();        /* NOTREACHED */
                    198: 
                    199:        default: 
                    200:            do_parent (child_id);
                    201:            break;
                    202:     }
                    203: }
                    204: 
                    205: /*  */
                    206: 
                    207: int     check_folder (folder)
                    208: char   *folder;
                    209: {
                    210:     char   *maildir;
                    211:     struct stat st;
                    212:     struct msgs *mp;
                    213: 
                    214:     maildir = m_maildir (folder + 1);
                    215: 
                    216:     if (stat (maildir, &st) == NOTOK)
                    217:        return 0;
                    218: 
                    219:     if ((st.st_mode & S_IFMT) != S_IFDIR)
                    220:        adios (NULLCP, "not a directory '%s'", maildir);
                    221:     check_mode (maildir, (st.st_mode | 0555) & 0777);
                    222: 
                    223:     if (chdir (maildir) == NOTOK)
                    224:        adios (maildir, "unable to change to");
                    225:     if (!(mp = m_gmsg (folder + 1)))
                    226:        adios (NULLCP, "unable to read %s", folder);
                    227: 
                    228:     if (chdir (cwd) == NOTOK)
                    229:        admonish (cwd, "could not change back to");
                    230:     return (mp -> hghmsg != 0);
                    231: }
                    232: 
                    233: /*  */
                    234: 
                    235: do_parent (child_id)
                    236: int     child_id;
                    237: {
                    238:     int     zap = 0;
                    239:     char    buffer[BUFSIZ];
                    240: 
                    241:     if (pidwait (child_id, NOTOK) == NOTOK)
                    242:        done (1);
                    243: 
                    244:     (void) putchar ('\n');
                    245: 
                    246:     (void) check_folder (bbfolder);
                    247:     if (getanswer ("Incorporate changes? "))
                    248:        update (&bbstat, bb -> bb_file, bbfolder, bb -> bb_info, bb -> bb_map);
                    249:     (void) sprintf (buffer, "Remove %s? ", bbfolder);
                    250:     if (getanswer (buffer))
                    251:        zap++;
                    252: 
                    253:     if (check_folder (subfolder)) {
                    254:        if (getanswer ("Update archives? "))
                    255:            update (&substat, bb -> bb_archive, subfolder, NULLCP, NULLCP);
                    256:     (void) sprintf (buffer, "Remove %s? ", subfolder);
                    257:     if (getanswer (buffer))
                    258:        rmf (subfolder);
                    259:     }
                    260:     else
                    261:        if (sub_ok
                    262:                && getanswer ("Remove archives? ")
                    263:                && getanswer ("Are you sure? "))
                    264:            if (unlink (bb -> bb_archive) == NOTOK)
                    265:                admonish (bb -> bb_archive, "unable to remove %s");
                    266:     if (zap)
                    267:        rmf (bbfolder);
                    268: }
                    269: 
                    270: /*  */
                    271: 
                    272: check_mode (dir, mode)
                    273: char   *dir;
                    274: unsigned int    mode;
                    275: {
                    276:     int     child_id;
                    277:     struct stat st;
                    278:     struct direct  *dp;
                    279:     DIR * dd;
                    280: 
                    281:     if (verbosw)
                    282:        fprintf (stderr, "chmod %o %s\n", mode, dir);
                    283: 
                    284:     switch (child_id = fork ()) {
                    285:        case NOTOK: 
                    286:            adios ("fork", "unable to");
                    287: 
                    288:        case OK: 
                    289:            (void) setgid (getgid ());
                    290:            (void) setuid (getuid ());
                    291: 
                    292:            if (chmod (dir, (int) mode) == NOTOK)
                    293:                adios (dir, "unable to change mode of");
                    294:            if (chdir (dir) == NOTOK)
                    295:                adios (dir, "unable to change to");
                    296:            if ((dd = opendir (dir)) == NULL)
                    297:                adios (dir, "unable to read");
                    298:            while (dp = readdir (dd))
                    299:                if (dp -> d_name[0] != '.') {
                    300:                    if (stat (dp -> d_name, &st) == NOTOK) {
                    301:                        admonish (dp -> d_name, "unable to stat");
                    302:                        continue;
                    303:                    }
                    304:                    if (chmod (dp -> d_name, (int) ((st.st_mode | 0444) & 0777))
                    305:                            == NOTOK)
                    306:                        admonish (dp -> d_name, "unable to change mode of");
                    307:                }
                    308:            closedir (dd);
                    309:            done (0);
                    310: 
                    311:        default: 
                    312:            if (pidwait (child_id, OK))
                    313:                done (1);
                    314:            break;
                    315:     }
                    316: }
                    317: 
                    318: /*  */
                    319: 
                    320: /* ARGSUSED */
                    321: 
                    322: update (stp, file, folder, info, map)
                    323: struct stat *stp;
                    324: char   *file,
                    325:        *folder,
                    326:        *info,
                    327:        *map;
                    328: {
                    329:     int     fd;
                    330:     struct stat st;
                    331: 
                    332:     if (stat (file, &st) != NOTOK
                    333:            && st.st_mtime != stp -> st_mtime) {
                    334:        printf ("File '%s' has changed...\n", file);
                    335:        if (getanswer ("Append to it instead? "))
                    336:            goto work;
                    337:        else
                    338:            if (!getanswer ("Still update it? "))
                    339:                return;
                    340:     }
                    341:     if ((fd = creat (file, BBMODE)) == NOTOK)
                    342:        adios (file, "unable to re-create");
                    343:     else {
                    344:        (void) close (fd);
                    345:        if (map)
                    346:            (void) unlink (map);
                    347:     }
                    348: #ifdef notdef
                    349:     if (info)
                    350:        check_info (folder, info);
                    351: #endif notdef
                    352: 
                    353: work: ;
                    354:     pack (folder, file);
                    355:     if (chmod (file, (int) (stp -> st_mode & 0777)) == NOTOK)
                    356:        admonish (file, "unable to change mode of");
                    357:     if (stat (file, &st) != NOTOK && st.st_gid != stp -> st_gid)
                    358:        chgrp (file, stp -> st_gid);
                    359: }
                    360: 
                    361: /*  */
                    362: 
                    363: #ifdef notdef
                    364: check_info (folder, info)
                    365: char   *folder,
                    366:        *info;
                    367: {
                    368:     int     id,
                    369:             state;
                    370:     char   *hdrptr,
                    371:            *maildir,
                    372:            *msgnam,
                    373:             posted[BUFSIZ],
                    374:             name[NAMESZ],
                    375:             buf[BUFSIZ];
                    376:     struct msgs *mp;
                    377:     FILE * fp;
                    378: 
                    379:     if (chdir (maildir = m_maildir (folder + 1)) == NOTOK)
                    380:        adios (maildir, "unable to change to");
                    381: 
                    382:     if (!(mp = m_gmsg (folder + 1)))
                    383:        adios (NULL, "unable to read %s", folder);
                    384:     if (mp -> hghmsg) {
                    385:        if ((fp = fopen (msgnam = m_name (mp -> hghmsg), "r")) == NULL)
                    386:            adios (NULL, "unable to read message %s in %s",
                    387:                    msgnam, folder);
                    388:        id = 0;
                    389:        posted[0] = NULL;
                    390:        for (state = FLD;;) {
                    391:            switch (state = m_getfld (state, name, buf, sizeof buf, fp)) {
                    392:                case FLD: 
                    393:                case FLDEOF: 
                    394:                case FLDPLUS: 
                    395:                    hdrptr = add (buf, NULL);
                    396:                    while (state == FLDPLUS) {
                    397:                        state = m_getfld (state, name, buf, sizeof buf, fp);
                    398:                        hdrptr = add (buf, hdrptr);
                    399:                    }
                    400:                    if (uleq (name, "BBoard-ID")) {
                    401:                        id = atoi (buf);
                    402:                        if (id > 0 && posted[0])
                    403:                            break;
                    404:                    }
                    405:                    if (uleq (name, "BB-Posted")) {
                    406:                        strncpy (posted, buf, sizeof posted - 2);
                    407:                        if (posted[strlen (posted) - 1] == '\n')
                    408:                            posted[strlen (posted) - 1] = NULL;
                    409:                        if (id > 0 && posted[0])
                    410:                            break;
                    411:                    }
                    412:                    continue;
                    413: 
                    414:                default: 
                    415:                    admonish (NULL, "unable to find BBoard-info in message %s",
                    416:                            msgnam);
                    417:                    (void) fclose (fp);
                    418:                    goto no_risk;
                    419:            }
                    420:            break;
                    421:        }
                    422:        (void) fclose (fp);
                    423: 
                    424:        if (verbosw)
                    425:            fprintf (stderr,
                    426:                    "[ Highest message has %s%d and\n\t\t      %s%s ]\n",
                    427:                    "BBoard-ID: ", id, "BB-Posted: ", posted);
                    428: 
                    429:        if ((fp = lkfopen (info, "w")) == NULL)
                    430:            adios (info, "unable to lock and fopen");
                    431:        fprintf (fp, "%d\n%s\n", id, posted);
                    432:        (void) lkfclose (fp, info);
                    433:     }
                    434: 
                    435: no_risk: ;
                    436:     if (chdir (cwd) == NOTOK)
                    437:        admonish (cwd, "could not change back to");
                    438: }
                    439: #endif notdef
                    440: 
                    441: /*  */
                    442: 
                    443: pack (folder, file)
                    444: char   *folder,
                    445:        *file;
                    446: {
                    447:     int     child_id;
                    448: 
                    449:     switch (child_id = fork ()) {
                    450:        case NOTOK: 
                    451:            admonish ("fork", "unable to");
                    452:            return;
                    453: 
                    454:        case OK: 
                    455:            if (verbosw)
                    456:                fprintf (stderr, "pack %s -file %s\n", folder, file);
                    457: 
                    458:            execlp (packproc, r1bindex (packproc, '/'),
                    459:                    folder, "-file", file, NULLCP);
                    460:            fprintf (stderr, "unable to exec ");
                    461:            perror (packproc);
                    462:            _exit (-1);
                    463: 
                    464:        default: 
                    465:            (void) pidXwait (child_id, packproc);
                    466:            break;
                    467:     }
                    468: }
                    469: 
                    470: /*  */
                    471: 
                    472: chgrp (file, gid)
                    473: char   *file;
                    474: short  gid;
                    475: {
                    476:     int     child_id;
                    477:     char    group[BUFSIZ];
                    478: 
                    479:     switch (child_id = fork ()) {
                    480:        case NOTOK: 
                    481:            admonish ("fork", "unable to");
                    482:            return;
                    483: 
                    484:        case OK: 
                    485:            (void) setuid (geteuid ());/* make sure chgrp works */
                    486:            (void) sprintf (group, "%d", gid);
                    487:            if (verbosw)
                    488:                fprintf (stderr, "chgrp %s %s\n", group, file);
                    489: 
                    490:            execlp ("/bin/chgrp", "chgrp", group, file, NULLCP);
                    491:            fprintf (stderr, "unable to exec ");
                    492:            perror ("/bin/chgrp");
                    493:            _exit (-1);
                    494: 
                    495:        default: 
                    496:            (void) pidXwait (child_id, "chgrp");
                    497:            break;
                    498:     }
                    499: }
                    500: 
                    501: /*  */
                    502: 
                    503: rmf (folder)
                    504: char   *folder;
                    505: {
                    506:     int     child_id;
                    507: 
                    508:     switch (child_id = fork ()) {
                    509:        case NOTOK: 
                    510:            admonish ("fork", "unable to");
                    511:            return;
                    512: 
                    513:        case OK: 
                    514:            (void) setgid (getgid ());
                    515:            (void) setuid (getuid ());
                    516:            if (verbosw)
                    517:                fprintf (stderr, "rmf %s\n", folder);
                    518: 
                    519:            execlp (rmfproc, r1bindex (rmfproc, '/'), folder, NULLCP);
                    520:            fprintf (stderr, "unable to exec ");
                    521:            perror (rmfproc);
                    522:            _exit (-1);
                    523: 
                    524:        default: 
                    525:            (void) pidXwait (child_id, rmfproc);
                    526:            break;
                    527:     }
                    528: }
                    529: 
                    530: /*  */
                    531: 
                    532: do_child () {
                    533:     char    buffer[BUFSIZ];
                    534: 
                    535:     (void) setgid (getgid ());         /* become the user, not bboards */
                    536:     (void) setuid (getuid ());
                    537: 
                    538:     inc (bb -> bb_file, bbfolder);
                    539:     if (sub_ok)
                    540:        inc (bb -> bb_archive, subfolder);
                    541: /*  else
                    542:        create the folder */
                    543: 
                    544:     if (verbosw)
                    545:        (void) putchar ('\n');
                    546:     printf ("[ Working folder is %s, Archive folder is %s ]\n",
                    547:            bbfolder, subfolder);
                    548:     printf ("[ Type CTRL-D to finish ]\n");
                    549: 
                    550:     m_replace (pfolder, bbfolder + 1);
                    551:     m_update ();
                    552: 
                    553:     (void) sprintf (buffer, "=> %s: %s", invo_name, bb -> bb_name);
                    554:     execlp (shell, buffer, NULLCP);
                    555:     fprintf (stderr, "unable to exec ");
                    556:     perror (shell);
                    557:     _exit (-1);
                    558: }
                    559: 
                    560: /*  */
                    561: 
                    562: inc (file, folder)
                    563: char   *file,
                    564:        *folder;
                    565: {
                    566:     int     child_id;
                    567: 
                    568:     switch (child_id = fork ()) {
                    569:        case NOTOK: 
                    570:            adios ("fork", "unable to");
                    571: 
                    572:        case OK: 
                    573:            if (verbosw)
                    574:                fprintf (stderr, "inc %s -file %s -silent\n", folder, file);
                    575:            execlp (incproc, r1bindex (incproc, '/'),
                    576:                    folder, "-file", file, "-silent", NULLCP);
                    577:            fprintf (stderr, "unable to exec ");
                    578:            perror (incproc);
                    579:            _exit (-1);
                    580: 
                    581:        default: 
                    582:            if (pidXwait (child_id, incproc))
                    583:                done (1);
                    584:            break;
                    585:     }
                    586: }

unix.superglobalmegacorp.com

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