Mercurial > illumos > illumos-gate
changeset 12151:a78c082f61ab
6867268 sol10 on T2000: vn_rele: vnode ref count 0
author | Milan Cermak <Milan.Cermak@Sun.COM> |
---|---|
date | Tue, 13 Apr 2010 08:51:42 +0200 |
parents | 4af87752eaf2 |
children | c0b746bffad6 |
files | usr/src/uts/common/syscall/fcntl.c |
diffstat | 1 files changed, 22 insertions(+), 7 deletions(-) [+] |
line wrap: on
line diff
--- a/usr/src/uts/common/syscall/fcntl.c Mon Apr 12 23:02:08 2010 -0700 +++ b/usr/src/uts/common/syscall/fcntl.c Tue Apr 13 08:51:42 2010 +0200 @@ -21,8 +21,7 @@ /* ONC_PLUS EXTRACT START */ /* - * Copyright 2010 Sun Microsystems, Inc. All rights reserved. - * Use is subject to license terms. + * Copyright (c) 1994, 2010, Oracle and/or its affiliates. All rights reserved. */ /* Copyright (c) 1983, 1984, 1985, 1986, 1987, 1988, 1989 AT&T */ @@ -149,12 +148,28 @@ if (iarg >= 0) fd_too_big(p); error = EINVAL; - } else if ((retval = ufalloc_file(iarg, fp)) == -1) { + goto done; + } + /* + * We need to increment the f_count reference counter + * before allocating a new file descriptor. + * Doing it other way round opens a window for race condition + * with closeandsetf() on the target file descriptor which can + * close the file still referenced by the original + * file descriptor. + */ + mutex_enter(&fp->f_tlock); + fp->f_count++; + mutex_exit(&fp->f_tlock); + if ((retval = ufalloc_file(iarg, fp)) == -1) { + /* + * New file descriptor can't be allocated. + * Revert the reference count. + */ + mutex_enter(&fp->f_tlock); + fp->f_count--; + mutex_exit(&fp->f_tlock); error = EMFILE; - } else { - mutex_enter(&fp->f_tlock); - fp->f_count++; - mutex_exit(&fp->f_tlock); } goto done;