cpu_relax();
 }
 
-void __default_send_IPI_shortcut(unsigned int shortcut, int vector)
+/*
+ * This is safe against interruption because it only writes the lower 32
+ * bits of the APIC_ICR register. The destination field is ignored for
+ * short hand IPIs.
+ *
+ *  wait_icr_idle()
+ *  write(ICR2, dest)
+ *  NMI
+ *     wait_icr_idle()
+ *     write(ICR)
+ *     wait_icr_idle()
+ *  write(ICR)
+ *
+ * This function does not need to disable interrupts as there is no ICR2
+ * interaction. The memory write is direct except when the machine is
+ * affected by the 11AP Pentium erratum, which turns the plain write into
+ * an XCHG operation.
+ */
+static void __default_send_IPI_shortcut(unsigned int shortcut, int vector)
 {
        /*
-        * Subtle. In the case of the 'never do double writes' workaround
-        * we have to lock out interrupts to be safe.  As we don't care
-        * of the value read we use an atomic rmw access to avoid costly
-        * cli/sti.  Otherwise we use an even cheaper single atomic write
-        * to the APIC.
-        */
-       unsigned int cfg;
-
-       /*
-        * Wait for idle.
+        * Wait for the previous ICR command to complete.  Use
+        * safe_apic_wait_icr_idle() for the NMI vector as there have been
+        * issues where otherwise the system hangs when the panic CPU tries
+        * to stop the others before launching the kdump kernel.
         */
        if (unlikely(vector == NMI_VECTOR))
                safe_apic_wait_icr_idle();
        else
                __xapic_wait_icr_idle();
 
-       /*
-        * No need to touch the target chip field. Also the destination
-        * mode is ignored when a shorthand is used.
-        */
-       cfg = __prepare_ICR(shortcut, vector, 0);
-
-       /*
-        * Send the IPI. The write to APIC_ICR fires this off.
-        */
-       native_apic_mem_write(APIC_ICR, cfg);
+       /* Destination field (ICR2) and the destination mode are ignored */
+       native_apic_mem_write(APIC_ICR, __prepare_ICR(shortcut, vector, 0));
 }
 
 /*
  * This is used to send an IPI with no shorthand notation (the destination is
  * specified in bits 56 to 63 of the ICR).
  */
-void __default_send_IPI_dest_field(unsigned int mask, int vector, unsigned int dest)
+void __default_send_IPI_dest_field(unsigned int dest_mask, int vector,
+                                  unsigned int dest_mode)
 {
-       unsigned long cfg;
-
-       /*
-        * Wait for idle.
-        */
+       /* See comment in __default_send_IPI_shortcut() */
        if (unlikely(vector == NMI_VECTOR))
                safe_apic_wait_icr_idle();
        else
                __xapic_wait_icr_idle();
 
-       /*
-        * prepare target chip field
-        */
-       cfg = __prepare_ICR2(mask);
-       native_apic_mem_write(APIC_ICR2, cfg);
-
-       /*
-        * program the ICR
-        */
-       cfg = __prepare_ICR(0, vector, dest);
-
-       /*
-        * Send the IPI. The write to APIC_ICR fires this off.
-        */
-       native_apic_mem_write(APIC_ICR, cfg);
+       /* Set the IPI destination field in the ICR */
+       native_apic_mem_write(APIC_ICR2, __prepare_ICR2(dest_mask));
+       /* Send it with the proper destination mode */
+       native_apic_mem_write(APIC_ICR, __prepare_ICR(0, vector, dest_mode));
 }
 
 void default_send_IPI_single_phys(int cpu, int vector)