Avoid relocking filedesc lock when closing fds during fdp destruction.

Don't call bzero nor fdunused from fdfree for such cases. It would do
unnecessary work and complain that the lock is not taken.

MFC after:	1 week
This commit is contained in:
Mateusz Guzik 2014-07-10 20:59:54 +00:00
parent bfc30490a7
commit e518baf8f9
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=268505

View File

@ -294,18 +294,36 @@ fdunused(struct filedesc *fdp, int fd)
/*
* Free a file descriptor.
*
* Avoid some work if fdp is about to be destroyed.
*/
static inline void
fdfree(struct filedesc *fdp, int fd)
_fdfree(struct filedesc *fdp, int fd, int last)
{
struct filedescent *fde;
fde = &fdp->fd_ofiles[fd];
filecaps_free(&fde->fde_caps);
if (last)
return;
bzero(fde, sizeof(*fde));
fdunused(fdp, fd);
}
static inline void
fdfree(struct filedesc *fdp, int fd)
{
_fdfree(fdp, fd, 0);
}
static inline void
fdfree_last(struct filedesc *fdp, int fd)
{
_fdfree(fdp, fd, 1);
}
/*
* System calls on descriptors.
*/
@ -2011,25 +2029,10 @@ fdescfree(struct thread *td)
FILEDESC_XLOCK(fdp);
i = --fdp->fd_refcnt;
FILEDESC_XUNLOCK(fdp);
if (i > 0)
if (i > 0) {
FILEDESC_XUNLOCK(fdp);
return;
for (i = 0; i <= fdp->fd_lastfile; i++) {
fp = fdp->fd_ofiles[i].fde_file;
if (fp != NULL) {
FILEDESC_XLOCK(fdp);
fdfree(fdp, i);
FILEDESC_XUNLOCK(fdp);
(void) closef(fp, td);
}
}
FILEDESC_XLOCK(fdp);
if (fdp->fd_nfiles > NDFILE)
free(fdp->fd_ofiles, M_FILEDESC);
if (NDSLOTS(fdp->fd_nfiles) > NDSLOTS(NDFILE))
free(fdp->fd_map, M_FILEDESC);
fdp->fd_nfiles = 0;
@ -2041,6 +2044,19 @@ fdescfree(struct thread *td)
fdp->fd_jdir = NULL;
FILEDESC_XUNLOCK(fdp);
for (i = 0; i <= fdp->fd_lastfile; i++) {
fp = fdp->fd_ofiles[i].fde_file;
if (fp != NULL) {
fdfree_last(fdp, i);
(void) closef(fp, td);
}
}
if (fdp->fd_nfiles > NDFILE)
free(fdp->fd_ofiles, M_FILEDESC);
if (NDSLOTS(fdp->fd_nfiles) > NDSLOTS(NDFILE))
free(fdp->fd_map, M_FILEDESC);
if (cdir != NULL)
vrele(cdir);
if (rdir != NULL)