--- ray/src/util/rtcontrib.c 2005/06/10 16:42:11 1.17 +++ ray/src/util/rtcontrib.c 2005/10/05 05:20:21 1.29 @@ -1,5 +1,5 @@ #ifndef lint -static const char RCSid[] = "$Id: rtcontrib.c,v 1.17 2005/06/10 16:42:11 greg Exp $"; +static const char RCSid[] = "$Id: rtcontrib.c,v 1.29 2005/10/05 05:20:21 greg Exp $"; #endif /* * Gather rtrace output to compute contributions from particular sources @@ -16,7 +16,9 @@ static const char RCSid[] = "$Id: rtcontrib.c,v 1.17 2 #include "lookup.h" #include "calcomp.h" +#ifndef MAXMODLIST #define MAXMODLIST 1024 /* maximum modifiers we'll track */ +#endif int treebufsiz = BUFSIZ; /* current tree buffer size */ @@ -72,7 +74,8 @@ struct rtproc { }; /* rtrace process buffer */ /* rtrace command and defaults */ -char *rtargv[256] = { "rtrace", "-dj", ".5", "-dr", "3", +char *rtargv[256+2*MAXMODLIST] = { "rtrace", + "-dj", ".5", "-dr", "3", "-ab", "1", "-ad", "128", }; int rtargc = 9; /* overriding rtrace options */ @@ -109,6 +112,8 @@ int using_stdout = 0; /* are we using stdout? */ const char *modname[MAXMODLIST]; /* ordered modifier name list */ int nmods = 0; /* number of modifiers */ +#define queue_length() (lastray - lastdone) + MODCONT *addmodifier(char *modn, char *outf, char *binv); void addmodfile(char *fname, char *outf, char *binv); @@ -125,6 +130,18 @@ void put_contrib(const DCOLOR cnt, FILE *fout); void add_contrib(const char *modn); void done_contrib(void); +/* return number of open rtrace processes */ +static int +nrtprocs(void) +{ + int nrtp = 0; + struct rtproc *rtp; + + for (rtp = &rt0; rtp != NULL; rtp = rtp->next) + nrtp += rtp->pd.running; + return(nrtp); +} + /* set input/output format */ static void setformat(const char *fmt) @@ -170,6 +187,13 @@ main(int argc, char *argv[]) char *binval = NULL; char fmt[8]; int i, j; + /* need at least one argument */ + if (argc < 2) { + fprintf(stderr, +"Usage: %s [-n nprocs][-r][-e expr][-f source][-o ospec][-b binv] {-m mod | -M file} [rtrace options] octree\n", + argv[0]); + exit(1); + } /* global program name */ gargv = argv; /* initialize calcomp routines */ @@ -193,7 +217,7 @@ main(int argc, char *argv[]) recover++; continue; case 'n': /* number of processes */ - if (argv[i][2] || i >= argc-1) break; + if (argv[i][2] || i >= argc-2) break; nprocs = atoi(argv[++i]); if (nprocs <= 0) error(USER, "illegal number of processes"); @@ -218,7 +242,7 @@ main(int argc, char *argv[]) case 'f': /* file or i/o format */ if (!argv[i][2]) { char *fpath; - if (i >= argc-1) break; + if (i >= argc-2) break; fpath = getpath(argv[++i], getrlibpath(), R_OK); if (fpath == NULL) { @@ -233,34 +257,36 @@ main(int argc, char *argv[]) setformat(argv[i]+2); continue; case 'e': /* expression */ - if (argv[i][2] || i >= argc-1) break; + if (argv[i][2] || i >= argc-2) break; scompile(argv[++i], NULL, 0); continue; case 'o': /* output file spec. */ - if (argv[i][2] || i >= argc-1) break; + if (argv[i][2] || i >= argc-2) break; curout = argv[++i]; continue; case 'x': /* horiz. output resolution */ - if (argv[i][2] || i >= argc-1) break; + if (argv[i][2] || i >= argc-2) break; xres = atoi(argv[++i]); continue; case 'y': /* vert. output resolution */ - if (argv[i][2] || i >= argc-1) break; + if (argv[i][2] || i >= argc-2) break; yres = atoi(argv[++i]); continue; case 'b': /* bin expression */ - if (argv[i][2] || i >= argc-1) break; + if (argv[i][2] || i >= argc-2) break; binval = argv[++i]; continue; case 'm': /* modifier name */ - if (argv[i][2] || i >= argc-1) break; + if (argv[i][2] || i >= argc-2) break; rtargv[rtargc++] = "-ti"; rtargv[rtargc++] = argv[++i]; addmodifier(argv[i], curout, binval); continue; case 'M': /* modifier file */ - if (argv[i][2] || i >= argc-1) break; - addmodfile(argv[++i], curout, binval); + if (argv[i][2] || i >= argc-2) break; + rtargv[rtargc++] = "-tI"; + rtargv[rtargc++] = argv[++i]; + addmodfile(argv[i], curout, binval); continue; } rtargv[rtargc++] = argv[i]; /* assume rtrace option */ @@ -310,20 +336,23 @@ main(int argc, char *argv[]) error(USER, "missing octree argument"); rtargv[rtargc++] = octree = argv[i]; rtargv[rtargc] = NULL; - /* start rtrace & compute contributions */ + /* start rtrace */ init(nprocs); if (recover) /* perform recovery if requested */ recover_output(stdin); - trace_contribs(stdin); + trace_contribs(stdin); /* compute contributions */ quit(0); } +#ifndef SIGALRM +#define SIGALRM SIGTERM +#endif /* kill persistent rtrace process */ static void killpersist(void) { FILE *fp = fopen(persistfn, "r"); - int pid; + RT_PID pid; if (fp == NULL) return; @@ -463,8 +492,11 @@ addmodfile(char *fname, char *outf, char *binv) { char *mname[MAXMODLIST]; int i; - /* load the file & store strings */ - wordfile(mname, fname); + /* find the file & store strings */ + if (wordfile(mname, getpath(fname, getrlibpath(), R_OK)) < 0) { + sprintf(errmsg, "cannot find modifier file '%s'", fname); + error(SYSTEM, errmsg); + } for (i = 0; mname[i]; i++) /* add each one */ addmodifier(mname[i], outf, binv); } @@ -615,10 +647,8 @@ getofile(const char *ospec, const char *mname, int bn) if (header) { char info[512]; char *cp = info; - if (ofl & OF_MODIFIER) { - sprintf(cp, "MODIFIER=%s\n", mname); - while (*cp) ++cp; - } + sprintf(cp, "MODIFIER=%s\n", mname); + while (*cp) ++cp; if (ofl & OF_BIN) { sprintf(cp, "BIN=%d\n", bn); while (*cp) ++cp; @@ -700,7 +730,7 @@ add_contrib(const char *modn) bn = (int)(evalue(mp->binv) + .5); if (bn <= 0) bn = 0; - else if (bn > mp->nbins) { /* new bin */ + else if (bn >= mp->nbins) { /* new bin */ mp = (MODCONT *)realloc(mp, sizeof(MODCONT) + bn*sizeof(DCOLOR)); if (mp == NULL) @@ -899,7 +929,7 @@ wait_rproc(void) if (rt->bsiz + BUFSIZ <= treebufsiz) rt->bsiz = treebufsiz; else - rt->bsiz = treebufsiz += BUFSIZ; + treebufsiz = rt->bsiz += BUFSIZ; rt->buf = (char *)realloc(rt->buf, rt->bsiz); } if (rt->buf == NULL) @@ -940,7 +970,8 @@ trace_contribs(FILE *fin) struct rtproc *rtp; /* loop over input */ while ((iblen = getinp(inpbuf, fin)) > 0) { - if (lastray+1 < lastray) { /* counter rollover? */ + if (lastray+1 < lastray || /* need reset? */ + queue_length() > 5*nrtprocs()) { while (wait_rproc() != NULL) process_queue(); lastdone = lastray = 0; @@ -1024,8 +1055,13 @@ recover_output(FILE *fin) error(USER, "cannot recover from command"); /* open output */ fp = fopen(oname, "rb+"); - if (fp == NULL) - break; /* must be end of modifier */ + if (fp == NULL) { + if (j) + break; /* assume end of modifier */ + sprintf(errmsg, "missing recover file '%s'", + oname); + error(USER, errmsg); + } nvals = lseek(fileno(fp), 0, SEEK_END); if (nvals <= 0) { lastout = 0; /* empty output, quit here */ @@ -1080,10 +1116,15 @@ recover_output(FILE *fin) error(WARNING, "no output files to recover"); return; } + if (raysleft && lastout >= raysleft) { + error(WARNING, "output appears to be complete"); + /* XXX should read & discard input? */ + quit(0); + } /* seek on all files */ nvals = lastout * outvsiz; lu_doall(&ofiletab, myseeko, &nvals); - /* discard input */ + /* skip repeated input */ for (nvals = 0; nvals < lastout; nvals++) if (getinp(oname, fin) <= 0) error(USER, "unexpected EOF on input");