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

1.1       root        1: /* bbc.c - ZOTnet BBoard checker */
                      2: 
                      3: #include "../h/mh.h"
                      4: #include "../zotnet/bboards.h"
                      5: #include <stdio.h>
                      6: #ifdef BPOP
                      7: #include "../zotnet/mts.h"
                      8: #endif BPOP
                      9: #include <errno.h>
                     10: #include <signal.h>
                     11: #ifndef        sigmask
                     12: #define        sigmask(s)      (1 << ((s) - 1))
                     13: #endif not sigmask
                     14: #include <sys/types.h>
                     15: #include <sys/stat.h>
                     16: #ifdef SIGTSTP
                     17: #include <sys/wait.h>
                     18: #include <sys/time.h>
                     19: #include <sys/resource.h>
                     20: #endif SIGTSTP
                     21: 
                     22: 
                     23: #define        RCFILE  ".bbrc"
                     24: 
                     25: #define        NBB     100
                     26: 
                     27: /*  */
                     28: 
                     29: static struct swit switches[] = {
                     30: #define        TOPICSW 0
                     31:     "topics", 6,
                     32: #define        CHECKSW 1
                     33:     "check", 5,
                     34: #define        READSW  2
                     35:     "read", 4,
                     36: 
                     37: #define        QUIETSW 3
                     38:     "quiet", 4,
                     39: #define        VERBOSW 4
                     40:     "verbose", 4,
                     41: 
                     42: #define ARCHSW 5
                     43:     "archive", 4,
                     44: #define NOARCH  6
                     45:     "noarchive", 3,
                     46: 
                     47: #define        PROTSW  7
                     48:     "protocol", 4,
                     49: #define        NPROTSW 8
                     50:     "noprotocol", 3,
                     51: 
                     52: #define        PROGSW  9
                     53:     "mshproc program", 4,
                     54: 
                     55: #define        RCSW    10
                     56:     "rcfile rcfile", 4,
                     57: #define        NRCSW   11
                     58:     "norcfile", 3,
                     59: 
                     60: #define        FILESW  12
                     61:     "file BBoardsfile", 4,
                     62: #define        USERSW  13
                     63:     "user BBoardsuser", 4,
                     64: 
                     65: #define        HOSTSW  14
                     66:     "host host",
                     67: #ifndef        BPOP
                     68:     -4,
                     69: #else  BPOP
                     70:     4,
                     71: #endif BPOP
                     72: #define        RPOPSW  15
                     73:     "rpop",
                     74: #ifndef        RPOP
                     75:        -4,
                     76: #else  RPOP
                     77:        4,
                     78: #endif RPOP
                     79: #define        NRPOPSW 16
                     80:     "norpop",
                     81: #ifndef        RPOP
                     82:        -6,
                     83: #else  RPOP
                     84:        6,
                     85: #endif RPOP
                     86: 
                     87: #define        HELPSW  17
                     88:     "help", 4,
                     89: 
                     90:     NULL, NULL
                     91: };
                     92: 
                     93: struct bbcount {
                     94:     char   *key;
                     95:     int     count;
                     96:     struct bbcount *left;
                     97:     struct bbcount *right;
                     98: };
                     99: 
                    100: /*  */
                    101: 
                    102: extern int  errno;
                    103: 
                    104: static int  changed = 0;
                    105: static int  quitting = 0;
                    106: 
                    107: static int  archivesw = 0;
                    108: static int  checksw = 0;
                    109: static int  protsw = 1;
                    110: static int  quietsw = 0;
                    111: static int  readsw = 0;
                    112: static int  topicsw = 0;
                    113: static int  verbosw = 0;
                    114: 
                    115: static int  didpop = OK;
                    116: static int  rpop = 1;
                    117: static char *user = BBOARDS;
                    118: static char *host = NULL;
                    119: #ifdef BPOP
                    120: extern char response[];
                    121: 
                    122: char   *getusr(), **getip();
                    123: #endif BPOP
                    124: 
                    125: SIGDECL        sigser();
                    126: int    action();
                    127: #ifdef SIGTSTP
                    128: int    tstpid;
                    129: static SIGDECL tstpser();
                    130: #endif SIGTSTP
                    131: 
                    132: static char *rcfile;
                    133: 
                    134: 
                    135: static struct bbcount  *bbc = NULL;
                    136: static struct bboard   *bbl = NULL;
                    137: 
                    138: struct bbcount *add_count (), *seek_count ();
                    139: struct bboard *getbbaux (), *getbbvis ();
                    140: 
                    141: /*  */
                    142: 
                    143: /* ARGSUSED */
                    144: 
                    145: main(argc, argv)
                    146:        int argc;
                    147:        char **argv;
                    148: {
                    149:     int            bbp = 0,
                    150:            vecp = 1;
                    151:     char   *cp,
                    152:           *rc,
                    153:           **ap,
                    154:           **argp,
                    155:             buffer[80],
                    156:            *arguments[MAXARGS],
                    157:           *bbs[NBB + 1],
                    158:           *vec[MAXARGS];
                    159: 
                    160:     invo_name = r1bindex (argv[0], '/');
                    161: #ifdef BPOP
                    162:     mts_init (invo_name);
                    163:     if (popbbhost && *popbbhost)
                    164:        host = popbbhost;
                    165:     if (popbbuser && *popbbuser)
                    166:        user = popbbuser, rpop = 0;
                    167: #endif BPOP
                    168:     if ((cp = m_find (invo_name)) != NULL) {
                    169:        ap = brkstring (cp = getcpy (cp), " ", "\n");
                    170:        ap = copyip (ap, arguments);
                    171:     }
                    172:     else
                    173:        ap = arguments;
                    174:     (void) copyip (argv + 1, ap);
                    175:     argp = arguments;
                    176: 
                    177:     (void) setbbent (SB_STAY);
                    178: 
                    179: /*  */
                    180: 
                    181:     while (cp = *argp++) {
                    182:        if (*cp == '-')
                    183:            switch (smatch (++cp, switches)) {
                    184:                case AMBIGSW:
                    185:                    ambigsw (cp, switches);
                    186:                    done (1);
                    187:                case UNKWNSW:
                    188:                   vec[vecp++] = --cp;
                    189:                   continue;
                    190:                case HELPSW:
                    191:                    (void) sprintf (buffer,
                    192:                        "%s [bboards ...] [switches] [switches for mshproc]",
                    193:                        invo_name);
                    194:                    help (buffer, switches);
                    195:                    done (1);
                    196: 
                    197:                case TOPICSW:
                    198:                    topicsw++;
                    199:                    checksw = readsw = 0;
                    200:                    continue;
                    201:                case CHECKSW:
                    202:                    checksw++;
                    203:                    readsw = topicsw = 0;
                    204:                    continue;
                    205:                case READSW:
                    206:                    readsw++;
                    207:                    checksw = topicsw = 0;
                    208:                    continue;
                    209: 
                    210:                case ARCHSW:
                    211:                    archivesw++;
                    212:                    continue;
                    213:                case NOARCH:
                    214:                    archivesw = 0;
                    215:                    continue;
                    216: 
                    217:                case PROTSW:
                    218:                    protsw++;
                    219:                    continue;
                    220:                case NPROTSW:
                    221:                    protsw = 0;
                    222:                    continue;
                    223: 
                    224:                case QUIETSW:
                    225:                    quietsw++;
                    226:                    verbosw = 0;
                    227:                    continue;
                    228:                case VERBOSW:
                    229:                    verbosw++;
                    230:                    quietsw = 0;
                    231:                    continue;
                    232: 
                    233:                case PROGSW:
                    234:                    if (!(mshproc = *argp++) || *mshproc == '-')
                    235:                        adios (NULLCP, "missing argument to %s", argp[-2]);
                    236:                    continue;
                    237: 
                    238:                case RCSW:
                    239:                    if (!(rc = *argp++) || *rc == '-')
                    240:                        adios (NULLCP, "missing argument to %s", argp[-2]);
                    241:                    continue;
                    242:                case NRCSW:
                    243:                    rc = NULL;
                    244:                    continue;
                    245: 
                    246:                case FILESW:
                    247:                    if (!(cp = *argp++) || *cp == '-')
                    248:                        adios (NULLCP, "missing argument to %s", argp[-2]);
                    249:                    if (!setbbinfo (user, cp, 1))
                    250:                        adios (NULLCP, "setbbinfo(%s, %s, 1) failed -- %s",
                    251:                                user, cp, getbberr ());
                    252:                    continue;
                    253:                case USERSW:
                    254:                    if (!(user = *argp++) || *user == '-')
                    255:                        adios (NULLCP, "missing argument to %s", argp[-2]);
                    256:                    continue;
                    257: 
                    258:                case HOSTSW:
                    259:                    if (!(host = *argp++) || *host == '-')
                    260:                        adios (NULLCP, "missing argument to %s", argp[-2]);
                    261:                    didpop = NOTOK;
                    262:                    continue;
                    263:                case RPOPSW:
                    264:                    rpop++;
                    265:                    continue;
                    266:                case NRPOPSW:
                    267:                    rpop = 0;
                    268:                    continue;
                    269:            }
                    270:        if (bbp < NBB)
                    271:            bbs[bbp++] = cp;
                    272:        else
                    273:            adios (NULLCP, "too many bboards, starting with %s", cp);
                    274:     }
                    275:     bbs[bbp] = NULL;
                    276: 
                    277: /*  */
                    278: 
                    279: #ifdef BPOP
                    280:     if (!*host)
                    281:        host = NULL, didpop = OK;
                    282:     if (!host || !rpop)
                    283:        (void) setuid (getuid ());
                    284: #endif BPOP
                    285: 
                    286:     if (!m_find ("path"))
                    287:        free (path ("./", TFOLDER));
                    288: 
                    289:     rcinit (rc);
                    290: 
                    291:     for (bbp = 0; cp = bbs[bbp]; bbp++)
                    292:        add_bb (cp, NOTOK);
                    293: 
                    294:     if (topicsw)
                    295:        topics ();
                    296:     else {
                    297:        default_bboards ();
                    298:        if (checksw)
                    299:            check ();
                    300:        else
                    301:            process (vecp, vec);
                    302:     }
                    303: 
                    304: #ifdef BPOP
                    305:     if (didpop != OK && pop_quit () == NOTOK)
                    306:        adios (NULLCP, "%s", response);
                    307: #endif BPOP
                    308: 
                    309:     done (0);
                    310: }
                    311: 
                    312: /*  */
                    313: 
                    314: topics()
                    315: {
                    316:     register char  *cp,
                    317:                   **ap;
                    318:     register struct bboard *bb;
                    319: 
                    320:     printf ("%16s %s   %s\n", "BBoard", "Items",
                    321:            verbosw ? "Interesting Facts" : "Last Update");
                    322:     printf ("%16s %s   %s\n", "------", "-----",
                    323:            verbosw ? "-----------------" : "-----------");
                    324: 
                    325:     for (bb = bbl ? bbl : getbbvis ();
                    326:            bb;
                    327:            bb = bbl ? bb -> bb_link : getbbvis ()) {
                    328:        printf ("%16s %5d   %s\n",
                    329:                bb -> bb_name, bb -> bb_maxima, bb -> bb_date);
                    330:        if (verbosw) {
                    331:            if (*bb -> bb_aka) {
                    332:                cp = NULL;
                    333:                for (ap = bb -> bb_aka; *ap; ap++)
                    334:                    cp = add (*ap, cp ? add (", ", cp) : cp);
                    335:                printv ("AKA", cp);
                    336:                free (cp);
                    337:            }
                    338: 
                    339:            printv ("Leaders", *bb -> bb_leader);
                    340:            for (ap = bb -> bb_leader + 1; *ap; ap++)
                    341:                printv (NULLCP, *ap);
                    342:            printv ("File", bb -> bb_file);
                    343:            printv ("Archive", bb -> bb_archive);
                    344:            printv ("Info", bb -> bb_info);
                    345:            printv ("Map", bb -> bb_map);
                    346:            printv ("Password", bb -> bb_passwd);
                    347:            if (strcmp (bb -> bb_name, bb -> bb_addr))
                    348:                printv ("Address", bb -> bb_addr);
                    349:            if (strcmp (*bb -> bb_leader, bb -> bb_request))
                    350:                printv ("Request", bb -> bb_request);
                    351:            if (*bb -> bb_relay)
                    352:                printv ("Relay", bb -> bb_relay);
                    353:            if (*bb -> bb_dist) {
                    354:                changed = 0;
                    355:                (void) getbbdist (bb, action);
                    356:                if (!changed)
                    357:                    printv ("Dist", "");
                    358:                if (cp = getbberr ())
                    359:                    printv ("Error", cp);
                    360:            }
                    361:            printb (bb -> bb_flags);
                    362:        }
                    363:     }
                    364: }
                    365: 
                    366: /*  */
                    367: 
                    368: printv(key, value)
                    369:        register char *key, *value;
                    370: {
                    371:     char    buffer[BUFSIZ];
                    372: 
                    373:     if (key)
                    374:        (void) sprintf (buffer, "%s: ", key);
                    375:     else
                    376:        buffer[0] = '\0';
                    377:     printf ("%*s%-*s", 25, "", 10, buffer);
                    378:     if (value && *value)
                    379:        printf ("%s", value);
                    380:     (void) putchar ('\n');
                    381: }
                    382: 
                    383: action(local, domain)
                    384:        register char *local, *domain;
                    385: {
                    386:     char    buffer[BUFSIZ];
                    387: 
                    388:     (void) sprintf (buffer, "%s@%s", local, domain);
                    389:     printv (changed++ ? NULL : "Dist", buffer);
                    390:     return 0;
                    391: }
                    392: 
                    393: 
                    394: printb(flags)
                    395:        unsigned int flags;
                    396: {
                    397:     char buffer[BUFSIZ];
                    398: 
                    399:     printv ("Flags", sprintb (buffer, flags, BBITS));
                    400: }
                    401: 
                    402: /*  */
                    403: 
                    404: check()
                    405: {
                    406: #define        grammar(a,b,c)  (a == 1 ? b : c)
                    407: #define        plural(d)       grammar(d, "", "s")
                    408: 
                    409:     int     diff;
                    410:     register struct bboard  *bb;
                    411: 
                    412:     for (bb = bbl; bb; bb = bb -> bb_link) {
                    413:        diff = bb -> bb_maxima - bb -> bb_count;
                    414:        if (quietsw) {
                    415:            if (diff > 0)
                    416:                printf ("%s -- %d item%s unseen\n",
                    417:                        bb -> bb_name, diff, plural (diff));
                    418:        }
                    419:        else
                    420:            if (bb -> bb_maxima == 0)
                    421:                printf ("%s -- empty\n", bb -> bb_name);
                    422:            else
                    423:                if (bb -> bb_count == 0)
                    424:                    printf ("%s -- %d item%sseen)\n",
                    425:                            bb -> bb_name, bb -> bb_maxima,
                    426:                            grammar (bb -> bb_maxima, " (un", "s (none "));
                    427:                else
                    428:                    if (diff <= 0)
                    429:                        printf ("%s -- %d item%s (all seen)\n",
                    430:                                bb -> bb_name, bb -> bb_maxima,
                    431:                                plural (bb -> bb_maxima));
                    432:                    else
                    433:                        printf ("%s -- %d item%s unseen\n",
                    434:                                bb -> bb_name, diff, plural (diff));
                    435:     }
                    436: }
                    437: 
                    438: /*  */
                    439: 
                    440: process(vecp, vec)
                    441:        int vecp;
                    442:        char *vec[];
                    443: {
                    444:     int     diff;
                    445: #ifdef SIGTSTP
                    446:     SIGDECL (*tstat)();
                    447: #endif SIGTSTP
                    448:     register struct bboard *bb;
                    449: 
                    450:     vec[0] = r1bindex (mshproc, '/');
                    451: #ifdef SIGTSTP
                    452:     tstat = signal (SIGTSTP, tstpser);
                    453: #endif SIGTSTP
                    454: 
                    455:     for (bb = bbl; bb && !quitting; bb = bb -> bb_link) {
                    456:        diff = bb -> bb_maxima - bb -> bb_count;
                    457:        if (bb -> bb_maxima == 0) {
                    458:            if (!quietsw)
                    459:                printf ("%s -- empty\n", bb -> bb_name);
                    460:            continue;
                    461:        }
                    462:        else
                    463:            if (verbosw || archivesw || diff > 0)
                    464:                bbread (bb, vecp, vec);
                    465:            else
                    466:                if (!quietsw)
                    467:                    printf ("%s -- %d item%s (all seen)\n",
                    468:                            bb -> bb_name, bb -> bb_maxima,
                    469:                            plural (bb -> bb_maxima));
                    470: 
                    471:     };
                    472: 
                    473: #ifdef SIGTSTP
                    474:     (void) signal (SIGTSTP, tstat);
                    475: #endif SIGTSTP
                    476:     rcend ();
                    477: }
                    478: 
                    479: /*  */
                    480: 
                    481: #ifdef BPOP
                    482: /* ARGSUSED */
                    483: 
                    484: static int
                    485: xtnd1(s)
                    486:        char *s;
                    487: {
                    488:     return OK;
                    489: }
                    490: #endif BPOP
                    491: 
                    492: /*  */
                    493: 
                    494: bbread(bb, vecp, vec)
                    495:        register struct bboard *bb;
                    496:        int vecp;
                    497:        char *vec[];
                    498: {
                    499:     int     child_id,
                    500:             pd[2];
                    501:     char    buf1[BUFSIZ],
                    502:             buf2[BUFSIZ],
                    503:             buf3[BUFSIZ];
                    504: #ifdef BPOP
                    505:     int            nmsgs,
                    506:            nbytes;
                    507:     char    buf4[BUFSIZ],
                    508:             buf5[BUFSIZ];
                    509: #endif BPOP
                    510:     struct stat st;
                    511: 
                    512: #ifdef BPOP
                    513:     if (bb -> bb_flags & BB_REMOTE) {
                    514:        if (pop_xtnd (xtnd1, "%s %s", archivesw ? "archive" : "bboards",
                    515:                        bb -> bb_name) == NOTOK) {
                    516:            advise (NULLCP, "%s", response);
                    517:            return;
                    518:        }
                    519:        if (pop_stat (&nmsgs, &nbytes) == NOTOK)
                    520:            adios (NULLCP, "%s", response);
                    521:        if (nmsgs == 0)
                    522:            return;
                    523:        if (pop_fd (buf4, buf5) == NOTOK)
                    524:            adios (NULLCP, "%s", response);
                    525:     }
                    526:     else
                    527: #endif BPOP
                    528:     if (stat (archivesw ? bb -> bb_archive : bb -> bb_file, &st) != NOTOK
                    529:            && st.st_size == 0)
                    530:        return;
                    531: 
                    532:     if (protsw) {
                    533:        if (pipe (pd) == NOTOK)
                    534:            adios ("pipe", "unable to");
                    535:        (void) sprintf (buf3, "%d", getpid ());
                    536:     }
                    537: 
                    538:     switch (child_id = fork ()) {
                    539:        case NOTOK:
                    540:            adios ("fork", "unable to");
                    541: 
                    542:        case OK:
                    543:            if (protsw) {
                    544:                (void) close (pd[0]);
                    545:                (void) sprintf (buf1, "%d", bb -> bb_count + 1);
                    546:                (void) sprintf (buf2, "%d", pd[1]);
                    547:                vec[vecp++] = "-idname";
                    548:                vec[vecp++] = bb -> bb_name;
                    549:                vec[vecp++] = "-idstart";
                    550:                vec[vecp++] = buf1;
                    551:                vec[vecp++] = "-idstop";
                    552:                vec[vecp++] = buf2;
                    553:                vec[vecp++] = "-idquit";
                    554:                vec[vecp++] = buf3;
                    555:            }
                    556: #ifdef BPOP
                    557:            if (bb -> bb_flags & BB_REMOTE) {
                    558:                vec[vecp++] = "-popread";
                    559:                vec[vecp++] = buf4;
                    560:                vec[vecp++] = "-popwrite";
                    561:                vec[vecp++] = buf5;
                    562:            }
                    563: #endif BPOP
                    564:            vec[vecp++] = archivesw ? bb -> bb_archive : bb -> bb_file;
                    565:            vec[vecp] = NULL;
                    566:            execvp (mshproc, vec);
                    567:            fprintf (stderr, "unable to exec ");
                    568:            perror (mshproc);
                    569:            _exit (-1);
                    570: 
                    571:        default:
                    572: #ifdef SIGTSTP
                    573:            tstpid = child_id;
                    574: #endif SIGTSTP
                    575:            if (protsw) {
                    576:                (void) close (pd[1]);
                    577:                pgmread (pd[0], child_id, bb);
                    578:            }
                    579:            else
                    580:                (void) pidXwait (child_id, mshproc);
                    581:     }
                    582: }
                    583: 
                    584: /*  */
                    585: 
                    586: pgmread(pd, child_id, bb)
                    587:        int pd, child_id;
                    588:        register struct bboard  *bb;
                    589: {
                    590:     int     i,
                    591:             j,
                    592:             n;
                    593:     SIGDECL (*estat)(), (*hstat)(), (*istat)(), (*qstat)(), (*tstat)();
                    594:     char    buffer[BUFSIZ];
                    595:     struct bbcount *selected;
                    596: 
                    597:     estat = signal (SIGEMT, sigser);
                    598:     hstat = signal (SIGHUP, SIG_IGN);
                    599:     istat = signal (SIGINT, SIG_IGN);
                    600:     qstat = signal (SIGQUIT, SIG_IGN);
                    601:     tstat = signal (SIGTERM, sigser);
                    602: 
                    603:     while ((n = read (pd, buffer, sizeof buffer)) == NOTOK && errno == EINTR)
                    604:        continue;
                    605:     (void) close (pd);
                    606:     (void) pidXwait (child_id, mshproc);
                    607: 
                    608:     (void) signal (SIGEMT, estat);
                    609:     (void) signal (SIGHUP, hstat);
                    610:     (void) signal (SIGINT, istat);
                    611:     (void) signal (SIGQUIT, qstat);
                    612:     (void) signal (SIGTERM, tstat);
                    613: 
                    614:     if (n <= 0)
                    615:        return;
                    616:     if (sscanf (buffer, "%d %d", &i, &j) != 2 || i <= 0 || j <= 0)
                    617:        return;
                    618: 
                    619:     if ((selected = seek_count (bbc, bb -> bb_name)) == NULL) {
                    620:        bbc = add_count (bbc, bb -> bb_name, i);
                    621:        changed++;
                    622:     }
                    623:     else
                    624:        if (archivesw) {
                    625:            if (i > selected -> count) {
                    626:                selected -> count = i;
                    627:                changed++;
                    628:            }
                    629:        }
                    630:        else {
                    631:            if (bb -> bb_maxima > j && i >= j)/* bbl... */
                    632:                i = bb -> bb_maxima;
                    633:            if (i != selected -> count) {
                    634:                selected -> count = i;
                    635:                changed++;
                    636:            }
                    637:        }
                    638: }
                    639: 
                    640: 
                    641: /* ARGSUSED */
                    642: 
                    643: SIGDECL
                    644: sigser(i)
                    645:        int i;
                    646: {
                    647: #ifndef        BSD42
                    648:     (void) signal (i, sigser);
                    649: #endif not BSD42
                    650:     quitting++;
                    651: }
                    652: 
                    653: /*  */
                    654: 
                    655: rcinit(rc)
                    656:        register char *rc;
                    657: {
                    658:     int     state;
                    659:     register char  *cp;
                    660:     char    key[NAMESZ],
                    661:             value[BUFSIZ];
                    662:     register FILE  *bbrc;
                    663: 
                    664:     if ((cp = rc ? rc : getenv ("MHBBRC")) && *cp) {
                    665:        rcfile = path (cp, TFILE);
                    666:        if (*cp != '/')
                    667:            (void) putenv ("MHBBRC", rcfile);
                    668:     }
                    669:     else
                    670:        rcfile = concat (mypath, "/", RCFILE, NULLCP);
                    671: 
                    672:     if ((bbrc = fopen (rcfile, "r")) == NULL)
                    673:        if (cp && *cp)
                    674:            adios (rcfile, "unable to read");
                    675:        else
                    676:            return;
                    677: 
                    678:     for (state = FLD;;) {
                    679:        switch (state = m_getfld (state, key, value, sizeof value, bbrc)) {
                    680:            case FLD:
                    681:            case FLDEOF:
                    682:                make_lower (key, key);
                    683:                bbc = add_count (bbc, key, atoi (value));
                    684:                if (state == FLDEOF)
                    685:                    break;
                    686:                continue;
                    687: 
                    688:            default:
                    689:                admonish (NULLCP, "bad format: %s", rcfile);
                    690:            case FILEEOF:
                    691:                break;
                    692:        }
                    693: 
                    694:        break;
                    695:     }
                    696: 
                    697:     if (ferror (bbrc))
                    698:        admonish (rcfile, "error reading");
                    699:     (void) fclose (bbrc);
                    700: }
                    701: 
                    702: /*  */
                    703: 
                    704: rcend()
                    705: {
                    706:     SIGDECL (*hstat)(), (*istat)(), (*qstat)(), (*tstat)();
                    707:     register FILE *bbrc;
                    708: 
                    709:     if (!changed)
                    710:        return;
                    711: 
                    712:     hstat = signal (SIGHUP, SIG_IGN);
                    713:     istat = signal (SIGINT, SIG_IGN);
                    714:     qstat = signal (SIGQUIT, SIG_IGN);
                    715:     tstat = signal (SIGTERM, SIG_IGN);
                    716: 
                    717:     if ((bbrc = fopen (rcfile, "w")) == NULL)
                    718:        adios (rcfile, "unable to write");
                    719:     rcput (bbrc, bbc);
                    720: 
                    721:     if (ferror (bbrc))
                    722:        adios (rcfile, "error writing");
                    723:     (void) fclose (bbrc);
                    724: 
                    725:     (void) signal (SIGHUP, hstat);
                    726:     (void) signal (SIGINT, istat);
                    727:     (void) signal (SIGQUIT, qstat);
                    728:     (void) signal (SIGTERM, tstat);
                    729: 
                    730:     changed = 0;
                    731: }
                    732: 
                    733: rcput(bbrc, p)
                    734:        register FILE *bbrc;
                    735:        register struct bbcount *p;
                    736: {
                    737:     if (p == NULL)
                    738:        return;
                    739: 
                    740:     fprintf (bbrc, "%s: %d\n", p -> key, p -> count);
                    741:     rcput (bbrc, p -> left);
                    742:     rcput (bbrc, p -> right);
                    743: }
                    744: 
                    745: /*  */
                    746: 
                    747: #ifdef SIGTSTP
                    748: static SIGDECL
                    749: tstpser(sig)
                    750:        int sig;
                    751: {
                    752:     int            pid;
                    753:     union wait w;
                    754: 
                    755:     rcend ();
                    756: 
                    757:     while ((pid = wait3 (&w, WUNTRACED, (struct rusage *) 0)) != NOTOK
                    758:            && pid != tstpid)
                    759:        continue;
                    760: 
                    761:     (void) signal (SIGTSTP, SIG_DFL);
                    762: #ifdef BSD42
                    763:     (void) sigsetmask (sigblock (0) & ~sigmask (SIGTSTP));
                    764: #endif BSD42
                    765: 
                    766:     (void) kill (getpid (), sig);
                    767: 
                    768: #ifdef BSD42
                    769:     (void) sigblock (sigmask (SIGTSTP));
                    770: #endif BSD42
                    771:     (void) signal (SIGTSTP, tstpser);
                    772: }
                    773: #endif SIGTSTP
                    774: 
                    775: /*  */
                    776: 
                    777: struct bbcount *
                    778: add_count(p, w, i)
                    779:        register struct bbcount *p;
                    780:        register char *w;
                    781:        int i;
                    782: {
                    783:     int     cond;
                    784: 
                    785:     if (p == NULL) {
                    786:        p = (struct bbcount *) malloc (sizeof *p);
                    787:        if (p == NULL)
                    788:            adios (NULLCP,"insufficient memory");
                    789:        p -> key = getcpy (w);
                    790:        p -> count = i;
                    791:        p -> left = p -> right = NULL;
                    792:     }
                    793:     else
                    794:        if ((cond = strcmp (w, p -> key)) < 0)
                    795:            p -> left = add_count (p -> left, w, i);
                    796:        else
                    797:            if (cond > 0)
                    798:                p -> right = add_count (p -> right, w, i);
                    799: 
                    800:     return p;
                    801: }
                    802: 
                    803: struct bbcount *
                    804: seek_count(p, w)
                    805:        register struct bbcount *p;
                    806:        register char *w;
                    807: {
                    808:     int     cond;
                    809: 
                    810:     if (p == NULL || (cond = strcmp (w, p -> key)) == 0)
                    811:        return p;
                    812:     else
                    813:        return seek_count (cond < 0 ? p -> left : p -> right, w);
                    814: }
                    815: 
                    816: /*  */
                    817: 
                    818: default_bboards()
                    819: {
                    820:     register char  *cp,
                    821:                   **ap;
                    822: 
                    823:     if (bbl != NULL)
                    824:        return;
                    825: 
                    826:     if (!archivesw && ((cp = m_find ("bboards")) != NULL)) {
                    827: #ifndef        BPOP
                    828:        for (ap = brkstring (cp = getcpy (cp), " ", "\n"); *ap; ap++)
                    829: #else  BPOP
                    830:        for (ap = getip (cp); *ap; ap++)
                    831: #endif BPOP
                    832:            add_bb (*ap, OK);
                    833: #ifndef        BPOP
                    834:        free (cp);
                    835: #endif not BPOP
                    836:     }
                    837:     else
                    838:        add_bb ("system", NOTOK);
                    839: 
                    840:     if (bbl == NULL)
                    841:        done (1);
                    842: }
                    843: 
                    844: /*  */
                    845: 
                    846: add_bb(s, hush)
                    847:        register char *s;
                    848:        int hush;
                    849: {
                    850:     register struct bboard  *bb;
                    851:     static struct bboard   *tail = NULL;
                    852: 
                    853:     make_lower (s, s);
                    854:     if ((bb = getbbaux (s)) == NULL)
                    855:        if (hush == OK)
                    856:            return;
                    857:        else
                    858:            adios (NULLCP, "no such bboard as '%s'", s);
                    859: 
                    860:     if (tail != NULL)
                    861:        tail -> bb_link = bb;
                    862:     if (bbl == NULL)
                    863:        bbl = bb;
                    864:     tail = bb;
                    865: }
                    866: 
                    867: /*  */
                    868: 
                    869: #ifdef BPOP
                    870: static struct bboard   *Bhead = NULL;
                    871: static struct bboard   *Btail = NULL;
                    872: 
                    873: static int
                    874: xtnd2(s)
                    875:        char *s;
                    876: {
                    877:     int     maxima;
                    878:     char    name[BUFSIZ];
                    879:     register struct bboard *bb;
                    880: 
                    881:     if (sscanf (s, "%s %d", name, &maxima) != 2)
                    882:        adios (NULLCP, "XTND2 botch: %s", s);
                    883: 
                    884:     if ((bb = (struct bboard   *) calloc (1, sizeof *bb)) == NULL)
                    885:        adios (NULLCP, "insufficient memory");
                    886:     bb -> bb_name = getcpy (name);
                    887:     if ((bb -> bb_aka = (char **) calloc (1, sizeof *bb -> bb_aka)) == NULL)
                    888:        adios (NULLCP, "insufficient memory");
                    889:     *bb -> bb_aka = NULL;
                    890:     bb -> bb_file = bb -> bb_archive = bb -> bb_info = bb -> bb_map = "";
                    891:     bb -> bb_passwd = "";
                    892:     if ((bb -> bb_leader = (char **) calloc (1, sizeof *bb -> bb_leader))
                    893:            == NULL)
                    894:        adios (NULLCP, "insufficient memory");
                    895:     *bb -> bb_leader = NULL;
                    896:     bb -> bb_addr = bb -> bb_request = bb -> bb_relay = "";
                    897:     if ((bb -> bb_dist = (char **) calloc (1, sizeof *bb -> bb_dist)) == NULL)
                    898:        adios (NULLCP, "insufficient memory");
                    899:     *bb -> bb_dist = NULL;
                    900:     bb -> bb_flags = BB_REMOTE;
                    901:     bb -> bb_count = 0;
                    902:     bb -> bb_maxima = maxima;
                    903:     bb -> bb_date = "";
                    904:     bb -> bb_next = bb -> bb_link = bb -> bb_chain = NULL;
                    905: 
                    906:     if (Btail != NULL)
                    907:        Btail -> bb_chain = bb;
                    908:     if (Bhead == NULL)
                    909:        Bhead = bb;
                    910:     Btail = bb;
                    911: 
                    912:     return OK;
                    913: }
                    914: 
                    915: /*  */
                    916: 
                    917: static int
                    918: xtnd3(s)
                    919:        char *s;
                    920: {
                    921:     static int  bbs = 0;
                    922:     static struct bboard   *bb;
                    923: 
                    924:     switch (bbs++) {
                    925:        case 0:
                    926:            for (bb = Bhead; bb; bb = bb -> bb_chain)
                    927:                if (strcmp (bb -> bb_name, s) == 0)
                    928:                    break;
                    929:            if (bb == NULL)
                    930:                adios (NULLCP, "XTND3 botch");
                    931: 
                    932:            free (bb -> bb_name);
                    933:            bb -> bb_name = getcpy (s);
                    934:            break;
                    935:        case 1:
                    936:            if (bb -> bb_aka)
                    937:                free ((char *) bb -> bb_aka);
                    938:            bb -> bb_aka = getip (s);
                    939:            break;
                    940:        case 2:
                    941:            bb -> bb_file = getcpy (s);
                    942:            break;
                    943:        case 3:
                    944:            bb -> bb_archive = getcpy (s);
                    945:            break;
                    946:        case 4:
                    947:            bb -> bb_info = getcpy (s);
                    948:            break;
                    949:        case 5:
                    950:            bb -> bb_map = getcpy (s);
                    951:            break;
                    952:        case 6:
                    953:            bb -> bb_passwd = getcpy (s);
                    954:            break;
                    955:        case 7:
                    956:            if (bb -> bb_leader)
                    957:                free ((char *) bb -> bb_leader);
                    958:            bb -> bb_leader = getip (s);
                    959:            break;
                    960:        case 8:
                    961:            bb -> bb_addr = getcpy (s);
                    962:            break;
                    963:        case 9:
                    964:            bb -> bb_request = getcpy (s);
                    965:            break;
                    966:        case 10:
                    967:            bb -> bb_relay = getcpy (s);
                    968:            break;
                    969:        case 11:
                    970:            if (bb -> bb_dist)
                    971:                free ((char *) bb -> bb_dist);
                    972:            bb -> bb_dist = getip (s);
                    973:            break;
                    974:        case 12:
                    975:            bb -> bb_flags = bb -> bb_maxima = 0;
                    976:            (void) sscanf (s, "%o %d", &bb -> bb_flags, &bb -> bb_maxima);
                    977:            bb -> bb_flags |= BB_REMOTE;
                    978:            break;
                    979:        case 13:
                    980:            bb -> bb_date = getcpy (s);
                    981:            bbs = 0;
                    982:            break;
                    983:     }
                    984: 
                    985:     return OK;
                    986: }
                    987: 
                    988: 
                    989: static char **
                    990: getip(s)
                    991:        char *s;
                    992: {
                    993:     register char **ap,
                    994:                   **p,
                    995:                   **q;
                    996: 
                    997:     for (p = ap = brkstring (getcpy (s), " ", "\n"); *p; p++)
                    998:        continue;
                    999: 
                   1000:     q = (char **) calloc ((unsigned) (p - ap + 1), sizeof *q);
                   1001:     if (q == NULL)
                   1002:        adios (NULLCP, "insufficient memory");
                   1003: 
                   1004:     for (p = ap, ap = q; *p; *q++ = *p++)
                   1005:        continue;
                   1006:     *q = NULL;
                   1007: 
                   1008:     return ap;
                   1009: }
                   1010: 
                   1011: /*  */
                   1012: 
                   1013: static struct bboard *rover = NULL;
                   1014: 
                   1015: struct bboard *
                   1016: getbbpop()
                   1017: {
                   1018:     int     snoop;
                   1019:     char   *cp,
                   1020:            *pass = NULL;
                   1021:     register struct bboard *bb;
                   1022: 
                   1023:     if (didpop != NOTOK && ((bb = getbbent ()) || !host))
                   1024:        return bb;
                   1025: 
                   1026:     if (Bhead == NULL) {
                   1027:        snoop = (cp = getenv ("MHPOPDEBUG")) && *cp;
                   1028:        if (rpop) {
                   1029:            if (user == NULL)
                   1030:                user = getusr ();
                   1031:            pass = getusr ();
                   1032:        }
                   1033:        else
                   1034:            if (strcmp (user, popbbuser) == 0)
                   1035:                pass = user;
                   1036:            else
                   1037:                ruserpass (host, &user, &pass);
                   1038:        if (didpop != NOTOK)
                   1039:            didpop = DONE;
                   1040: 
                   1041:        if (pop_init (host, user, pass, snoop, rpop) == NOTOK)
                   1042:            adios (NULLCP, "%s", response);
                   1043:        if (rpop)
                   1044:            (void) setuid (getuid ());
                   1045:        if (pop_xtnd (xtnd2, "bboards") == NOTOK)
                   1046:            adios (NULLCP, "%s", response);
                   1047:        if (topicsw && verbosw) /* could optimize here */
                   1048:            for (bb = Bhead; bb; bb = bb -> bb_chain)
                   1049:                if (pop_xtnd (xtnd3, "x-bboards %s", bb -> bb_name) == NOTOK)
                   1050:                    adios (NULLCP, "%s", response);
                   1051:        rover = Bhead;
                   1052:     }
                   1053: 
                   1054:     if (bb = rover)
                   1055:        rover = rover -> bb_chain;
                   1056:     return bb;
                   1057: }
                   1058: 
                   1059: #define        getbbent        getbbpop
                   1060: #endif BPOP
                   1061: 
                   1062: /*  */
                   1063: 
                   1064: struct bboard *
                   1065: getbbaux(s)
                   1066:        register char *s;
                   1067: {
                   1068: #ifdef BPOP
                   1069:     int            nlatch = host ? 1 : 0;
                   1070: #endif BPOP
                   1071:     register char  **ap;
                   1072:     register struct bbcount *selected;
                   1073:     register struct bboard *bb;
                   1074:     static struct bboard   *head = NULL,
                   1075:                            *tail = NULL;
                   1076: 
                   1077:     for (bb = head; bb; bb = bb -> bb_next) {
                   1078:        if (strcmp (bb -> bb_name, s) == 0)
                   1079:            return bb;
                   1080:        for (ap = bb -> bb_aka; *ap; ap++)
                   1081:            if (strcmp (*ap, s) == 0)
                   1082:                return bb;
                   1083:     }
                   1084: 
                   1085: #ifdef BPOP
                   1086: one_more_time: ;
                   1087: #endif BPOP
                   1088:     while (bb = getbbent ()) {
                   1089:        if ((selected = seek_count (bbc, bb -> bb_name)) != NULL)
                   1090:            bb -> bb_count = selected -> count;
                   1091: 
                   1092: #ifdef BPOP
                   1093:        if (!(bb -> bb_flags & BB_REMOTE))
                   1094: #endif BPOP
                   1095:        if ((bb = getbbcpy (bb)) == NULL)
                   1096:            adios (NULLCP, "insufficient memory");
                   1097:        if (tail != NULL)
                   1098:            tail -> bb_next = bb;
                   1099:        if (head == NULL)
                   1100:            head = bb;
                   1101:        tail = bb;
                   1102: 
                   1103:        if (strcmp (bb -> bb_name, s) == 0)
                   1104:            return bb;
                   1105:        for (ap = bb -> bb_aka; *ap; ap++)
                   1106:            if (strcmp (*ap, s) == 0)
                   1107:                return bb;
                   1108:     }
                   1109: 
                   1110: #ifdef BPOP
                   1111:     if (nlatch && pop_xtnd (xtnd2, "bboards %s", s) != NOTOK) {
                   1112:        rover = Bhead;
                   1113:        nlatch = 0;
                   1114:        goto one_more_time;
                   1115:     }
                   1116: #endif BPOP
                   1117: 
                   1118:     return NULL;
                   1119: }
                   1120: 
                   1121: struct bboard *
                   1122: getbbvis()
                   1123: {
                   1124:     register struct bboard *bb;
                   1125: 
                   1126:     while (bb = getbbent ())
                   1127:        if (!(bb -> bb_flags & BB_INVIS)
                   1128:                && (access (bb -> bb_file, 04) != NOTOK || errno != EACCES))
                   1129:            break;
                   1130: 
                   1131:     return bb;
                   1132: }

unix.superglobalmegacorp.com

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