96f265
diff -up ksh-20120801/src/cmd/ksh93/include/io.h.macro ksh-20120801/src/cmd/ksh93/include/io.h
96f265
--- ksh-20120801/src/cmd/ksh93/include/io.h.macro	2012-07-18 16:12:38.000000000 +0200
96f265
+++ ksh-20120801/src/cmd/ksh93/include/io.h	2013-07-04 16:14:05.809595966 +0200
96f265
@@ -81,6 +81,7 @@ extern void 	sh_iosave(Shell_t *, int,in
96f265
 extern int 	sh_iovalidfd(Shell_t*, int);
96f265
 extern int 	sh_inuse(Shell_t*, int);
96f265
 extern void 	sh_iounsave(Shell_t*);
96f265
+extern void	iounpipe(Shell_t*);
96f265
 extern int	sh_chkopen(const char*);
96f265
 extern int	sh_ioaccess(int,int);
96f265
 extern int	sh_devtofd(const char*);
96f265
diff -up ksh-20120801/src/cmd/ksh93/sh/subshell.c.macro ksh-20120801/src/cmd/ksh93/sh/subshell.c
96f265
--- ksh-20120801/src/cmd/ksh93/sh/subshell.c.macro	2013-07-04 16:14:05.783595751 +0200
96f265
+++ ksh-20120801/src/cmd/ksh93/sh/subshell.c	2013-07-04 16:15:46.673432991 +0200
96f265
@@ -171,7 +171,7 @@ void sh_subfork(void)
96f265
 {
96f265
 	register struct subshell *sp = subshell_data;
96f265
 	Shell_t	*shp = sp->shp;
96f265
-	int	curenv = shp->curenv;
96f265
+	int	curenv = shp->curenv, comsub=shp->comsub;
96f265
 	pid_t pid;
96f265
 	char *trap = shp->st.trapcom[0];
96f265
 	if(trap)
96f265
@@ -204,7 +204,7 @@ void sh_subfork(void)
96f265
 		shp->comsub = 0;
96f265
 		SH_SUBSHELLNOD->nvalue.s = 0;
96f265
 		sp->subpid=0;
96f265
-		shp->st.trapcom[0] = trap;
96f265
+		shp->st.trapcom[0] = (comsub==2?NULL:trap);
96f265
 		shp->savesig = 0;
96f265
 	}
96f265
 }
96f265
@@ -743,7 +743,6 @@ Sfio_t *sh_subshell(Shell_t *shp,Shnode_
96f265
 		fchdir(shp->pwdfd);
96f265
 	}
96f265
 	shp->subshare = sp->subshare;
96f265
-	shp->comsub = sp->comsub;
96f265
 	shp->subdup = sp->subdup;
96f265
 #if SHOPT_COSHELL
96f265
 	shp->coshell = sp->coshell;
96f265
@@ -773,7 +772,12 @@ Sfio_t *sh_subshell(Shell_t *shp,Shnode_
96f265
 	if(nsig>0)
96f265
 		kill(getpid(),nsig);
96f265
 	if(sp->subpid)
96f265
+	{
96f265
 		job_wait(sp->subpid);
96f265
+		if(comsub>1)
96f265
+			iounpipe(shp);
96f265
+	}
96f265
+	shp->comsub = sp->comsub;
96f265
 	if(comsub && iop && sp->pipefd<0)
96f265
 		sfseek(iop,(off_t)0,SEEK_SET);
96f265
 	if(shp->trapnote)
96f265
diff -up ksh-20120801/src/cmd/ksh93/sh/xec.c.macro ksh-20120801/src/cmd/ksh93/sh/xec.c
96f265
--- ksh-20120801/src/cmd/ksh93/sh/xec.c.macro	2013-07-04 16:14:05.800595891 +0200
96f265
+++ ksh-20120801/src/cmd/ksh93/sh/xec.c	2013-07-04 16:14:05.810595975 +0200
96f265
@@ -102,11 +102,11 @@ struct funenv
96f265
  * temp file.
96f265
  */
96f265
 static int      subpipe[3],subdup,tsetio,usepipe;
96f265
-static void iounpipe(Shell_t*);
96f265
+void iounpipe(Shell_t*);
96f265
 
96f265
-static int iousepipe(Shell_t *shp)
96f265
+int iousepipe(Shell_t *shp)
96f265
 {
96f265
-	int i;
96f265
+	int fd=sffileno(sfstdout),i,err=errno;
96f265
 	if(usepipe)
96f265
 	{
96f265
 		usepipe++;
96f265
@@ -115,13 +115,18 @@ static int iousepipe(Shell_t *shp)
96f265
 	if(sh_rpipe(subpipe) < 0)
96f265
 		return(0);
96f265
 	usepipe++;
96f265
-	fcntl(subpipe[0],F_SETFD,FD_CLOEXEC);
96f265
-	subpipe[2] = sh_fcntl(1,F_DUPFD,10);
96f265
-	fcntl(subpipe[2],F_SETFD,FD_CLOEXEC);
96f265
+	if(shp->comsub!=1)
96f265
+	{
96f265
+		subpipe[2] = sh_fcntl(subpipe[1],F_DUPFD,10);
96f265
+		sh_close(subpipe[1]);
96f265
+		return(1);
96f265
+	}
96f265
+	subpipe[2] = sh_fcntl(fd,F_dupfd_cloexec,10);
96f265
 	shp->fdstatus[subpipe[2]] = shp->fdstatus[1];
96f265
-	close(1);
96f265
-	fcntl(subpipe[1],F_DUPFD,1);
96f265
-	shp->fdstatus[1] = shp->fdstatus[subpipe[1]];
96f265
+	while(close(fd)<0 && errno==EINTR)
96f265
+		errno = err;
96f265
+	fcntl(subpipe[1],F_DUPFD,fd);
96f265
+	shp->fdstatus[1] = shp->fdstatus[subpipe[1]]&~IOCLEX;
96f265
 	sh_close(subpipe[1]);
96f265
 	if(subdup=shp->subdup) for(i=0; i < 10; i++)
96f265
 	{
96f265
@@ -135,14 +140,23 @@ static int iousepipe(Shell_t *shp)
96f265
 	return(1);
96f265
 }
96f265
 
96f265
-static void iounpipe(Shell_t *shp)
96f265
+void iounpipe(Shell_t *shp)
96f265
 {
96f265
-	int n;
96f265
+	int fd=sffileno(sfstdout),n,err=errno;
96f265
 	char buff[SF_BUFSIZE];
96f265
-	close(1);
96f265
-	fcntl(subpipe[2], F_DUPFD, 1);
96f265
-	shp->fdstatus[1] = shp->fdstatus[subpipe[2]];
96f265
+	if(!usepipe)
96f265
+		return;
96f265
 	--usepipe;
96f265
+	if(shp->comsub>1)
96f265
+	{
96f265
+		sh_close(subpipe[2]);
96f265
+		while(read(subpipe[0],buff,sizeof(buff))>0);
96f265
+		goto done;
96f265
+	}
96f265
+	while(close(fd)<0 && errno==EINTR)
96f265
+		errno = err;
96f265
+	fcntl(subpipe[2], F_DUPFD, fd);
96f265
+	shp->fdstatus[1] = shp->fdstatus[subpipe[2]];
96f265
 	if(subdup) for(n=0; n < 10; n++)
96f265
 	{
96f265
 		if(subdup&(1<
96f265
@@ -174,6 +188,7 @@ static void iounpipe(Shell_t *shp)
96f265
 		else if(errno!=EINTR)
96f265
 			break;
96f265
 	}
96f265
+done:
96f265
 	sh_close(subpipe[0]);
96f265
 	subpipe[0] = -1;
96f265
 	tsetio = 0;
96f265
@@ -725,7 +740,7 @@ static void unset_instance(Namval_t *nq,
96f265
 }
96f265
 
96f265
 #if SHOPT_COSHELL
96f265
-uintmax_t	coused;
96f265
+static uintmax_t	coused;
96f265
 /*
96f265
  * print out function definition
96f265
  */
96f265
@@ -1619,10 +1634,14 @@ int sh_exec(register const Shnode_t *t,
96f265
 			if(shp->subshell)
96f265
 			{
96f265
 				sh_subtmpfile(shp);
96f265
-				if(shp->comsub==1 && !(shp->fdstatus[1]&IONOSEEK))
96f265
-					unpipe=iousepipe(shp);
96f265
 				if((type&(FAMP|TFORK))==(FAMP|TFORK))
96f265
-					sh_subfork();
96f265
+				{
96f265
+					if(shp->comsub && !(shp->fdstatus[1]&IONOSEEK))
96f265
+					{
96f265
+						unpipe = iousepipe(shp);
96f265
+						sh_subfork();
96f265
+					}
96f265
+				}
96f265
 			}
96f265
 			no_fork = !ntflag && !(type&(FAMP|FPOU)) && !shp->subshell &&
96f265
 			    !(shp->st.trapcom[SIGINT] && *shp->st.trapcom[SIGINT]) &&
96f265
@@ -3495,8 +3514,7 @@ static void sh_funct(Shell_t *shp,Namval
96f265
 	struct funenv fun;
96f265
 	char *fname = nv_getval(SH_FUNNAMENOD);
96f265
 	struct Level	*lp =(struct Level*)(SH_LEVELNOD->nvfun);
96f265
-	int		level, pipepid=shp->pipepid, comsub=shp->comsub;
96f265
-	shp->comsub = 0;
96f265
+	int		level, pipepid=shp->pipepid;
96f265
 	shp->pipepid = 0;
96f265
 	sh_stats(STAT_FUNCT);
96f265
 	if(!lp->hdr.disc)
96f265
@@ -3539,7 +3557,6 @@ static void sh_funct(Shell_t *shp,Namval
96f265
 	lp->maxlevel = level;
96f265
 	SH_LEVELNOD->nvalue.s = lp->maxlevel;
96f265
 	shp->last_root = nv_dict(DOTSHNOD);
96f265
-	shp->comsub = comsub;
96f265
 #if 0
96f265
 	nv_putval(SH_FUNNAMENOD,shp->st.funname,NV_NOFREE);
96f265
 #else
76b1d0
diff -up ksh-20120801/src/cmd/ksh93/sh/macro.c.orig ksh-20120801/src/cmd/ksh93/sh/macro.c
76b1d0
--- ksh-20120801/src/cmd/ksh93/sh/macro.c.orig	2012-06-29 20:05:47.000000000 +0200
76b1d0
+++ ksh-20120801/src/cmd/ksh93/sh/macro.c	2013-08-12 18:06:17.291843164 +0200
76b1d0
@@ -2152,6 +2152,11 @@ static void comsubst(Mac_t *mp,register
76b1d0
 	mp->ifsp = nv_getval(np);
76b1d0
 	stkset(stkp,savptr,savtop);
76b1d0
 	newlines = 0;
76b1d0
+	if(type/*==3 - don't break `` vs $() */ && mp->shp->spid)
76b1d0
+	{
76b1d0
+		job_wait(mp->shp->spid);
76b1d0
+		mp->shp->spid = 0;
76b1d0
+	}
76b1d0
 	sfsetbuf(sp,(void*)sp,0);
76b1d0
 	bufsize = sfvalue(sp);
76b1d0
 	/* read command substitution output and put on stack or here-doc */
76b1d0
diff -up ksh-20120801/src/cmd/ksh93/sh/xec.c.orig ksh-20120801/src/cmd/ksh93/sh/xec.c
76b1d0
--- ksh-20120801/src/cmd/ksh93/sh/xec.c.orig	2013-08-12 18:06:57.567497226 +0200
76b1d0
+++ ksh-20120801/src/cmd/ksh93/sh/xec.c	2013-08-12 18:20:36.443454280 +0200
76b1d0
@@ -1734,6 +1734,8 @@ int sh_exec(register const Shnode_t *t,
76b1d0
 					nlock--;
76b1d0
 					job_unlock();
76b1d0
 				}
76b1d0
+				if(shp->subshell)
76b1d0
+					shp->spid = parent;
76b1d0
 				if(type&FPCL)
76b1d0
 					sh_close(shp->inpipe[0]);
76b1d0
 				if(type&(FCOOP|FAMP))