Index: sys/kern/kern_descrip.c =================================================================== --- sys/kern/kern_descrip.c +++ sys/kern/kern_descrip.c @@ -4366,7 +4366,7 @@ pwd_smr = uma_zone_get_smr(pwd_zone); mtx_init(&sigio_lock, "sigio lock", NULL, MTX_DEF); } -SYSINIT(select, SI_SUB_LOCK, SI_ORDER_FIRST, filelistinit, NULL); +SYSINIT(select, SI_SUB_INTRINSIC - 1, SI_ORDER_ANY, filelistinit, NULL); /*-------------------------------------------------------------------*/ Index: sys/kern/subr_smr.c =================================================================== --- sys/kern/subr_smr.c +++ sys/kern/subr_smr.c @@ -622,12 +622,12 @@ /* * Initialize the UMA slab zone. */ -void -smr_init(void) +static void +smr_init(void *arg __unused) { - smr_shared_zone = uma_zcreate("SMR SHARED", sizeof(struct smr_shared), NULL, NULL, NULL, NULL, (CACHE_LINE_SIZE * 2) - 1, 0); smr_zone = uma_zcreate("SMR CPU", sizeof(struct smr), NULL, NULL, NULL, NULL, (CACHE_LINE_SIZE * 2) - 1, UMA_ZONE_PCPU); } +SYSINIT(smr_init, SI_SUB_SMR, SI_ORDER_FIRST, smr_init, NULL); Index: sys/sys/kernel.h =================================================================== --- sys/sys/kernel.h +++ sys/sys/kernel.h @@ -106,6 +106,7 @@ SI_SUB_VNET_PRELINK = 0x1E00000, /* vnet init before modules */ SI_SUB_KLD = 0x2000000, /* KLD and module setup */ SI_SUB_CPU = 0x2100000, /* CPU resource(s)*/ + SI_SUB_SMR = 0x2101000, /* SMR zones can be used */ SI_SUB_RACCT = 0x2110000, /* resource accounting */ SI_SUB_KDTRACE = 0x2140000, /* Kernel dtrace hooks */ SI_SUB_RANDOM = 0x2160000, /* random number generator */ Index: sys/sys/smr.h =================================================================== --- sys/sys/smr.h +++ sys/sys/smr.h @@ -255,7 +255,4 @@ smr_wait(smr, smr_advance(smr)); } -/* Only at startup. */ -void smr_init(void); - #endif /* _SYS_SMR_H_ */ Index: sys/vm/uma_core.c =================================================================== --- sys/vm/uma_core.c +++ sys/vm/uma_core.c @@ -2230,6 +2230,9 @@ keg->uk_flags |= UMA_ZONE_ROUNDROBIN; #endif + KASSERT(booted >= BOOT_KVA || (keg->uk_flags & UMA_ZONE_PCPU) == 0, + ("%s: early pcpu keg %s", __func__, keg->uk_name)); + /* * If we haven't booted yet we need allocations to go through the * startup cache until the vm is ready. @@ -2307,12 +2310,11 @@ return; KEG_GET(zone, keg); + /* Switch to the real allocator. */ if (keg->uk_allocf == startup_alloc) { - /* Switch to the real allocator. */ - if (keg->uk_flags & UMA_ZONE_PCPU) - keg->uk_allocf = pcpu_page_alloc; - else if ((keg->uk_flags & UMA_ZONE_CONTIG) != 0 && - keg->uk_ppera > 1) + KASSERT((keg->uk_flags & UMA_ZONE_PCPU) == 0, + ("%s: early pcpu keg %s", __func__, keg->uk_name)); + if ((keg->uk_flags & UMA_ZONE_CONTIG) != 0 && keg->uk_ppera > 1) keg->uk_allocf = contig_alloc; else keg->uk_allocf = page_alloc; @@ -2870,7 +2872,6 @@ NULL, NULL, NULL, NULL, UMA_ALIGN_PTR, UMA_ZFLAG_INTERNAL); bucket_init(); - smr_init(); } #ifndef UMA_MD_SMALL_ALLOC @@ -3300,7 +3301,7 @@ #ifdef UMA_ZALLOC_DEBUG void *item; - KASSERT((zone->uz_flags & UMA_ZONE_SMR) != 0, + KASSERT(booted < BOOT_RUNNING || (zone->uz_flags & UMA_ZONE_SMR) != 0, ("uma_zalloc_arg: called with non-SMR zone.\n")); if (uma_zalloc_debug(zone, &item, NULL, flags) == EJUSTRETURN) return (item); @@ -4643,7 +4644,8 @@ uma_zone_set_smr(uma_zone_t zone, smr_t smr) { - ZONE_ASSERT_COLD(zone); + if (booted >= BOOT_RUNNING) + ZONE_ASSERT_COLD(zone); KASSERT(smr != NULL, ("Got NULL smr")); KASSERT((zone->uz_flags & UMA_ZONE_SMR) == 0, Index: sys/vm/vm_radix.c =================================================================== --- sys/vm/vm_radix.c +++ sys/vm/vm_radix.c @@ -375,10 +375,17 @@ vm_radix_node_zone = uma_zcreate("RADIX NODE", sizeof(struct vm_radix_node), NULL, NULL, NULL, NULL, - VM_RADIX_PAD, UMA_ZONE_VM | UMA_ZONE_SMR | UMA_ZONE_ZINIT); - vm_radix_smr = uma_zone_get_smr(vm_radix_node_zone); + VM_RADIX_PAD, UMA_ZONE_VM | UMA_ZONE_ZINIT); } +static void +vm_radix_zinit2(void) +{ + vm_radix_smr = smr_create("RADIX NODE", 0, 0); + uma_zone_set_smr(vm_radix_node_zone, vm_radix_smr); +} +SYSINIT(vm_radix_zinit2, SI_SUB_SMR, SI_ORDER_ANY, vm_radix_zinit2, NULL); + /* * Inserts the key-value pair into the trie. * Panics if the key already exists.