From 1d7eff0ba635ac5983bed820dd349af2ebee0850 Mon Sep 17 00:00:00 2001 From: root Date: Fri, 13 Jul 2012 00:51:35 -0700 Subject: better comments, working toward MODE switching --- tools/hi-q.c | 85 +++++++++++++++++++++++++++++++++++++++--------------------- 1 file changed, 55 insertions(+), 30 deletions(-) (limited to 'tools/hi-q.c') diff --git a/tools/hi-q.c b/tools/hi-q.c index aa552e1..bf9c599 100644 --- a/tools/hi-q.c +++ b/tools/hi-q.c @@ -112,7 +112,14 @@ void usage() { //////////////////////////////////////// // we have data coming in on fd 0. -// and control coming in on fd 1. +// and envelope / control information coming in on fd 1. + +void dump___not_used(const string var){ + char* str = getenv(var.c_str()); + if (str) cerr << "hi-q: " << var + << " is set to '" << str << "'" << endl; + else cerr << "hi-q: " << var << " is not set." << endl; +} int main(int argc, char** argv, char const * const * env) { int verbose(1); @@ -143,10 +150,16 @@ int main(int argc, char** argv, char const * const * env) { typedef vector VS; vector filter; - char* conf_name; + string conf_var = "HI_Q_CONF"; + + int mode(0); + char* modevar = getenv("HI_Q_MODE"); + if (modevar) mode = 1000 + atoi(modevar); + cerr << "hi-q mode: " << mode << endl; + char* conf_name; if (argc == 1) { - conf_name = getenv("HI_Q_CONF"); + conf_name = getenv(conf_var.c_str()); if (!conf_name) { usage(); exit(1); @@ -194,22 +207,30 @@ int main(int argc, char** argv, char const * const * env) { vector kidpid(nkids); // indexed by kid number // At this point, there are some loop invariants; -// (a) fd0 is open and ready for the next child to read, and -// (b) fd1 is open but is something children can (and should) -// throw away as soon as convenient. - - {int ii; for (ii=0; ii < nkids; ii++){ /* loop over all kids */ +// (a) fd0 is open and has the email msg, +// ready for the next child to read, and +// (b) fd1 is open and has envelope information. +// We need it to be open, so that pipe() +// doesn't choose it. That allows us to close +// it and dup() something onto it. + + for (int ii=0; ii < nkids; ii++){ /* loop over all kids */ int datapipe[2]; int kid_end; - int lastkid = (ii == nkids-1); -#define flip(a,b) (lastkid ? b : a) //xx fprintf(stderr, "Top of loop %d loose: %d\n", ii, loose_end); + if (loose_end) { + close(0); + dup2(loose_end, 0); + close(loose_end); + } + // Create a pipe, which will be used to connect // this child's fd1 to the next child's fd0 ... -// except for the last kid, which reads fd1 rather -// than writing it. +// except for the last kid, which reads both fd0 and fd1, +// while writing nothing. + rslt = pipe(datapipe); if (rslt < 0) { fprintf(stderr, "hi-q: could not create datapipe: "); @@ -218,34 +239,37 @@ int main(int argc, char** argv, char const * const * env) { } //xx fprintf(stderr, "pipe: %d %d\n", datapipe[0], datapipe[1]); - if (loose_end) { - close(0); - dup2(loose_end, 0); - close(loose_end); - } +// For N-1 kids, the loose end feeds forward. +// It will be written by this kid and read by the next kid. +// For the last kid, the loose end connects to hi-q. +// It will be written by hi-q and read by the last kid. + int lastkid = (ii == nkids-1); +#define flip(a,b) (lastkid ? b : a) loose_end = datapipe[flip(0,1)]; - kid_end = datapipe[flip(1,0)]; + kid_end = datapipe[flip(1,0)]; kidpid[ii] = fork(); if (!kidpid[ii]) { /*** child code ***/ -// Now that we are through creating pipes, get rid -// of the placeholder: +// Now that we are through creating pipes, we don't +// need to continue blocking fd1: close(1); - close(loose_end); // the reading end is none of our business + close(loose_end); // the reading end is none of this kid's business + // except last kid: writing end - rslt = dup2(kid_end, 1); + rslt = dup2(kid_end, 1); // the writing end is stdout for this kid + // except last kid: nonstandard input if (rslt < 0) { - fprintf(stderr, "hi-q: dup2(kid(%d),1) failed: ", kid_end); + fprintf(stderr, "hi-q: kid %d: dup2(%d,1) failed: ", ii, kid_end); perror(0); exit(ex_syserr); } close(kid_end); // use fd1 instead now - // OK, at this point we are set up to read fd0 - // and write fd1 (except last kid reads fd1). + // OK, at this point this kid is set up to read fd0 and write fd1 + // (except last kid reads fd1 as well as fd0). //// probe_fd(); int ntok = filter[ii].size(); @@ -272,15 +296,14 @@ int main(int argc, char** argv, char const * const * env) { ii, kidpid[ii], kid_end); // sleep(1); /* let kid run a while */ #endif - }} + } // here with the whole pipeline of kids running close(0); // the reading end of stdin was // delegated to the first child - - {int ii; for (ii=0; ii