| version 1.112.2.5, 2006/08/11 15:45:46 |
version 1.112.2.6, 2006/09/03 15:25:22 |
| Line 364 pr_item_notouch_get(const struct pool *p |
|
| Line 364 pr_item_notouch_get(const struct pool *p |
|
| static inline int |
static inline int |
| phtree_compare(struct pool_item_header *a, struct pool_item_header *b) |
phtree_compare(struct pool_item_header *a, struct pool_item_header *b) |
| { |
{ |
| |
|
| |
/* |
| |
* we consider pool_item_header with smaller ph_page bigger. |
| |
* (this unnatural ordering is for the benefit of pr_find_pagehead.) |
| |
*/ |
| |
|
| if (a->ph_page < b->ph_page) |
if (a->ph_page < b->ph_page) |
| return (-1); |
|
| else if (a->ph_page > b->ph_page) |
|
| return (1); |
return (1); |
| |
else if (a->ph_page > b->ph_page) |
| |
return (-1); |
| else |
else |
| return (0); |
return (0); |
| } |
} |
| Line 376 SPLAY_PROTOTYPE(phtree, pool_item_header |
|
| Line 382 SPLAY_PROTOTYPE(phtree, pool_item_header |
|
| SPLAY_GENERATE(phtree, pool_item_header, ph_node, phtree_compare); |
SPLAY_GENERATE(phtree, pool_item_header, ph_node, phtree_compare); |
| |
|
| /* |
/* |
| * Return the pool page header based on page address. |
* Return the pool page header based on item address. |
| */ |
*/ |
| static inline struct pool_item_header * |
static inline struct pool_item_header * |
| pr_find_pagehead(struct pool *pp, caddr_t page) |
pr_find_pagehead(struct pool *pp, void *v) |
| { |
{ |
| struct pool_item_header *ph, tmp; |
struct pool_item_header *ph, tmp; |
| |
|
| if ((pp->pr_roflags & PR_PHINPAGE) != 0) |
if ((pp->pr_roflags & PR_NOALIGN) != 0) { |
| return ((struct pool_item_header *)(page + pp->pr_phoffset)); |
tmp.ph_page = (caddr_t)(uintptr_t)v; |
| |
ph = SPLAY_FIND(phtree, &pp->pr_phtree, &tmp); |
| |
if (ph == NULL) { |
| |
ph = SPLAY_ROOT(&pp->pr_phtree); |
| |
if (ph != NULL && phtree_compare(&tmp, ph) >= 0) { |
| |
ph = SPLAY_NEXT(phtree, &pp->pr_phtree, ph); |
| |
} |
| |
KASSERT(ph == NULL || phtree_compare(&tmp, ph) < 0); |
| |
} |
| |
} else { |
| |
caddr_t page = |
| |
(caddr_t)((uintptr_t)v & pp->pr_alloc->pa_pagemask); |
| |
|
| |
if ((pp->pr_roflags & PR_PHINPAGE) != 0) { |
| |
ph = (void *)(page + pp->pr_phoffset); |
| |
} else { |
| |
tmp.ph_page = page; |
| |
ph = SPLAY_FIND(phtree, &pp->pr_phtree, &tmp); |
| |
} |
| |
} |
| |
|
| tmp.ph_page = page; |
KASSERT(ph == NULL || ((pp->pr_roflags & PR_PHINPAGE) != 0) || |
| ph = SPLAY_FIND(phtree, &pp->pr_phtree, &tmp); |
(ph->ph_page <= (char *)v && |
| |
(char *)v < ph->ph_page + pp->pr_alloc->pa_pagesz)); |
| return ph; |
return ph; |
| } |
} |
| |
|
| Line 611 pool_init(struct pool *pp, size_t size, |
|
| Line 637 pool_init(struct pool *pp, size_t size, |
|
| if (align == 0) |
if (align == 0) |
| align = ALIGN(1); |
align = ALIGN(1); |
| |
|
| if (size < sizeof(struct pool_item)) |
if ((flags & PR_NOTOUCH) == 0 && size < sizeof(struct pool_item)) |
| size = sizeof(struct pool_item); |
size = sizeof(struct pool_item); |
| |
|
| size = roundup(size, align); |
size = roundup(size, align); |
| #ifdef DIAGNOSTIC |
#ifdef DIAGNOSTIC |
| if (size > palloc->pa_pagesz) |
if (size > palloc->pa_pagesz) |
| panic("pool_init: pool item size (%lu) too large", |
panic("pool_init: pool item size (%zu) too large", size); |
| (u_long)size); |
|
| #endif |
#endif |
| |
|
| /* |
/* |
| Line 667 pool_init(struct pool *pp, size_t size, |
|
| Line 692 pool_init(struct pool *pp, size_t size, |
|
| /* See the comment below about reserved bytes. */ |
/* See the comment below about reserved bytes. */ |
| trysize = palloc->pa_pagesz - ((align - ioff) % align); |
trysize = palloc->pa_pagesz - ((align - ioff) % align); |
| phsize = ALIGN(sizeof(struct pool_item_header)); |
phsize = ALIGN(sizeof(struct pool_item_header)); |
| if ((pp->pr_roflags & PR_NOTOUCH) == 0 && |
if ((pp->pr_roflags & (PR_NOTOUCH | PR_NOALIGN)) == 0 && |
| (pp->pr_size < MIN(palloc->pa_pagesz / 16, phsize << 3) || |
(pp->pr_size < MIN(palloc->pa_pagesz / 16, phsize << 3) || |
| trysize / pp->pr_size == (trysize - phsize) / pp->pr_size)) { |
trysize / pp->pr_size == (trysize - phsize) / pp->pr_size)) { |
| /* Use the end of the page for the page header */ |
/* Use the end of the page for the page header */ |
| Line 1121 pool_do_put(struct pool *pp, void *v, st |
|
| Line 1146 pool_do_put(struct pool *pp, void *v, st |
|
| { |
{ |
| struct pool_item *pi = v; |
struct pool_item *pi = v; |
| struct pool_item_header *ph; |
struct pool_item_header *ph; |
| caddr_t page; |
|
| |
|
| LOCK_ASSERT(simple_lock_held(&pp->pr_slock)); |
LOCK_ASSERT(simple_lock_held(&pp->pr_slock)); |
| SCHED_ASSERT_UNLOCKED(); |
SCHED_ASSERT_UNLOCKED(); |
| |
|
| page = (caddr_t)((u_long)v & pp->pr_alloc->pa_pagemask); |
|
| |
|
| #ifdef DIAGNOSTIC |
#ifdef DIAGNOSTIC |
| if (__predict_false(pp->pr_nout == 0)) { |
if (__predict_false(pp->pr_nout == 0)) { |
| printf("pool %s: putting with none out\n", |
printf("pool %s: putting with none out\n", |
| Line 1136 pool_do_put(struct pool *pp, void *v, st |
|
| Line 1158 pool_do_put(struct pool *pp, void *v, st |
|
| } |
} |
| #endif |
#endif |
| |
|
| if (__predict_false((ph = pr_find_pagehead(pp, page)) == NULL)) { |
if (__predict_false((ph = pr_find_pagehead(pp, v)) == NULL)) { |
| pr_printlog(pp, NULL, printf); |
pr_printlog(pp, NULL, printf); |
| panic("pool_put: %s: page header missing", pp->pr_wchan); |
panic("pool_put: %s: page header missing", pp->pr_wchan); |
| } |
} |
| Line 1356 pool_prime_page(struct pool *pp, caddr_t |
|
| Line 1378 pool_prime_page(struct pool *pp, caddr_t |
|
| LOCK_ASSERT(simple_lock_held(&pp->pr_slock)); |
LOCK_ASSERT(simple_lock_held(&pp->pr_slock)); |
| |
|
| #ifdef DIAGNOSTIC |
#ifdef DIAGNOSTIC |
| if (((u_long)cp & (pp->pr_alloc->pa_pagesz - 1)) != 0) |
if ((pp->pr_roflags & PR_NOALIGN) == 0 && |
| |
((uintptr_t)cp & (pp->pr_alloc->pa_pagesz - 1)) != 0) |
| panic("pool_prime_page: %s: unaligned page", pp->pr_wchan); |
panic("pool_prime_page: %s: unaligned page", pp->pr_wchan); |
| #endif |
#endif |
| |
|
| Line 1763 pool_print1(struct pool *pp, const char |
|
| Line 1786 pool_print1(struct pool *pp, const char |
|
| (*pr)("\n"); |
(*pr)("\n"); |
| if ((pp->pr_roflags & PR_LOGGING) == 0) |
if ((pp->pr_roflags & PR_LOGGING) == 0) |
| (*pr)("\tno log\n"); |
(*pr)("\tno log\n"); |
| else |
else { |
| pr_printlog(pp, NULL, pr); |
pr_printlog(pp, NULL, pr); |
| |
} |
| |
|
| skip_log: |
skip_log: |
| if (print_cache == 0) |
if (print_cache == 0) |
| Line 1815 pool_chk_page(struct pool *pp, const cha |
|
| Line 1839 pool_chk_page(struct pool *pp, const cha |
|
| caddr_t page; |
caddr_t page; |
| int n; |
int n; |
| |
|
| page = (caddr_t)((u_long)ph & pp->pr_alloc->pa_pagemask); |
if ((pp->pr_roflags & PR_NOALIGN) == 0) { |
| if (page != ph->ph_page && |
page = (caddr_t)((uintptr_t)ph & pp->pr_alloc->pa_pagemask); |
| (pp->pr_roflags & PR_PHINPAGE) != 0) { |
if (page != ph->ph_page && |
| if (label != NULL) |
(pp->pr_roflags & PR_PHINPAGE) != 0) { |
| printf("%s: ", label); |
if (label != NULL) |
| printf("pool(%p:%s): page inconsistency: page %p;" |
printf("%s: ", label); |
| " at page head addr %p (p %p)\n", pp, |
printf("pool(%p:%s): page inconsistency: page %p;" |
| pp->pr_wchan, ph->ph_page, |
" at page head addr %p (p %p)\n", pp, |
| ph, page); |
pp->pr_wchan, ph->ph_page, |
| return 1; |
ph, page); |
| |
return 1; |
| |
} |
| } |
} |
| |
|
| if ((pp->pr_roflags & PR_NOTOUCH) != 0) |
if ((pp->pr_roflags & PR_NOTOUCH) != 0) |
| Line 1839 pool_chk_page(struct pool *pp, const cha |
|
| Line 1865 pool_chk_page(struct pool *pp, const cha |
|
| if (label != NULL) |
if (label != NULL) |
| printf("%s: ", label); |
printf("%s: ", label); |
| printf("pool(%s): free list modified: magic=%x;" |
printf("pool(%s): free list modified: magic=%x;" |
| " page %p; item ordinal %d;" |
" page %p; item ordinal %d; addr %p\n", |
| " addr %p (p %p)\n", |
|
| pp->pr_wchan, pi->pi_magic, ph->ph_page, |
pp->pr_wchan, pi->pi_magic, ph->ph_page, |
| n, pi, page); |
n, pi); |
| panic("pool"); |
panic("pool"); |
| } |
} |
| #endif |
#endif |
| page = |
if ((pp->pr_roflags & PR_NOALIGN) != 0) { |
| (caddr_t)((u_long)pi & pp->pr_alloc->pa_pagemask); |
continue; |
| |
} |
| |
page = (caddr_t)((uintptr_t)pi & pp->pr_alloc->pa_pagemask); |
| if (page == ph->ph_page) |
if (page == ph->ph_page) |
| continue; |
continue; |
| |
|