]> err.no Git - linux-2.6/blobdiff - include/asm-x86/processor.h
mm: xip/ext2 fix block allocation race
[linux-2.6] / include / asm-x86 / processor.h
index f92315ed68e1e61ed35b05349fb005c12d21e5f7..4df3e2f6fb563f2039cbc90aa4016dce9cf9274c 100644 (file)
@@ -722,14 +722,35 @@ static inline void __sti_mwait(unsigned long eax, unsigned long ecx)
 
 extern void mwait_idle_with_hints(unsigned long eax, unsigned long ecx);
 
-extern int                     force_mwait;
-
 extern void select_idle_routine(const struct cpuinfo_x86 *c);
 
 extern unsigned long           boot_option_idle_override;
 extern unsigned long           idle_halt;
 extern unsigned long           idle_nomwait;
 
+/*
+ * on systems with caches, caches must be flashed as the absolute
+ * last instruction before going into a suspended halt.  Otherwise,
+ * dirty data can linger in the cache and become stale on resume,
+ * leading to strange errors.
+ *
+ * perform a variety of operations to guarantee that the compiler
+ * will not reorder instructions.  wbinvd itself is serializing
+ * so the processor will not reorder.
+ *
+ * Systems without cache can just go into halt.
+ */
+static inline void wbinvd_halt(void)
+{
+       mb();
+       /* check for clflush to determine if wbinvd is legal */
+       if (cpu_has_clflush)
+               asm volatile("cli; wbinvd; 1: hlt; jmp 1b" : : : "memory");
+       else
+               while (1)
+                       halt();
+}
+
 extern void enable_sep_cpu(void);
 extern int sysenter_setup(void);