pseudofs_vncache.c (303906) | pseudofs_vncache.c (312248) |
---|---|
1/*- 2 * Copyright (c) 2001 Dag-Erling Co��dan Sm��rgrav 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright --- 13 unchanged lines hidden (view full) --- 22 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 */ 28 29#include <sys/cdefs.h> | 1/*- 2 * Copyright (c) 2001 Dag-Erling Co��dan Sm��rgrav 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright --- 13 unchanged lines hidden (view full) --- 22 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 */ 28 29#include <sys/cdefs.h> |
30__FBSDID("$FreeBSD: stable/11/sys/fs/pseudofs/pseudofs_vncache.c 303906 2016-08-10 12:34:49Z kib $"); | 30__FBSDID("$FreeBSD: stable/11/sys/fs/pseudofs/pseudofs_vncache.c 312248 2017-01-16 00:43:57Z kib $"); |
31 32#include "opt_pseudofs.h" 33 34#include <sys/param.h> 35#include <sys/kernel.h> 36#include <sys/systm.h> 37#include <sys/eventhandler.h> 38#include <sys/lock.h> --- 7 unchanged lines hidden (view full) --- 46#include <fs/pseudofs/pseudofs_internal.h> 47 48static MALLOC_DEFINE(M_PFSVNCACHE, "pfs_vncache", "pseudofs vnode cache"); 49 50static struct mtx pfs_vncache_mutex; 51static struct pfs_vdata *pfs_vncache; 52static eventhandler_tag pfs_exit_tag; 53static void pfs_exit(void *arg, struct proc *p); | 31 32#include "opt_pseudofs.h" 33 34#include <sys/param.h> 35#include <sys/kernel.h> 36#include <sys/systm.h> 37#include <sys/eventhandler.h> 38#include <sys/lock.h> --- 7 unchanged lines hidden (view full) --- 46#include <fs/pseudofs/pseudofs_internal.h> 47 48static MALLOC_DEFINE(M_PFSVNCACHE, "pfs_vncache", "pseudofs vnode cache"); 49 50static struct mtx pfs_vncache_mutex; 51static struct pfs_vdata *pfs_vncache; 52static eventhandler_tag pfs_exit_tag; 53static void pfs_exit(void *arg, struct proc *p); |
54static void pfs_purge_locked(struct pfs_node *pn, bool force); |
|
54 55static SYSCTL_NODE(_vfs_pfs, OID_AUTO, vncache, CTLFLAG_RW, 0, 56 "pseudofs vnode cache"); 57 58static int pfs_vncache_entries; 59SYSCTL_INT(_vfs_pfs_vncache, OID_AUTO, entries, CTLFLAG_RD, 60 &pfs_vncache_entries, 0, 61 "number of entries in the vnode cache"); --- 30 unchanged lines hidden (view full) --- 92/* 93 * Tear down vnode cache 94 */ 95void 96pfs_vncache_unload(void) 97{ 98 99 EVENTHANDLER_DEREGISTER(process_exit, pfs_exit_tag); | 55 56static SYSCTL_NODE(_vfs_pfs, OID_AUTO, vncache, CTLFLAG_RW, 0, 57 "pseudofs vnode cache"); 58 59static int pfs_vncache_entries; 60SYSCTL_INT(_vfs_pfs_vncache, OID_AUTO, entries, CTLFLAG_RD, 61 &pfs_vncache_entries, 0, 62 "number of entries in the vnode cache"); --- 30 unchanged lines hidden (view full) --- 93/* 94 * Tear down vnode cache 95 */ 96void 97pfs_vncache_unload(void) 98{ 99 100 EVENTHANDLER_DEREGISTER(process_exit, pfs_exit_tag); |
101 mtx_lock(&pfs_vncache_mutex); 102 pfs_purge_locked(NULL, true); 103 mtx_unlock(&pfs_vncache_mutex); |
|
100 KASSERT(pfs_vncache_entries == 0, 101 ("%d vncache entries remaining", pfs_vncache_entries)); 102 mtx_destroy(&pfs_vncache_mutex); 103} 104 105/* 106 * Allocate a vnode 107 */ --- 159 unchanged lines hidden (view full) --- 267 * assumptions about the state of the cache after vgone() returns. In 268 * consequence, we must start over after every vgone() call, and keep 269 * trying until we manage to traverse the entire cache. 270 * 271 * The only way to improve this situation is to change the data structure 272 * used to implement the cache. 273 */ 274static void | 104 KASSERT(pfs_vncache_entries == 0, 105 ("%d vncache entries remaining", pfs_vncache_entries)); 106 mtx_destroy(&pfs_vncache_mutex); 107} 108 109/* 110 * Allocate a vnode 111 */ --- 159 unchanged lines hidden (view full) --- 271 * assumptions about the state of the cache after vgone() returns. In 272 * consequence, we must start over after every vgone() call, and keep 273 * trying until we manage to traverse the entire cache. 274 * 275 * The only way to improve this situation is to change the data structure 276 * used to implement the cache. 277 */ 278static void |
275pfs_purge_locked(struct pfs_node *pn) | 279pfs_purge_locked(struct pfs_node *pn, bool force) |
276{ 277 struct pfs_vdata *pvd; 278 struct vnode *vnp; 279 280 mtx_assert(&pfs_vncache_mutex, MA_OWNED); 281 pvd = pfs_vncache; 282 while (pvd != NULL) { | 280{ 281 struct pfs_vdata *pvd; 282 struct vnode *vnp; 283 284 mtx_assert(&pfs_vncache_mutex, MA_OWNED); 285 pvd = pfs_vncache; 286 while (pvd != NULL) { |
283 if (pvd->pvd_dead || (pn != NULL && pvd->pvd_pn == pn)) { | 287 if (force || pvd->pvd_dead || 288 (pn != NULL && pvd->pvd_pn == pn)) { |
284 vnp = pvd->pvd_vnode; 285 vhold(vnp); 286 mtx_unlock(&pfs_vncache_mutex); 287 VOP_LOCK(vnp, LK_EXCLUSIVE); 288 vgone(vnp); 289 VOP_UNLOCK(vnp, 0); 290 mtx_lock(&pfs_vncache_mutex); 291 vdrop(vnp); --- 4 unchanged lines hidden (view full) --- 296 } 297} 298 299void 300pfs_purge(struct pfs_node *pn) 301{ 302 303 mtx_lock(&pfs_vncache_mutex); | 289 vnp = pvd->pvd_vnode; 290 vhold(vnp); 291 mtx_unlock(&pfs_vncache_mutex); 292 VOP_LOCK(vnp, LK_EXCLUSIVE); 293 vgone(vnp); 294 VOP_UNLOCK(vnp, 0); 295 mtx_lock(&pfs_vncache_mutex); 296 vdrop(vnp); --- 4 unchanged lines hidden (view full) --- 301 } 302} 303 304void 305pfs_purge(struct pfs_node *pn) 306{ 307 308 mtx_lock(&pfs_vncache_mutex); |
304 pfs_purge_locked(pn); | 309 pfs_purge_locked(pn, false); |
305 mtx_unlock(&pfs_vncache_mutex); 306} 307 308/* 309 * Free all vnodes associated with a defunct process 310 */ 311static void 312pfs_exit(void *arg, struct proc *p) 313{ 314 struct pfs_vdata *pvd; 315 int dead; 316 317 if (pfs_vncache == NULL) 318 return; 319 mtx_lock(&pfs_vncache_mutex); 320 for (pvd = pfs_vncache, dead = 0; pvd != NULL; pvd = pvd->pvd_next) 321 if (pvd->pvd_pid == p->p_pid) 322 dead = pvd->pvd_dead = 1; 323 if (dead) | 310 mtx_unlock(&pfs_vncache_mutex); 311} 312 313/* 314 * Free all vnodes associated with a defunct process 315 */ 316static void 317pfs_exit(void *arg, struct proc *p) 318{ 319 struct pfs_vdata *pvd; 320 int dead; 321 322 if (pfs_vncache == NULL) 323 return; 324 mtx_lock(&pfs_vncache_mutex); 325 for (pvd = pfs_vncache, dead = 0; pvd != NULL; pvd = pvd->pvd_next) 326 if (pvd->pvd_pid == p->p_pid) 327 dead = pvd->pvd_dead = 1; 328 if (dead) |
324 pfs_purge_locked(NULL); | 329 pfs_purge_locked(NULL, false); |
325 mtx_unlock(&pfs_vncache_mutex); 326} | 330 mtx_unlock(&pfs_vncache_mutex); 331} |