mirror of
https://git.FreeBSD.org/src.git
synced 2025-01-07 13:14:51 +00:00
There is only one caller of the dupfdopen() function, so we can simplify
it a bit: - We can assert that only ENODEV and ENXIO errors are passed instead of handling other errors. - The caller always call finstall() for indx descriptor, so we can assume it is set. Actually the filedesc lock is dropped between finstall() and dupfdopen(), so there is a window there for another thread to close the indx descriptor, but it will be closed in next commit. Reviewed by: mjg MFC after: 1 month
This commit is contained in:
parent
6ae742a549
commit
6195bfebcc
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=237016
@ -2593,6 +2593,9 @@ dupfdopen(struct thread *td, struct filedesc *fdp, int indx, int dfd, int mode,
|
||||
struct file *wfp;
|
||||
struct file *fp;
|
||||
|
||||
KASSERT(error == ENODEV || error == ENXIO,
|
||||
("unexpected error %d in %s", error, __func__));
|
||||
|
||||
/*
|
||||
* If the to-be-dup'd fd number is greater than the allowed number
|
||||
* of file descriptors, or the fd to be dup'd has already been
|
||||
@ -2612,9 +2615,8 @@ dupfdopen(struct thread *td, struct filedesc *fdp, int indx, int dfd, int mode,
|
||||
*
|
||||
* For ENXIO steal away the file structure from (dfd) and store it in
|
||||
* (indx). (dfd) is effectively closed by this operation.
|
||||
*
|
||||
* Any other error code is just returned.
|
||||
*/
|
||||
fp = fdp->fd_ofiles[indx];
|
||||
switch (error) {
|
||||
case ENODEV:
|
||||
/*
|
||||
@ -2625,48 +2627,28 @@ dupfdopen(struct thread *td, struct filedesc *fdp, int indx, int dfd, int mode,
|
||||
FILEDESC_XUNLOCK(fdp);
|
||||
return (EACCES);
|
||||
}
|
||||
fp = fdp->fd_ofiles[indx];
|
||||
fdp->fd_ofiles[indx] = wfp;
|
||||
fdp->fd_ofileflags[indx] = fdp->fd_ofileflags[dfd];
|
||||
if (fp == NULL)
|
||||
fdused(fdp, indx);
|
||||
fhold(wfp);
|
||||
FILEDESC_XUNLOCK(fdp);
|
||||
if (fp != NULL)
|
||||
/*
|
||||
* We now own the reference to fp that the ofiles[]
|
||||
* array used to own. Release it.
|
||||
*/
|
||||
fdrop(fp, td);
|
||||
return (0);
|
||||
|
||||
break;
|
||||
case ENXIO:
|
||||
/*
|
||||
* Steal away the file pointer from dfd and stuff it into indx.
|
||||
*/
|
||||
fp = fdp->fd_ofiles[indx];
|
||||
fdp->fd_ofiles[indx] = fdp->fd_ofiles[dfd];
|
||||
fdp->fd_ofiles[indx] = wfp;
|
||||
fdp->fd_ofiles[dfd] = NULL;
|
||||
fdp->fd_ofileflags[indx] = fdp->fd_ofileflags[dfd];
|
||||
fdp->fd_ofileflags[dfd] = 0;
|
||||
fdunused(fdp, dfd);
|
||||
if (fp == NULL)
|
||||
fdused(fdp, indx);
|
||||
FILEDESC_XUNLOCK(fdp);
|
||||
|
||||
/*
|
||||
* We now own the reference to fp that the ofiles[] array
|
||||
* used to own. Release it.
|
||||
*/
|
||||
if (fp != NULL)
|
||||
fdrop(fp, td);
|
||||
return (0);
|
||||
|
||||
default:
|
||||
FILEDESC_XUNLOCK(fdp);
|
||||
return (error);
|
||||
break;
|
||||
}
|
||||
/* NOTREACHED */
|
||||
FILEDESC_XUNLOCK(fdp);
|
||||
/*
|
||||
* We now own the reference to fp that the ofiles[] array used to own.
|
||||
* Release it.
|
||||
*/
|
||||
fdrop(fp, td);
|
||||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
|
Loading…
Reference in New Issue
Block a user