00001
00007
00008
00009
00010
00011 #ifndef __L4_UTIL_CPU_H
00012 #define __L4_UTIL_CPU_H
00013
00014 #include <l4/sys/compiler.h>
00015
00016 EXTERN_C_BEGIN
00017
00026 L4_INLINE int l4util_cpu_has_cpuid(void);
00027
00035 L4_INLINE unsigned int l4util_cpu_capabilities(void);
00036
00043 L4_INLINE unsigned int l4util_cpu_capabilities_nocheck(void);
00044
00049 L4_INLINE void
00050 l4util_cpu_cpuid(unsigned long mode,
00051 unsigned long *eax, unsigned long *ebx,
00052 unsigned long *ecx, unsigned long *edx);
00053
00054 static inline void
00055 l4util_cpu_pause(void)
00056 {
00057 __asm__ __volatile__ ("rep; nop");
00058 }
00059
00060 L4_INLINE int
00061 l4util_cpu_has_cpuid(void)
00062 {
00063 unsigned long eax;
00064
00065 asm volatile("pushfl \t\n"
00066 "popl %%eax \t\n"
00067 "movl %%eax, %%ebx \t\n"
00068 "xorl $0x200000, %%eax \t\n"
00069 "pushl %%eax \t\n"
00070 "popfl \t\n"
00071 "pushfl \t\n"
00072 "popl %%eax \t\n"
00073 "xorl %%eax, %%ebx \t\n"
00074 "pushl %%ebx \t\n"
00075 "popfl \t\n"
00076 : "=a" (eax)
00077 :
00078 : "ebx");
00079
00080 return eax & 0x200000;
00081 }
00082
00083 L4_INLINE void
00084 l4util_cpu_cpuid(unsigned long mode,
00085 unsigned long *eax, unsigned long *ebx,
00086 unsigned long *ecx, unsigned long *edx)
00087 {
00088 asm volatile("cpuid"
00089 : "=a" (*eax),
00090 "=b" (*ebx),
00091 "=c" (*ecx),
00092 "=d" (*edx)
00093 : "a" (mode)
00094 : "cc");
00095 }
00096
00097 L4_INLINE unsigned int
00098 l4util_cpu_capabilities_nocheck(void)
00099 {
00100 unsigned long dummy, capability;
00101
00102
00103 l4util_cpu_cpuid(1, &dummy, &dummy, &dummy, &capability);
00104
00105 return capability;
00106 }
00107
00108 L4_INLINE unsigned int
00109 l4util_cpu_capabilities(void)
00110 {
00111 if (!l4util_cpu_has_cpuid())
00112 return 0;
00113
00114 return l4util_cpu_capabilities_nocheck();
00115 }
00116
00117 EXTERN_C_END
00118
00119 #endif
00120