Changeset 1692 for zzuf/trunk/src


Ignore:
Timestamp:
Jan 17, 2007, 8:48:23 PM (13 years ago)
Author:
Sam Hocevar
Message:
  • Reorganised code, got rid of global variables.
Location:
zzuf/trunk/src
Files:
2 added
2 edited

Legend:

Unmodified
Added
Removed
  • zzuf/trunk/src/Makefile.am

    r1683 r1692  
    44
    55bin_PROGRAMS = zzuf
    6 zzuf_SOURCES = zzuf.c $(COMMON) md5.c md5.h timer.c timer.h
     6zzuf_SOURCES = zzuf.c $(COMMON) opts.c opts.h md5.c md5.h timer.c timer.h
    77zzuf_CFLAGS = -DLIBDIR=\"$(libdir)/zzuf\"
    88zzuf_LDFLAGS = @MATH_LIBS@
  • zzuf/trunk/src/zzuf.c

    r1681 r1692  
    3939
    4040#include "libzzuf.h"
     41#include "opts.h"
    4142#include "random.h"
    4243#include "fd.h"
     
    4546#include "timer.h"
    4647
    47 static void loop_stdin(void);
    48 
    49 static void spawn_children(void);
    50 static void clean_children(void);
    51 static void read_children(void);
     48static void loop_stdin(struct opts *opts);
     49
     50static void spawn_children(struct opts *opts);
     51static void clean_children(struct opts *opts);
     52static void read_children(struct opts *opts);
    5253
    5354static char const *sig2str(int);
     
    6061#endif
    6162
    62 static struct child_list
    63 {
    64     enum status
    65     {
    66         STATUS_FREE,
    67         STATUS_RUNNING,
    68         STATUS_SIGTERM,
    69         STATUS_SIGKILL,
    70         STATUS_EOF,
    71     } status;
    72 
    73     pid_t pid;
    74     int fd[3]; /* 0 is debug, 1 is stderr, 2 is stdout */
    75     int bytes, seed;
    76     double ratio;
    77     int64_t date;
    78     struct md5 *ctx;
    79 } *child_list;
    80 static int maxforks = 1, child_count = 0, maxcrashes = 1, crashes = 0;
    81 
    82 static char **newargv;
    83 static char *protect = NULL, *refuse = NULL;
    84 static uint32_t seed = DEFAULT_SEED;
    85 static uint32_t endseed = DEFAULT_SEED + 1;
    86 static double minratio = DEFAULT_RATIO;
    87 static double maxratio = DEFAULT_RATIO;
    88 static int quiet = 0;
    89 static int maxbytes = -1;
    90 static int md5 = 0;
    91 static int checkexit = 0;
    92 static int verbose = 0;
    93 static int maxmem = -1;
    94 static int64_t maxtime = -1;
    95 static int64_t delay = 0;
    96 static int64_t lastlaunch = 0;
    97 
    9863#define ZZUF_FD_SET(fd, p_fdset, maxfd) \
    9964    if(fd >= 0) \
     
    10974int main(int argc, char *argv[])
    11075{
    111     char *parser, *include, *exclude;
     76    struct opts _opts, *opts = &_opts;
     77    char *tmp, *include, *exclude;
    11278    int i, cmdline = 0;
    11379
    11480    include = exclude = NULL;
     81
     82    _zz_opts_init(opts);
    11583
    11684#if defined(HAVE_GETOPT_H)
     
    164132            break;
    165133        case 'B': /* --max-bytes */
    166             maxbytes = atoi(optarg);
     134            opts->maxbytes = atoi(optarg);
    167135            break;
    168136        case 'c': /* --cmdline */
     
    170138            break;
    171139        case 'C': /* --max-crashes */
    172             maxcrashes = atoi(optarg);
    173             if(maxcrashes <= 0)
    174                 maxcrashes = 0;
     140            opts->maxcrashes = atoi(optarg);
     141            if(opts->maxcrashes <= 0)
     142                opts->maxcrashes = 0;
    175143            break;
    176144        case 'd': /* --debug */
     
    178146            break;
    179147        case 'D': /* --delay */
    180             delay = (int64_t)(atof(optarg) * 1000000.0);
     148            opts->delay = (int64_t)(atof(optarg) * 1000000.0);
    181149            break;
    182150        case 'E': /* --exclude */
     
    185153            {
    186154                printf("%s: invalid regex -- `%s'\n", argv[0], optarg);
     155                _zz_opts_fini(opts);
    187156                return EXIT_FAILURE;
    188157            }
    189158            break;
    190159        case 'F': /* --max-forks */
    191             maxforks = atoi(optarg) > 1 ? atoi(optarg) : 1;
     160            opts->maxchild = atoi(optarg) > 1 ? atoi(optarg) : 1;
    192161            break;
    193162        case 'i': /* --stdin */
     
    199168            {
    200169                printf("%s: invalid regex -- `%s'\n", argv[0], optarg);
     170                _zz_opts_fini(opts);
    201171                return EXIT_FAILURE;
    202172            }
    203173            break;
    204174        case 'm': /* --md5 */
    205             md5 = 1;
     175            opts->md5 = 1;
    206176            break;
    207177        case 'M': /* --max-memory */
    208178            setenv("ZZUF_MEMORY", "1", 1);
    209             maxmem = atoi(optarg);
     179            opts->maxmem = atoi(optarg);
    210180            break;
    211181        case 'n': /* --network */
     
    213183            break;
    214184        case 'P': /* --protect */
    215             protect = optarg;
     185            opts->protect = optarg;
    216186            break;
    217187        case 'q': /* --quiet */
    218             quiet = 1;
     188            opts->quiet = 1;
    219189            break;
    220190        case 'r': /* --ratio */
    221             parser = strchr(optarg, ':');
    222             minratio = atof(optarg);
    223             maxratio = parser ? atof(parser + 1) : minratio;
     191            tmp = strchr(optarg, ':');
     192            opts->minratio = atof(optarg);
     193            opts->maxratio = tmp ? atof(tmp + 1) : opts->minratio;
    224194            break;
    225195        case 'R': /* --refuse */
    226             refuse = optarg;
     196            opts->refuse = optarg;
    227197            break;
    228198        case 's': /* --seed */
    229             parser = strchr(optarg, ':');
    230             seed = atol(optarg);
    231             endseed = parser ? (uint32_t)atoi(parser + 1) : seed + 1;
     199            tmp = strchr(optarg, ':');
     200            opts->seed = atol(optarg);
     201            opts->endseed = tmp ? (uint32_t)atoi(tmp + 1) : opts->seed + 1;
    232202            break;
    233203        case 'S': /* --signal */
     
    235205            break;
    236206        case 'T': /* --max-time */
    237             maxtime = (int64_t)(atof(optarg) * 1000000.0);
     207            opts->maxtime = (int64_t)(atof(optarg) * 1000000.0);
    238208            break;
    239209        case 'x': /* --check-exit */
    240             checkexit = 1;
     210            opts->checkexit = 1;
    241211            break;
    242212        case 'v': /* --verbose */
    243             verbose = 1;
     213            opts->verbose = 1;
    244214            break;
    245215        case 'h': /* --help */
    246216            usage();
     217            _zz_opts_fini(opts);
    247218            return 0;
    248219        case 'V': /* --version */
    249220            version();
     221            _zz_opts_fini(opts);
    250222            return 0;
    251223        default:
    252224            printf("%s: invalid option -- %c\n", argv[0], c);
    253225            printf(MOREINFO, argv[0]);
     226            _zz_opts_fini(opts);
    254227            return EXIT_FAILURE;
    255228        }
     
    260233#endif
    261234
    262     _zz_setratio(minratio, maxratio);
    263     _zz_setseed(seed);
     235    _zz_setratio(opts->minratio, opts->maxratio);
     236    _zz_setseed(opts->seed);
    264237
    265238    /* If asked to read from the standard input */
    266239    if(optind >= argc)
    267240    {
    268         if(endseed != seed + 1)
     241        if(opts->endseed != opts->seed + 1)
    269242        {
    270243            printf("%s: seed ranges are incompatible with stdin fuzzing\n",
    271244                   argv[0]);
    272245            printf(MOREINFO, argv[0]);
     246            _zz_opts_fini(opts);
    273247            return EXIT_FAILURE;
    274248        }
    275249
    276         loop_stdin();
    277 
     250        loop_stdin(opts);
     251
     252        _zz_opts_fini(opts);
    278253        return EXIT_SUCCESS;
    279254    }
     
    299274    if(exclude)
    300275        setenv("ZZUF_EXCLUDE", exclude, 1);
    301     if(protect)
    302         setenv("ZZUF_PROTECT", protect, 1);
    303     if(refuse)
    304         setenv("ZZUF_REFUSE", refuse, 1);
     276    if(opts->protect)
     277        setenv("ZZUF_PROTECT", opts->protect, 1);
     278    if(opts->refuse)
     279        setenv("ZZUF_REFUSE", opts->refuse, 1);
    305280
    306281    /* Allocate memory for children handling */
    307     child_list = malloc(maxforks * sizeof(struct child_list));
    308     for(i = 0; i < maxforks; i++)
    309         child_list[i].status = STATUS_FREE;
    310     child_count = 0;
     282    opts->child = malloc(opts->maxchild * sizeof(struct child));
     283    for(i = 0; i < opts->maxchild; i++)
     284        opts->child[i].status = STATUS_FREE;
     285    opts->nchild = 0;
    311286
    312287    /* Preload libzzuf.so */
     
    314289
    315290    /* Create new argv */
    316     newargv = malloc((argc - optind + 1) * sizeof(char *));
    317     memcpy(newargv, argv + optind, (argc - optind) * sizeof(char *));
    318     newargv[argc - optind] = (char *)NULL;
     291    opts->newargv = malloc((argc - optind + 1) * sizeof(char *));
     292    memcpy(opts->newargv, argv + optind, (argc - optind) * sizeof(char *));
     293    opts->newargv[argc - optind] = (char *)NULL;
    319294
    320295    /* Main loop */
    321     while(child_count || seed < endseed)
     296    while(opts->nchild || opts->seed < opts->endseed)
    322297    {
    323298        /* Spawn new children, if necessary */
    324         spawn_children();
     299        spawn_children(opts);
    325300
    326301        /* Cleanup dead or dying children */
    327         clean_children();
     302        clean_children(opts);
    328303
    329304        /* Read data from children */
    330         read_children();
    331 
    332         if(maxcrashes && crashes >= maxcrashes && child_count == 0)
     305        read_children(opts);
     306
     307        if(opts->maxcrashes && opts->crashes >= opts->maxcrashes
     308            && opts->nchild == 0)
    333309            break;
    334310    }
    335311
    336312    /* Clean up */
    337     free(newargv);
    338     free(child_list);
    339 
    340     return crashes ? EXIT_FAILURE : EXIT_SUCCESS;   
    341 }
    342 
    343 static void loop_stdin(void)
     313    _zz_opts_fini(opts);
     314
     315    return opts->crashes ? EXIT_FAILURE : EXIT_SUCCESS;   
     316}
     317
     318static void loop_stdin(struct opts *opts)
    344319{
    345320    uint8_t md5sum[16];
    346321    struct md5 *ctx = NULL;
    347322
    348     if(md5)
     323    if(opts->md5)
    349324        ctx = _zz_md5_init();
    350325
    351     if(protect)
    352         _zz_protect(protect);
    353     if(refuse)
    354         _zz_refuse(refuse);
     326    if(opts->protect)
     327        _zz_protect(opts->protect);
     328    if(opts->refuse)
     329        _zz_refuse(opts->refuse);
    355330
    356331    _zz_fd_init();
     
    369344        _zz_addpos(0, ret);
    370345
    371         if(md5)
     346        if(opts->md5)
    372347            _zz_md5_add(ctx, buf, ret);
    373348        else while(ret)
     
    380355    }
    381356
    382     if(md5)
     357    if(opts->md5)
    383358    {
    384359        _zz_md5_fini(md5sum, ctx);
    385360        fprintf(stdout, "zzuf[s=%i,r=%g]: %.02x%.02x%.02x%.02x%.02x"
    386361                "%.02x%.02x%.02x%.02x%.02x%.02x%.02x%.02x%.02x%.02x%.02x\n",
    387                 seed, minratio, md5sum[0], md5sum[1], md5sum[2], md5sum[3],
    388                 md5sum[4], md5sum[5], md5sum[6], md5sum[7],
    389                 md5sum[8], md5sum[9], md5sum[10], md5sum[11],
    390                 md5sum[12], md5sum[13], md5sum[14], md5sum[15]);
     362                opts->seed, opts->minratio, md5sum[0], md5sum[1], md5sum[2],
     363                md5sum[3], md5sum[4], md5sum[5], md5sum[6], md5sum[7],
     364                md5sum[8], md5sum[9], md5sum[10], md5sum[11], md5sum[12],
     365                md5sum[13], md5sum[14], md5sum[15]);
    391366        fflush(stdout);
    392367    }
     
    444419}
    445420
    446 static void spawn_children(void)
     421static void spawn_children(struct opts *opts)
    447422{
    448423    static int const files[] = { DEBUG_FILENO, STDERR_FILENO, STDOUT_FILENO };
     
    453428    int i, j;
    454429
    455     if(child_count == maxforks)
     430    if(opts->nchild == opts->maxchild)
    456431        return; /* no slot */
    457432
    458     if(seed == endseed)
     433    if(opts->seed == opts->endseed)
    459434        return; /* job finished */
    460435
    461     if(maxcrashes && crashes >= maxcrashes)
     436    if(opts->maxcrashes && opts->crashes >= opts->maxcrashes)
    462437        return; /* all jobs crashed */
    463438
    464     if(delay > 0 && lastlaunch + delay > now)
     439    if(opts->delay > 0 && opts->lastlaunch + opts->delay > now)
    465440        return; /* too early */
    466441
    467442    /* Find the empty slot */
    468     for(i = 0; i < maxforks; i++)
    469         if(child_list[i].status == STATUS_FREE)
     443    for(i = 0; i < opts->maxchild; i++)
     444        if(opts->child[i].status == STATUS_FREE)
    470445            break;
    471446
     
    487462        case 0:
    488463            /* We’re the child */
    489             if(maxmem >= 0)
     464            if(opts->maxmem >= 0)
    490465            {
    491466                struct rlimit rlim;
    492                 rlim.rlim_cur = maxmem * 1000000;
    493                 rlim.rlim_max = maxmem * 1000000;
     467                rlim.rlim_cur = opts->maxmem * 1000000;
     468                rlim.rlim_max = opts->maxmem * 1000000;
    494469                setrlimit(RLIMIT_AS, &rlim);
    495470            }
     
    508483
    509484            /* Set environment variables */
    510             sprintf(buf, "%i", seed);
     485            sprintf(buf, "%i", opts->seed);
    511486            setenv("ZZUF_SEED", buf, 1);
    512             sprintf(buf, "%g", minratio);
     487            sprintf(buf, "%g", opts->minratio);
    513488            setenv("ZZUF_MINRATIO", buf, 1);
    514             sprintf(buf, "%g", maxratio);
     489            sprintf(buf, "%g", opts->maxratio);
    515490            setenv("ZZUF_MAXRATIO", buf, 1);
    516491
    517492            /* Run our process */
    518             if(execvp(newargv[0], newargv))
     493            if(execvp(opts->newargv[0], opts->newargv))
    519494            {
    520                 perror(newargv[0]);
     495                perror(opts->newargv[0]);
    521496                exit(EXIT_FAILURE);
    522497            }
     
    525500
    526501    /* We’re the parent, acknowledge spawn */
    527     child_list[i].date = now;
    528     child_list[i].pid = pid;
     502    opts->child[i].date = now;
     503    opts->child[i].pid = pid;
    529504    for(j = 0; j < 3; j++)
    530505    {
    531506        close(fd[j][1]);
    532         child_list[i].fd[j] = fd[j][0];
    533     }
    534     child_list[i].bytes = 0;
    535     child_list[i].seed = seed;
    536     child_list[i].ratio = _zz_getratio();
    537     child_list[i].status = STATUS_RUNNING;
    538     if(md5)
    539         child_list[i].ctx = _zz_md5_init();
    540 
    541     if(verbose)
     507        opts->child[i].fd[j] = fd[j][0];
     508    }
     509    opts->child[i].bytes = 0;
     510    opts->child[i].seed = opts->seed;
     511    opts->child[i].ratio = _zz_getratio();
     512    opts->child[i].status = STATUS_RUNNING;
     513    if(opts->md5)
     514        opts->child[i].ctx = _zz_md5_init();
     515
     516    if(opts->verbose)
    542517        fprintf(stderr, "zzuf[s=%i,r=%g]: launched %s\n",
    543                 child_list[i].seed, child_list[i].ratio, newargv[0]);
    544 
    545     lastlaunch = now;
    546     child_count++;
    547     seed++;
    548 
    549     _zz_setseed(seed);
    550 }
    551 
    552 static void clean_children(void)
     518                opts->child[i].seed, opts->child[i].ratio,
     519                opts->newargv[0]);
     520
     521    opts->lastlaunch = now;
     522    opts->nchild++;
     523    opts->seed++;
     524
     525    _zz_setseed(opts->seed);
     526}
     527
     528static void clean_children(struct opts *opts)
    553529{
    554530    int64_t now = _zz_time();
     
    556532
    557533    /* Terminate children if necessary */
    558     for(i = 0; i < maxforks; i++)
    559     {
    560         if(child_list[i].status == STATUS_RUNNING
    561             && maxbytes >= 0 && child_list[i].bytes > maxbytes)
    562         {
    563             if(verbose)
     534    for(i = 0; i < opts->maxchild; i++)
     535    {
     536        if(opts->child[i].status == STATUS_RUNNING
     537            && opts->maxbytes >= 0
     538            && opts->child[i].bytes > opts->maxbytes)
     539        {
     540            if(opts->verbose)
    564541                fprintf(stderr, "zzuf[s=%i,r=%g]: "
    565542                        "data output exceeded, sending SIGTERM\n",
    566                         child_list[i].seed, child_list[i].ratio);
    567             kill(child_list[i].pid, SIGTERM);
    568             child_list[i].date = now;
    569             child_list[i].status = STATUS_SIGTERM;
    570         }
    571 
    572         if(child_list[i].status == STATUS_RUNNING
    573             && maxtime >= 0
    574             && now > child_list[i].date + maxtime)
    575         {
    576             if(verbose)
     543                        opts->child[i].seed, opts->child[i].ratio);
     544            kill(opts->child[i].pid, SIGTERM);
     545            opts->child[i].date = now;
     546            opts->child[i].status = STATUS_SIGTERM;
     547        }
     548
     549        if(opts->child[i].status == STATUS_RUNNING
     550            && opts->maxtime >= 0
     551            && now > opts->child[i].date + opts->maxtime)
     552        {
     553            if(opts->verbose)
    577554                fprintf(stderr, "zzuf[s=%i,r=%g]: "
    578555                        "running time exceeded, sending SIGTERM\n",
    579                         child_list[i].seed, child_list[i].ratio);
    580             kill(child_list[i].pid, SIGTERM);
    581             child_list[i].date = now;
    582             child_list[i].status = STATUS_SIGTERM;
     556                        opts->child[i].seed, opts->child[i].ratio);
     557            kill(opts->child[i].pid, SIGTERM);
     558            opts->child[i].date = now;
     559            opts->child[i].status = STATUS_SIGTERM;
    583560        }
    584561    }
    585562
    586563    /* Kill children if necessary (still there after 2 seconds) */
    587     for(i = 0; i < maxforks; i++)
    588     {
    589         if(child_list[i].status == STATUS_SIGTERM
    590             && now > child_list[i].date + 2000000)
    591         {
    592             if(verbose)
     564    for(i = 0; i < opts->maxchild; i++)
     565    {
     566        if(opts->child[i].status == STATUS_SIGTERM
     567            && now > opts->child[i].date + 2000000)
     568        {
     569            if(opts->verbose)
    593570                fprintf(stderr, "zzuf[s=%i,r=%g]: "
    594571                        "not responding, sending SIGKILL\n",
    595                         child_list[i].seed, child_list[i].ratio);
    596             kill(child_list[i].pid, SIGKILL);
    597             child_list[i].status = STATUS_SIGKILL;
     572                        opts->child[i].seed, opts->child[i].ratio);
     573            kill(opts->child[i].pid, SIGKILL);
     574            opts->child[i].status = STATUS_SIGKILL;
    598575        }
    599576    }
    600577
    601578    /* Collect dead children */
    602     for(i = 0; i < maxforks; i++)
     579    for(i = 0; i < opts->maxchild; i++)
    603580    {
    604581        uint8_t md5sum[16];
     
    606583        pid_t pid;
    607584
    608         if(child_list[i].status != STATUS_SIGKILL
    609             && child_list[i].status != STATUS_SIGTERM
    610             && child_list[i].status != STATUS_EOF)
     585        if(opts->child[i].status != STATUS_SIGKILL
     586            && opts->child[i].status != STATUS_SIGTERM
     587            && opts->child[i].status != STATUS_EOF)
    611588            continue;
    612589
    613         pid = waitpid(child_list[i].pid, &status, WNOHANG);
     590        pid = waitpid(opts->child[i].pid, &status, WNOHANG);
    614591        if(pid <= 0)
    615592            continue;
    616593
    617         if(checkexit && WIFEXITED(status) && WEXITSTATUS(status))
     594        if(opts->checkexit && WIFEXITED(status) && WEXITSTATUS(status))
    618595        {
    619596            fprintf(stderr, "zzuf[s=%i,r=%g]: exit %i\n",
    620                     child_list[i].seed, child_list[i].ratio,
     597                    opts->child[i].seed, opts->child[i].ratio,
    621598                    WEXITSTATUS(status));
    622             crashes++;
     599            opts->crashes++;
    623600        }
    624601        else if(WIFSIGNALED(status)
    625602                 && !(WTERMSIG(status) == SIGTERM
    626                        && child_list[i].status == STATUS_SIGTERM))
     603                       && opts->child[i].status == STATUS_SIGTERM))
    627604        {
    628605            fprintf(stderr, "zzuf[s=%i,r=%g]: signal %i%s%s\n",
    629                     child_list[i].seed, child_list[i].ratio,
     606                    opts->child[i].seed, opts->child[i].ratio,
    630607                    WTERMSIG(status), sig2str(WTERMSIG(status)),
    631                       (WTERMSIG(status) == SIGKILL && maxmem >= 0) ?
     608                      (WTERMSIG(status) == SIGKILL && opts->maxmem >= 0) ?
    632609                      " (memory exceeded?)" : "");
    633             crashes++;
     610            opts->crashes++;
    634611        }
    635612
    636613        for(j = 0; j < 3; j++)
    637             if(child_list[i].fd[j] >= 0)
    638                 close(child_list[i].fd[j]);
    639 
    640         if(md5)
    641         {
    642             _zz_md5_fini(md5sum, child_list[i].ctx);
    643             fprintf(stdout, "zzuf[s=%i,r=%g]: %.02x%.02x%.02x%.02x%.02x"
    644                     "%.02x%.02x%.02x%.02x%.02x%.02x%.02x%.02x%.02x%.02x%.02x\n",
    645                     child_list[i].seed, child_list[i].ratio, md5sum[0],
    646                     md5sum[1], md5sum[2], md5sum[3], md5sum[4], md5sum[5],
    647                     md5sum[6], md5sum[7], md5sum[8], md5sum[9], md5sum[10],
    648                     md5sum[11], md5sum[12], md5sum[13], md5sum[14], md5sum[15]);
     614            if(opts->child[i].fd[j] >= 0)
     615                close(opts->child[i].fd[j]);
     616
     617        if(opts->md5)
     618        {
     619            _zz_md5_fini(md5sum, opts->child[i].ctx);
     620            fprintf(stdout, "zzuf[s=%i,r=%g]: %.02x%.02x%.02x%.02x%.02x%.02x"
     621                    "%.02x%.02x%.02x%.02x%.02x%.02x%.02x%.02x%.02x%.02x\n",
     622                    opts->child[i].seed, opts->child[i].ratio,
     623                    md5sum[0], md5sum[1], md5sum[2], md5sum[3], md5sum[4],
     624                    md5sum[5], md5sum[6], md5sum[7], md5sum[8], md5sum[9],
     625                    md5sum[10], md5sum[11], md5sum[12], md5sum[13],
     626                    md5sum[14], md5sum[15]);
    649627            fflush(stdout);
    650628        }
    651         child_list[i].status = STATUS_FREE;
    652         child_count--;
    653     }
    654 }
    655 
    656 static void read_children(void)
     629        opts->child[i].status = STATUS_FREE;
     630        opts->nchild--;
     631    }
     632}
     633
     634static void read_children(struct opts *opts)
    657635{
    658636    struct timeval tv;
     
    662640    /* Read data from all sockets */
    663641    FD_ZERO(&fdset);
    664     for(i = 0; i < maxforks; i++)
    665     {
    666         if(child_list[i].status != STATUS_RUNNING)
     642    for(i = 0; i < opts->maxchild; i++)
     643    {
     644        if(opts->child[i].status != STATUS_RUNNING)
    667645            continue;
    668646
    669647        for(j = 0; j < 3; j++)
    670             ZZUF_FD_SET(child_list[i].fd[j], &fdset, maxfd);
     648            ZZUF_FD_SET(opts->child[i].fd[j], &fdset, maxfd);
    671649    }
    672650    tv.tv_sec = 0;
     
    680658
    681659    /* XXX: cute (i, j) iterating hack */
    682     for(i = 0, j = 0; i < maxforks; i += (j == 2), j = (j + 1) % 3)
     660    for(i = 0, j = 0; i < opts->maxchild; i += (j == 2), j = (j + 1) % 3)
    683661    {
    684662        uint8_t buf[BUFSIZ];
    685663
    686         if(child_list[i].status != STATUS_RUNNING)
     664        if(opts->child[i].status != STATUS_RUNNING)
    687665            continue;
    688666
    689         if(!ZZUF_FD_ISSET(child_list[i].fd[j], &fdset))
     667        if(!ZZUF_FD_ISSET(opts->child[i].fd[j], &fdset))
    690668            continue;
    691669
    692         ret = read(child_list[i].fd[j], buf, BUFSIZ - 1);
     670        ret = read(opts->child[i].fd[j], buf, BUFSIZ - 1);
    693671        if(ret > 0)
    694672        {
    695673            /* We got data */
    696674            if(j != 0)
    697                 child_list[i].bytes += ret;
    698 
    699             if(md5 && j == 2)
    700                 _zz_md5_add(child_list[i].ctx, buf, ret);
    701             else if(!quiet || j == 0)
     675                opts->child[i].bytes += ret;
     676
     677            if(opts->md5 && j == 2)
     678                _zz_md5_add(opts->child[i].ctx, buf, ret);
     679            else if(!opts->quiet || j == 0)
    702680                write((j < 2) ? STDERR_FILENO : STDOUT_FILENO, buf, ret);
    703681        }
     
    705683        {
    706684            /* End of file reached */
    707             close(child_list[i].fd[j]);
    708             child_list[i].fd[j] = -1;
    709 
    710             if(child_list[i].fd[0] == -1 && child_list[i].fd[1] == -1
    711                && child_list[i].fd[2] == -1)
    712                 child_list[i].status = STATUS_EOF;
     685            close(opts->child[i].fd[j]);
     686            opts->child[i].fd[j] = -1;
     687
     688            if(opts->child[i].fd[0] == -1
     689                && opts->child[i].fd[1] == -1
     690                && opts->child[i].fd[2] == -1)
     691                opts->child[i].status = STATUS_EOF;
    713692        }
    714693    }
Note: See TracChangeset for help on using the changeset viewer.