Date: Wed, 6 Apr 2011 19:13:04 +0000 (UTC) From: Edward Tomasz Napierala <trasz@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r220400 - in head/sys: fs/fdescfs kern Message-ID: <201104061913.p36JD4Xb014239@svn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: trasz Date: Wed Apr 6 19:13:04 2011 New Revision: 220400 URL: http://svn.freebsd.org/changeset/base/220400 Log: Add RACCT_NOFILE accounting. Sponsored by: The FreeBSD Foundation Reviewed by: kib (earlier version) Modified: head/sys/fs/fdescfs/fdesc_vfsops.c head/sys/kern/kern_descrip.c Modified: head/sys/fs/fdescfs/fdesc_vfsops.c ============================================================================== --- head/sys/fs/fdescfs/fdesc_vfsops.c Wed Apr 6 19:08:50 2011 (r220399) +++ head/sys/fs/fdescfs/fdesc_vfsops.c Wed Apr 6 19:13:04 2011 (r220400) @@ -47,6 +47,7 @@ #include <sys/malloc.h> #include <sys/mount.h> #include <sys/proc.h> +#include <sys/racct.h> #include <sys/resourcevar.h> #include <sys/vnode.h> @@ -186,6 +187,7 @@ fdesc_statfs(mp, sbp) int i; int last; int freefd; + uint64_t limit; td = curthread; @@ -200,6 +202,9 @@ fdesc_statfs(mp, sbp) PROC_UNLOCK(td->td_proc); fdp = td->td_proc->p_fd; FILEDESC_SLOCK(fdp); + limit = racct_get_limit(td->td_proc, RACCT_NOFILE); + if (lim > limit) + lim = limit; last = min(fdp->fd_nfiles, lim); freefd = 0; for (i = fdp->fd_freefile; i < last; i++) Modified: head/sys/kern/kern_descrip.c ============================================================================== --- head/sys/kern/kern_descrip.c Wed Apr 6 19:08:50 2011 (r220399) +++ head/sys/kern/kern_descrip.c Wed Apr 6 19:13:04 2011 (r220400) @@ -62,6 +62,7 @@ __FBSDID("$FreeBSD$"); #include <sys/priv.h> #include <sys/proc.h> #include <sys/protosw.h> +#include <sys/racct.h> #include <sys/resourcevar.h> #include <sys/signalvar.h> #include <sys/socketvar.h> @@ -276,11 +277,15 @@ int getdtablesize(struct thread *td, struct getdtablesize_args *uap) { struct proc *p = td->td_proc; + uint64_t lim; PROC_LOCK(p); td->td_retval[0] = min((int)lim_cur(p, RLIMIT_NOFILE), maxfilesperproc); + lim = racct_get_limit(td->td_proc, RACCT_NOFILE); PROC_UNLOCK(p); + if (lim < td->td_retval[0]) + td->td_retval[0] = lim; return (0); } @@ -793,8 +798,25 @@ do_dup(struct thread *td, int flags, int * out for a race. */ if (flags & DUP_FIXED) { - if (new >= fdp->fd_nfiles) + if (new >= fdp->fd_nfiles) { + /* + * The resource limits are here instead of e.g. fdalloc(), + * because the file descriptor table may be shared between + * processes, so we can't really use racct_add()/racct_sub(). + * Instead of counting the number of actually allocated + * descriptors, just put the limit on the size of the file + * descriptor table. + */ + PROC_LOCK(p); + error = racct_set(p, RACCT_NOFILE, new + 1); + PROC_UNLOCK(p); + if (error != 0) { + FILEDESC_XUNLOCK(fdp); + fdrop(fp, td); + return (EMFILE); + } fdgrowtable(fdp, new + 1); + } if (fdp->fd_ofiles[new] == NULL) fdused(fdp, new); } else { @@ -1440,7 +1462,7 @@ fdalloc(struct thread *td, int minfd, in { struct proc *p = td->td_proc; struct filedesc *fdp = p->p_fd; - int fd = -1, maxfd; + int fd = -1, maxfd, error; FILEDESC_XLOCK_ASSERT(fdp); @@ -1463,6 +1485,11 @@ fdalloc(struct thread *td, int minfd, in return (EMFILE); if (fd < fdp->fd_nfiles) break; + PROC_LOCK(p); + error = racct_set(p, RACCT_NOFILE, min(fdp->fd_nfiles * 2, maxfd)); + PROC_UNLOCK(p); + if (error != 0) + return (EMFILE); fdgrowtable(fdp, min(fdp->fd_nfiles * 2, maxfd)); } @@ -1494,6 +1521,11 @@ fdavail(struct thread *td, int n) FILEDESC_LOCK_ASSERT(fdp); + /* + * XXX: This is only called from uipc_usrreq.c:unp_externalize(); + * call racct_add() from there instead of dealing with containers + * here. + */ PROC_LOCK(p); lim = min((int)lim_cur(p, RLIMIT_NOFILE), maxfilesperproc); PROC_UNLOCK(p); @@ -1742,6 +1774,10 @@ fdfree(struct thread *td) if (fdp == NULL) return; + PROC_LOCK(td->td_proc); + racct_set(td->td_proc, RACCT_NOFILE, 0); + PROC_UNLOCK(td->td_proc); + /* Check for special need to clear POSIX style locks */ fdtol = td->td_proc->p_fdtol; if (fdtol != NULL) {
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201104061913.p36JD4Xb014239>