# include "ctlmod.h" # include "pipes.h" # include SCCSID(@(#)do_st.c 8.1 12/31/84) /* ** DO_ST -- do a state. ** ** This routine does a state as indicated by ppb, handing it ** pc & pv as parameters. The state must be known already. ** ** If the state is local, it calls 'call_fn' to actually ** do the setup and call the function. ** If the state is remote, it uses send_off to send ppb ** to the process that can do it. ** ** It returns the next state to execute, possibly PB_UNKNOWN. ** ** Parameters: ** ppb -- a pipe block which identifies the state ** to call, etc. ** pc -- the pc to hand to the function. ** pv -- the pv to had to the function. ** ** Returns: ** none (except through ppb) ** ** Side Effects: ** *ppb gets set to identify the next state. ** Resp is set if local function. ** ** Called By: ** do_seq ** ** Trace Flags: ** 2.8 - 2.15 */ do_st(ppb, pc, pv) register pb_t *ppb; int pc; PARM *pv; { register state_t *s; register int i; int rtval; i = ppb->pb_st; s = &Cm.cm_state[i]; if (i < 0 || i > CM_MAXST || s->st_type == ST_UNDEF) syserr("do_st: undef state %d", i); # ifdef xCTR1 if (tTf(2, 8)) lprintf("do_st: state %d type %d mark %d\n", i, s->st_type, markbuf(Qbuf)); # endif switch (s->st_type) { case ST_REMOT: /* ** Remote: determine the correct process and send ** it on its way. */ ppb->pb_proc = s->st_v.st_rem.st_proc; send_off(ppb, pc, pv); pb_flush(ppb); rtval = PB_UNKNOWN; break; case ST_LOCAL: /* ** Local: execute the function using 'call_fn' ** and compute next state. ** If call originated in this process, set the EOF bit ** so we don't try to read this pipe later. */ if (bitset(PB_FRFR, ppb->pb_stat) && !bitset(ST_EXTERN, s->st_stat)) syserr("do_st: restricted state %d", i); if (ppb->pb_from == Cm.cm_myproc) setbit(PB_EOF, ppb->pb_stat); call_fn(s->st_v.st_loc.st_funcno, pc, pv); rtval = s->st_v.st_loc.st_next; break; default: syserr("do_st: type %d", s->st_type); } # ifdef xCTR1 if (tTf(2, 10)) lprintf("do_st: ret %d mark %d\n", rtval, markbuf(Qbuf)); # endif return (rtval); }