Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files. =================================================================== RCS file: /ftp/cvs/cvsroot/src/sys/kern/subr_pool.c,v rcsdiff: /ftp/cvs/cvsroot/src/sys/kern/subr_pool.c,v: warning: Unknown phrases like `commitid ...;' are present. retrieving revision 1.165 retrieving revision 1.170.2.2 diff -u -p -r1.165 -r1.170.2.2 --- src/sys/kern/subr_pool.c 2008/07/07 12:27:19 1.165 +++ src/sys/kern/subr_pool.c 2009/04/28 07:37:00 1.170.2.2 @@ -1,4 +1,4 @@ -/* $NetBSD: subr_pool.c,v 1.165 2008/07/07 12:27:19 yamt Exp $ */ +/* $NetBSD: subr_pool.c,v 1.170.2.2 2009/04/28 07:37:00 skrll Exp $ */ /*- * Copyright (c) 1997, 1999, 2000, 2002, 2007, 2008 The NetBSD Foundation, Inc. @@ -31,7 +31,7 @@ */ #include -__KERNEL_RCSID(0, "$NetBSD: subr_pool.c,v 1.165 2008/07/07 12:27:19 yamt Exp $"); +__KERNEL_RCSID(0, "$NetBSD: subr_pool.c,v 1.170.2.2 2009/04/28 07:37:00 skrll Exp $"); #include "opt_ddb.h" #include "opt_pool.h" @@ -180,7 +180,7 @@ TAILQ_HEAD(,pool_cache) pool_cache_head TAILQ_HEAD_INITIALIZER(pool_cache_head); int pool_cache_disable; /* global disable for caching */ -static pcg_t pcg_dummy; /* zero sized: always empty, yet always full */ +static const pcg_t pcg_dummy; /* zero sized: always empty, yet always full */ static bool pool_cache_put_slow(pool_cache_cpu_t *, int, void *); @@ -864,7 +864,7 @@ pool_init(struct pool *pp, size_t size, if (__predict_true(!cold)) mutex_exit(&pool_head_lock); - /* Insert this into the list of pools using this allocator. */ + /* Insert this into the list of pools using this allocator. */ if (__predict_true(!cold)) mutex_enter(&palloc->pa_lock); TAILQ_INSERT_TAIL(&palloc->pa_list, pp, pr_alloc_list); @@ -1253,10 +1253,7 @@ pool_do_put(struct pool *pp, void *v, st if (pp->pr_flags & PR_WANTED) { pp->pr_flags &= ~PR_WANTED; - if (ph->ph_nmissing == 0) - pp->pr_nidle++; cv_broadcast(&pp->pr_cv); - return; } /* @@ -1530,6 +1527,8 @@ pool_update_curpage(struct pool *pp) if (pp->pr_curpage == NULL) { pp->pr_curpage = LIST_FIRST(&pp->pr_emptypages); } + KASSERT((pp->pr_curpage == NULL && pp->pr_nitems == 0) || + (pp->pr_curpage != NULL && pp->pr_nitems > 0)); } void @@ -2211,8 +2210,8 @@ pool_cache_cpu_init1(struct cpu_info *ci cc->cc_cpuindex = index; cc->cc_hits = 0; cc->cc_misses = 0; - cc->cc_current = &pcg_dummy; - cc->cc_previous = &pcg_dummy; + cc->cc_current = __UNCONST(&pcg_dummy); + cc->cc_previous = __UNCONST(&pcg_dummy); pc->pc_cpus[index] = cc; } @@ -2370,6 +2369,9 @@ pool_cache_get_slow(pool_cache_cpu_t *cc pool_cache_t pc; void *object; + KASSERT(cc->cc_current->pcg_avail == 0); + KASSERT(cc->cc_previous->pcg_avail == 0); + pc = cc->cc_cache; cc->cc_misses++; @@ -2522,9 +2524,27 @@ pool_cache_put_slow(pool_cache_cpu_t *cc uint64_t ncsw; pool_cache_t pc; + KASSERT(cc->cc_current->pcg_avail == cc->cc_current->pcg_size); + KASSERT(cc->cc_previous->pcg_avail == cc->cc_previous->pcg_size); + pc = cc->cc_cache; + pcg = NULL; cc->cc_misses++; + /* + * If there are no empty groups in the cache then allocate one + * while still unlocked. + */ + if (__predict_false(pc->pc_emptygroups == NULL)) { + if (__predict_true(!pool_cache_disable)) { + pcg = pool_get(pc->pc_pcgpool, PR_NOWAIT); + } + if (__predict_true(pcg != NULL)) { + pcg->pcg_avail = 0; + pcg->pcg_size = pc->pc_pcgsize; + } + } + /* Lock the cache. */ if (__predict_false(!mutex_tryenter(&pc->pc_lock))) { ncsw = curlwp->l_ncsw; @@ -2537,20 +2557,16 @@ pool_cache_put_slow(pool_cache_cpu_t *cc */ if (__predict_false(curlwp->l_ncsw != ncsw)) { mutex_exit(&pc->pc_lock); + if (pcg != NULL) { + pool_put(pc->pc_pcgpool, pcg); + } return true; } } /* If there are no empty groups in the cache then allocate one. */ - if (__predict_false((pcg = pc->pc_emptygroups) == NULL)) { - if (__predict_true(!pool_cache_disable)) { - pcg = pool_get(pc->pc_pcgpool, PR_NOWAIT); - } - if (__predict_true(pcg != NULL)) { - pcg->pcg_avail = 0; - pcg->pcg_size = pc->pc_pcgsize; - } - } else { + if (pcg == NULL && pc->pc_emptygroups != NULL) { + pcg = pc->pc_emptygroups; pc->pc_emptygroups = pcg->pcg_next; pc->pc_nempty--; } @@ -2605,6 +2621,7 @@ pool_cache_put_paddr(pool_cache_t pc, vo pcg_t *pcg; int s; + KASSERT(object != NULL); FREECHECK_IN(&pc->pc_freecheck, object); /* Lock out interrupts and disable preemption. */ @@ -2661,9 +2678,9 @@ pool_cache_xcall(pool_cache_t pc) mutex_enter(&pc->pc_lock); cc = pc->pc_cpus[curcpu()->ci_index]; cur = cc->cc_current; - cc->cc_current = &pcg_dummy; + cc->cc_current = __UNCONST(&pcg_dummy); prev = cc->cc_previous; - cc->cc_previous = &pcg_dummy; + cc->cc_previous = __UNCONST(&pcg_dummy); if (cur != &pcg_dummy) { if (cur->pcg_avail == cur->pcg_size) { list = &pc->pc_fullgroups; @@ -2977,7 +2994,7 @@ found: if (pool_in_cg(pp, cc->cc_current, addr) || pool_in_cg(pp, cc->cc_previous, addr)) { struct cpu_info *ci = - cpu_lookup_byindex(i); + cpu_lookup(i); incpucache = true; snprintf(cpucachestr,