Index: sys/x86/x86/intr_machdep.c =================================================================== --- sys/x86/x86/intr_machdep.c +++ sys/x86/x86/intr_machdep.c @@ -569,6 +569,7 @@ cpuset_t intr_cpus = CPUSET_T_INITIALIZER(0x1); static int current_cpu[MAXMEMDOM]; +static bool intr_single_domain; static void intr_init_cpus(void) @@ -576,7 +577,17 @@ int i; for (i = 0; i < vm_ndomains; i++) { + /* Check if we have any usable CPUs in this domain. */ + if (CPU_OVERLAP(&cpuset_domain[i], &intr_cpus) == 0) { + intr_single_domain = true; + printf( + "%s: CPUs in domain %d cannot service interrupts\n", + __func__, i); + } + current_cpu[i] = 0; + if (intr_single_domain && i > 0) + continue; if (!CPU_ISSET(current_cpu[i], &intr_cpus) || !CPU_ISSET(current_cpu[i], &cpuset_domain[i])) intr_next_cpu(i); @@ -596,6 +607,8 @@ if (mp_ncpus == 1) return (PCPU_GET(apic_id)); + if (intr_single_domain) + domain = 0; mtx_lock_spin(&icu_lock); apic_id = cpu_apic_ids[current_cpu[domain]]; do { @@ -603,7 +616,8 @@ if (current_cpu[domain] > mp_maxid) current_cpu[domain] = 0; } while (!CPU_ISSET(current_cpu[domain], &intr_cpus) || - !CPU_ISSET(current_cpu[domain], &cpuset_domain[domain])); + (!CPU_ISSET(current_cpu[domain], &cpuset_domain[domain]) && + !intr_single_domain)); mtx_unlock_spin(&icu_lock); return (apic_id); }