svn commit: r332572 - stable/11/sys/vm
Gleb Smirnoff
glebius at FreeBSD.org
Mon Apr 16 15:07:20 UTC 2018
Author: glebius
Date: Mon Apr 16 15:07:19 2018
New Revision: 332572
URL: https://svnweb.freebsd.org/changeset/base/332572
Log:
Merge r331871:
Handle a special case when a slab can fit only one allocation,
and zone has a large alignment. With alignment taken into
account uk_rsize will be greater than space in a slab. However,
since we have only one item per slab, it is always naturally
aligned.
Code that will panic before this change with 4k page:
z = uma_zcreate("test", 3984, NULL, NULL, NULL, NULL, 31, 0);
uma_zalloc(z, M_WAITOK);
A practical scenario to hit the panic is a machine with 56 CPUs
and 2 NUMA domains, which yields in zone size of 3984 (on head).
PR: 227116
Modified:
stable/11/sys/vm/uma_core.c
Directory Properties:
stable/11/ (props changed)
Modified: stable/11/sys/vm/uma_core.c
==============================================================================
--- stable/11/sys/vm/uma_core.c Mon Apr 16 14:46:02 2018 (r332571)
+++ stable/11/sys/vm/uma_core.c Mon Apr 16 15:07:19 2018 (r332572)
@@ -1249,7 +1249,15 @@ keg_small_init(uma_keg_t keg)
else
shsize = sizeof(struct uma_slab);
- keg->uk_ipers = (slabsize - shsize) / rsize;
+ if (rsize <= slabsize - shsize)
+ keg->uk_ipers = (slabsize - shsize) / rsize;
+ else {
+ /* Handle special case when we have 1 item per slab, so
+ * alignment requirement can be relaxed. */
+ KASSERT(keg->uk_size <= slabsize - shsize,
+ ("%s: size %u greater than slab", __func__, keg->uk_size));
+ keg->uk_ipers = 1;
+ }
KASSERT(keg->uk_ipers > 0 && keg->uk_ipers <= SLAB_SETSIZE,
("%s: keg->uk_ipers %u", __func__, keg->uk_ipers));
More information about the svn-src-stable
mailing list