kernel - Change allocvnode() to not recursively block freeing vnodes
authorMatthew Dillon <dillon@apollo.backplane.com>
Sat, 8 Dec 2012 02:52:30 +0000 (18:52 -0800)
committerMatthew Dillon <dillon@apollo.backplane.com>
Fri, 14 Dec 2012 03:13:24 +0000 (19:13 -0800)
commit3dc54cbd317ca29e0cd0e5b0ed07668ca3307280
tree9a94c900072846a084bb3b128f98a6a72d421e6e
parentbfbb2132a079ca54cc1fa53d20df0cc3fba3be3d
kernel - Change allocvnode() to not recursively block freeing vnodes

allocvnode() has caused many deadlock issues over the years, including
recent issues with softupdates, because it is often called from deep
within VFS modules and attempts to clean and free unrelated vnodes when
the vnode limit is reached to make room for the new one.

* numvnodes is not protected by any locks and needs atomic ops.

* Change allocvnode() to always allocate and not attempt to free
  other vnodes.

* allocvnode() now flags the LWP to handle reducing the number of vnodes
  in the system as of when it returns to userland instead.  Consolidate
  several flags into a single conditional function call, lwpuserret().

  When triggered, this code will do a limited scan of the free list to
  try to find vnodes to free.

* The vnlru_proc_wait() code existed to handle a separate algorithm
  related to vnodes with cached buffers and VM pages but represented
  a major bottleneck in the system.

  Remove vnlru_proc_wait() and allow vnodes with buffers and/or non-empty
  VM objects to be placed on the free list.

  This also requires not vhold()ing the vnode for related buffer cache
  buffer since the vnode will not go away until related buffers have been
  cleaned out.  We shouldn't need those holds.

Testing-by: vsrinivas
sys/kern/kern_proc.c
sys/kern/vfs_lock.c
sys/kern/vfs_mount.c
sys/kern/vfs_subr.c
sys/platform/pc32/i386/trap.c
sys/platform/pc64/x86_64/trap.c
sys/platform/vkernel/i386/trap.c
sys/platform/vkernel64/x86_64/trap.c
sys/sys/proc.h
sys/sys/vnode.h