Author: royger Date: Wed Jan 29 09:33:40 2020 New Revision: 357251 URL: https://svnweb.freebsd.org/changeset/base/357251
Log: MFC r354637: xen: fix dispatching of NMIs Modified: stable/12/sys/x86/xen/xen_apic.c Directory Properties: stable/12/ (props changed) Modified: stable/12/sys/x86/xen/xen_apic.c ============================================================================== --- stable/12/sys/x86/xen/xen_apic.c Wed Jan 29 08:46:35 2020 (r357250) +++ stable/12/sys/x86/xen/xen_apic.c Wed Jan 29 09:33:40 2020 (r357251) @@ -72,7 +72,6 @@ static driver_filter_t xen_invlcache; static driver_filter_t xen_ipi_bitmap_handler; static driver_filter_t xen_cpustop_handler; static driver_filter_t xen_cpususpend_handler; -static driver_filter_t xen_cpustophard_handler; #endif /*---------------------------------- Macros ----------------------------------*/ @@ -96,7 +95,6 @@ static struct xen_ipi_handler xen_ipis[] = [IPI_TO_IDX(IPI_BITMAP_VECTOR)] = { xen_ipi_bitmap_handler, "b" }, [IPI_TO_IDX(IPI_STOP)] = { xen_cpustop_handler, "st" }, [IPI_TO_IDX(IPI_SUSPEND)] = { xen_cpususpend_handler, "sp" }, - [IPI_TO_IDX(IPI_STOP_HARD)] = { xen_cpustophard_handler, "sth" }, }; #endif @@ -259,12 +257,52 @@ xen_pv_lapic_ipi_raw(register_t icrlo, u_int dest) XEN_APIC_UNSUPPORTED; } +#define PCPU_ID_GET(id, field) (pcpu_find(id)->pc_##field) static void +send_nmi(int dest) +{ + unsigned int cpu; + + /* + * NMIs are not routed over event channels, and instead delivered as on + * native using the exception vector (#2). Triggering them can be done + * using the local APIC, or an hypercall as a shortcut like it's done + * below. + */ + switch(dest) { + case APIC_IPI_DEST_SELF: + HYPERVISOR_vcpu_op(VCPUOP_send_nmi, PCPU_GET(vcpu_id), NULL); + break; + case APIC_IPI_DEST_ALL: + CPU_FOREACH(cpu) + HYPERVISOR_vcpu_op(VCPUOP_send_nmi, + PCPU_ID_GET(cpu, vcpu_id), NULL); + break; + case APIC_IPI_DEST_OTHERS: + CPU_FOREACH(cpu) + if (cpu != PCPU_GET(cpuid)) + HYPERVISOR_vcpu_op(VCPUOP_send_nmi, + PCPU_ID_GET(cpu, vcpu_id), NULL); + break; + default: + HYPERVISOR_vcpu_op(VCPUOP_send_nmi, + PCPU_ID_GET(apic_cpuid(dest), vcpu_id), NULL); + break; + } +} +#undef PCPU_ID_GET + +static void xen_pv_lapic_ipi_vectored(u_int vector, int dest) { xen_intr_handle_t *ipi_handle; int ipi_idx, to_cpu, self; + if (vector >= IPI_NMI_FIRST) { + send_nmi(dest); + return; + } + ipi_idx = IPI_TO_IDX(vector); if (ipi_idx >= nitems(xen_ipis)) panic("IPI out of range"); @@ -519,14 +557,6 @@ xen_cpususpend_handler(void *arg) { cpususpend_handler(); - return (FILTER_HANDLED); -} - -static int -xen_cpustophard_handler(void *arg) -{ - - ipi_nmi_handler(); return (FILTER_HANDLED); } _______________________________________________ svn-src-all@freebsd.org mailing list https://lists.freebsd.org/mailman/listinfo/svn-src-all To unsubscribe, send any mail to "svn-src-all-unsubscr...@freebsd.org"