mirror of
git://git.code.sf.net/p/cdesktopenv/code
synced 2025-02-13 11:42:21 +00:00
Simplify SHOPT_SPAWN procsub file descriptor leak fix (re: 6d63b57d
)
Before the fix, a file descriptor leak could occur on command not found because sh_ntfork() saves sh.topfd on function entry (as part of the sh_pushcontext() macro expansion) and uses that value to sh_iorestore(). Process substitution arguments will already have been processed by then and their file descriptors opened, so those were not closed on restore. To compensate, the committed fix added a second sh_iorestore() call using the topfd variable, in which sh_exec) saves the value of sh.topfd on its function entry. A more elegant fix is to pass that value to sh_ntfork() as an argument so its own sh_iorestore() call does the right thing.
This commit is contained in:
parent
1884f57a74
commit
a43bb4f1bd
1 changed files with 5 additions and 9 deletions
|
@ -65,7 +65,7 @@
|
|||
extern int nice(int);
|
||||
#endif /* _lib_nice */
|
||||
#if SHOPT_SPAWN
|
||||
static pid_t sh_ntfork(const Shnode_t*,char*[],int*);
|
||||
static pid_t sh_ntfork(const Shnode_t*,char*[],int*,int);
|
||||
#endif /* SHOPT_SPAWN */
|
||||
|
||||
static void sh_funct(Namval_t*, int, char*[], struct argnod*,int);
|
||||
|
@ -1517,13 +1517,9 @@ int sh_exec(register const Shnode_t *t, int flags)
|
|||
if(com && !job.jobcontrol)
|
||||
#endif /* _use_ntfork_tcpgrp */
|
||||
{
|
||||
parent = sh_ntfork(t,com,&jobid);
|
||||
parent = sh_ntfork(t,com,&jobid,topfd);
|
||||
if(parent<0)
|
||||
{
|
||||
if(sh.topfd > topfd)
|
||||
sh_iorestore(topfd,0); /* prevent FD leak from 'not found' */
|
||||
break;
|
||||
}
|
||||
}
|
||||
else
|
||||
#endif /* SHOPT_SPAWN */
|
||||
|
@ -3389,7 +3385,7 @@ static void sigreset(int mode)
|
|||
* Incompatible with job control on interactive shells (job.jobcontrol) if
|
||||
* the system does not support posix_spawn_file_actions_addtcsetpgrp_np().
|
||||
*/
|
||||
static pid_t sh_ntfork(const Shnode_t *t,char *argv[],int *jobid)
|
||||
static pid_t sh_ntfork(const Shnode_t *t,char *argv[],int *jobid,int topfd)
|
||||
{
|
||||
static pid_t spawnpid;
|
||||
struct checkpt *buffp = (struct checkpt*)stkalloc(sh.stk,sizeof(struct checkpt));
|
||||
|
@ -3559,8 +3555,8 @@ static pid_t sh_ntfork(const Shnode_t *t,char *argv[],int *jobid)
|
|||
if(jmpval==SH_JMPSCRIPT)
|
||||
nv_setlist(t->com.comset,NV_EXPORT|NV_IDENT|NV_ASSIGN,0);
|
||||
}
|
||||
if(t->com.comio && (jmpval || spawnpid<=0))
|
||||
sh_iorestore(buffp->topfd,jmpval);
|
||||
if(t->com.comio && (jmpval || spawnpid<=0) && sh.topfd > topfd)
|
||||
sh_iorestore(topfd,jmpval);
|
||||
if(jmpval>SH_JMPCMD)
|
||||
siglongjmp(*sh.jmplist,jmpval);
|
||||
if(spawnpid>0)
|
||||
|
|
Loading…
Reference in a new issue