Make uma_mtx MTX_RECURSE. Here's why:

The general UMA lock is a recursion-allowed lock because
there is a code path where, while we're still configured
to use startup_alloc() for backend page allocations, we
may end up in uma_reclaim() which calls zone_foreach(zone_drain),
which grabs uma_mtx, only to later call into startup_alloc()
because while freeing we needed to allocate a bucket.  Since
startup_alloc() also takes uma_mtx, we need to be able to
recurse on it.

This exact explanation also added as comment above mtx_init().

Trace showing recursion reported by: Peter Holm <peter-at-holm.cc>
This commit is contained in:
bmilekic 2004-06-23 21:59:03 +00:00
parent 51304a50f3
commit 7a6a2d65d4

View File

@ -1393,7 +1393,17 @@ uma_startup(void *bootmem)
#ifdef UMA_DEBUG
printf("Creating uma keg headers zone and keg.\n");
#endif
mtx_init(&uma_mtx, "UMA lock", NULL, MTX_DEF);
/*
* The general UMA lock is a recursion-allowed lock because
* there is a code path where, while we're still configured
* to use startup_alloc() for backend page allocations, we
* may end up in uma_reclaim() which calls zone_foreach(zone_drain),
* which grabs uma_mtx, only to later call into startup_alloc()
* because while freeing we needed to allocate a bucket. Since
* startup_alloc() also takes uma_mtx, we need to be able to
* recurse on it.
*/
mtx_init(&uma_mtx, "UMA lock", NULL, MTX_DEF | MTX_RECURSE);
/* "manually" create the initial zone */
args.name = "UMA Kegs";