evalsubshell(union node *n, int flags)
{
	struct job *jp;
	int backgnd = (n->type == NBACKGND);
	int status;

	errlinno = lineno = n->nredir.linno;
	if (funcline)
		lineno -= funcline - 1;

	expredir(n->nredir.redirect);
	INTOFF;
	if (!backgnd && flags & EV_EXIT && !have_traps()) {
		forkreset();
		goto nofork;
	}
	jp = makejob(n, 1);
	if (forkshell(jp, n, backgnd) == 0) {
		flags |= EV_EXIT;
		if (backgnd)
			flags &=~ EV_TESTED;
nofork:
		INTON;
		redirect(n->nredir.redirect, 0);
		evaltreenr(n->nredir.n, flags);
		/* never returns */
	}
	status = 0;
	if (! backgnd)
		status = waitforjob(jp);
	INTON;
	return status;
}
evalsubshell(union node *n, int flags)
{
	struct job *jp;
	int backgnd = (n->type == NBACKGND);
	int status;

	errlinno = lineno = n->nredir.linno;
	if (funcline)
		lineno -= funcline - 1;

	expredir(n->nredir.redirect);
	INTOFF;
	if (!backgnd && flags & EV_EXIT && !have_traps()) {
		forkreset();
		goto nofork;
	}
	jp = makejob(n, 1);
	if (forkshell(jp, n, backgnd) == 0) {
		flags |= EV_EXIT;
		if (backgnd)
			flags &=~ EV_TESTED;
nofork:
		INTON;
		redirect(n->nredir.redirect, 0);
		evaltreenr(n->nredir.n, flags);
		 
	}
	status = 0;
	if (! backgnd)
		status = waitforjob(jp);
	INTON;
	return status;
}