cpuid.h 7.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209
  1. /*===---- cpuid.h - X86 cpu model detection --------------------------------===
  2. *
  3. * Permission is hereby granted, free of charge, to any person obtaining a copy
  4. * of this software and associated documentation files (the "Software"), to deal
  5. * in the Software without restriction, including without limitation the rights
  6. * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  7. * copies of the Software, and to permit persons to whom the Software is
  8. * furnished to do so, subject to the following conditions:
  9. *
  10. * The above copyright notice and this permission notice shall be included in
  11. * all copies or substantial portions of the Software.
  12. *
  13. * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  14. * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  15. * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  16. * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  17. * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  18. * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
  19. * THE SOFTWARE.
  20. *
  21. *===-----------------------------------------------------------------------===
  22. */
  23. #if !(__x86_64__ || __i386__)
  24. #error this header is for x86 only
  25. #endif
  26. /* Responses identification request with %eax 0 */
  27. /* AMD: "AuthenticAMD" */
  28. #define signature_AMD_ebx 0x68747541
  29. #define signature_AMD_edx 0x69746e65
  30. #define signature_AMD_ecx 0x444d4163
  31. /* CENTAUR: "CentaurHauls" */
  32. #define signature_CENTAUR_ebx 0x746e6543
  33. #define signature_CENTAUR_edx 0x48727561
  34. #define signature_CENTAUR_ecx 0x736c7561
  35. /* CYRIX: "CyrixInstead" */
  36. #define signature_CYRIX_ebx 0x69727943
  37. #define signature_CYRIX_edx 0x736e4978
  38. #define signature_CYRIX_ecx 0x64616574
  39. /* INTEL: "GenuineIntel" */
  40. #define signature_INTEL_ebx 0x756e6547
  41. #define signature_INTEL_edx 0x49656e69
  42. #define signature_INTEL_ecx 0x6c65746e
  43. /* TM1: "TransmetaCPU" */
  44. #define signature_TM1_ebx 0x6e617254
  45. #define signature_TM1_edx 0x74656d73
  46. #define signature_TM1_ecx 0x55504361
  47. /* TM2: "GenuineTMx86" */
  48. #define signature_TM2_ebx 0x756e6547
  49. #define signature_TM2_edx 0x54656e69
  50. #define signature_TM2_ecx 0x3638784d
  51. /* NSC: "Geode by NSC" */
  52. #define signature_NSC_ebx 0x646f6547
  53. #define signature_NSC_edx 0x43534e20
  54. #define signature_NSC_ecx 0x79622065
  55. /* NEXGEN: "NexGenDriven" */
  56. #define signature_NEXGEN_ebx 0x4778654e
  57. #define signature_NEXGEN_edx 0x72446e65
  58. #define signature_NEXGEN_ecx 0x6e657669
  59. /* RISE: "RiseRiseRise" */
  60. #define signature_RISE_ebx 0x65736952
  61. #define signature_RISE_edx 0x65736952
  62. #define signature_RISE_ecx 0x65736952
  63. /* SIS: "SiS SiS SiS " */
  64. #define signature_SIS_ebx 0x20536953
  65. #define signature_SIS_edx 0x20536953
  66. #define signature_SIS_ecx 0x20536953
  67. /* UMC: "UMC UMC UMC " */
  68. #define signature_UMC_ebx 0x20434d55
  69. #define signature_UMC_edx 0x20434d55
  70. #define signature_UMC_ecx 0x20434d55
  71. /* VIA: "VIA VIA VIA " */
  72. #define signature_VIA_ebx 0x20414956
  73. #define signature_VIA_edx 0x20414956
  74. #define signature_VIA_ecx 0x20414956
  75. /* VORTEX: "Vortex86 SoC" */
  76. #define signature_VORTEX_ebx 0x74726f56
  77. #define signature_VORTEX_edx 0x36387865
  78. #define signature_VORTEX_ecx 0x436f5320
  79. /* Features in %ecx for level 1 */
  80. #define bit_SSE3 0x00000001
  81. #define bit_PCLMULQDQ 0x00000002
  82. #define bit_DTES64 0x00000004
  83. #define bit_MONITOR 0x00000008
  84. #define bit_DSCPL 0x00000010
  85. #define bit_VMX 0x00000020
  86. #define bit_SMX 0x00000040
  87. #define bit_EIST 0x00000080
  88. #define bit_TM2 0x00000100
  89. #define bit_SSSE3 0x00000200
  90. #define bit_CNXTID 0x00000400
  91. #define bit_FMA 0x00001000
  92. #define bit_CMPXCHG16B 0x00002000
  93. #define bit_xTPR 0x00004000
  94. #define bit_PDCM 0x00008000
  95. #define bit_PCID 0x00020000
  96. #define bit_DCA 0x00040000
  97. #define bit_SSE41 0x00080000
  98. #define bit_SSE42 0x00100000
  99. #define bit_x2APIC 0x00200000
  100. #define bit_MOVBE 0x00400000
  101. #define bit_POPCNT 0x00800000
  102. #define bit_TSCDeadline 0x01000000
  103. #define bit_AESNI 0x02000000
  104. #define bit_XSAVE 0x04000000
  105. #define bit_OSXSAVE 0x08000000
  106. #define bit_AVX 0x10000000
  107. #define bit_RDRND 0x40000000
  108. /* Features in %edx for level 1 */
  109. #define bit_FPU 0x00000001
  110. #define bit_VME 0x00000002
  111. #define bit_DE 0x00000004
  112. #define bit_PSE 0x00000008
  113. #define bit_TSC 0x00000010
  114. #define bit_MSR 0x00000020
  115. #define bit_PAE 0x00000040
  116. #define bit_MCE 0x00000080
  117. #define bit_CX8 0x00000100
  118. #define bit_APIC 0x00000200
  119. #define bit_SEP 0x00000800
  120. #define bit_MTRR 0x00001000
  121. #define bit_PGE 0x00002000
  122. #define bit_MCA 0x00004000
  123. #define bit_CMOV 0x00008000
  124. #define bit_PAT 0x00010000
  125. #define bit_PSE36 0x00020000
  126. #define bit_PSN 0x00040000
  127. #define bit_CLFSH 0x00080000
  128. #define bit_DS 0x00200000
  129. #define bit_ACPI 0x00400000
  130. #define bit_MMX 0x00800000
  131. #define bit_FXSR 0x01000000
  132. #define bit_FXSAVE bit_FXSR /* for gcc compat */
  133. #define bit_SSE 0x02000000
  134. #define bit_SSE2 0x04000000
  135. #define bit_SS 0x08000000
  136. #define bit_HTT 0x10000000
  137. #define bit_TM 0x20000000
  138. #define bit_PBE 0x80000000
  139. /* Features in %ebx for level 7 sub-leaf 0 */
  140. #define bit_FSGSBASE 0x00000001
  141. #define bit_SMEP 0x00000080
  142. #define bit_ENH_MOVSB 0x00000200
  143. #if __i386__
  144. #define __cpuid(__level, __eax, __ebx, __ecx, __edx) \
  145. __asm("cpuid" : "=a"(__eax), "=b" (__ebx), "=c"(__ecx), "=d"(__edx) \
  146. : "0"(__level))
  147. #define __cpuid_count(__level, __count, __eax, __ebx, __ecx, __edx) \
  148. __asm("cpuid" : "=a"(__eax), "=b" (__ebx), "=c"(__ecx), "=d"(__edx) \
  149. : "0"(__level), "2"(__count))
  150. #else
  151. /* x86-64 uses %rbx as the base register, so preserve it. */
  152. #define __cpuid(__level, __eax, __ebx, __ecx, __edx) \
  153. __asm(" xchgq %%rbx,%q1\n" \
  154. " cpuid\n" \
  155. " xchgq %%rbx,%q1" \
  156. : "=a"(__eax), "=r" (__ebx), "=c"(__ecx), "=d"(__edx) \
  157. : "0"(__level))
  158. #define __cpuid_count(__level, __count, __eax, __ebx, __ecx, __edx) \
  159. __asm(" xchgq %%rbx,%q1\n" \
  160. " cpuid\n" \
  161. " xchgq %%rbx,%q1" \
  162. : "=a"(__eax), "=r" (__ebx), "=c"(__ecx), "=d"(__edx) \
  163. : "0"(__level), "2"(__count))
  164. #endif
  165. static __inline int __get_cpuid (unsigned int __level, unsigned int *__eax,
  166. unsigned int *__ebx, unsigned int *__ecx,
  167. unsigned int *__edx) {
  168. __cpuid(__level, *__eax, *__ebx, *__ecx, *__edx);
  169. return 1;
  170. }
  171. static __inline int __get_cpuid_max (unsigned int __level, unsigned int *__sig)
  172. {
  173. unsigned int __eax, __ebx, __ecx, __edx;
  174. #if __i386__
  175. int __cpuid_supported;
  176. __asm(" pushfl\n"
  177. " popl %%eax\n"
  178. " movl %%eax,%%ecx\n"
  179. " xorl $0x00200000,%%eax\n"
  180. " pushl %%eax\n"
  181. " popfl\n"
  182. " pushfl\n"
  183. " popl %%eax\n"
  184. " movl $0,%0\n"
  185. " cmpl %%eax,%%ecx\n"
  186. " je 1f\n"
  187. " movl $1,%0\n"
  188. "1:"
  189. : "=r" (__cpuid_supported) : : "eax", "ecx");
  190. if (!__cpuid_supported)
  191. return 0;
  192. #endif
  193. __cpuid(__level, __eax, __ebx, __ecx, __edx);
  194. if (__sig)
  195. *__sig = __ebx;
  196. return __eax;
  197. }