detect_arm64.go 7.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219
  1. // Copyright (c) 2015 Klaus Post, released under MIT License. See LICENSE file.
  2. //+build arm64,!gccgo,!noasm,!appengine
  3. package cpuid
  4. func getMidr() (midr uint64)
  5. func getProcFeatures() (procFeatures uint64)
  6. func getInstAttributes() (instAttrReg0, instAttrReg1 uint64)
  7. func initCPU() {
  8. cpuid = func(uint32) (a, b, c, d uint32) { return 0, 0, 0, 0 }
  9. cpuidex = func(x, y uint32) (a, b, c, d uint32) { return 0, 0, 0, 0 }
  10. xgetbv = func(uint32) (a, b uint32) { return 0, 0 }
  11. rdtscpAsm = func() (a, b, c, d uint32) { return 0, 0, 0, 0 }
  12. }
  13. func addInfo(c *CPUInfo) {
  14. // ARM64 disabled for now.
  15. if true {
  16. return
  17. }
  18. // midr := getMidr()
  19. // MIDR_EL1 - Main ID Register
  20. // x--------------------------------------------------x
  21. // | Name | bits | visible |
  22. // |--------------------------------------------------|
  23. // | Implementer | [31-24] | y |
  24. // |--------------------------------------------------|
  25. // | Variant | [23-20] | y |
  26. // |--------------------------------------------------|
  27. // | Architecture | [19-16] | y |
  28. // |--------------------------------------------------|
  29. // | PartNum | [15-4] | y |
  30. // |--------------------------------------------------|
  31. // | Revision | [3-0] | y |
  32. // x--------------------------------------------------x
  33. // fmt.Printf(" implementer: 0x%02x\n", (midr>>24)&0xff)
  34. // fmt.Printf(" variant: 0x%01x\n", (midr>>20)&0xf)
  35. // fmt.Printf("architecture: 0x%01x\n", (midr>>16)&0xf)
  36. // fmt.Printf(" part num: 0x%03x\n", (midr>>4)&0xfff)
  37. // fmt.Printf(" revision: 0x%01x\n", (midr>>0)&0xf)
  38. procFeatures := getProcFeatures()
  39. // ID_AA64PFR0_EL1 - Processor Feature Register 0
  40. // x--------------------------------------------------x
  41. // | Name | bits | visible |
  42. // |--------------------------------------------------|
  43. // | DIT | [51-48] | y |
  44. // |--------------------------------------------------|
  45. // | SVE | [35-32] | y |
  46. // |--------------------------------------------------|
  47. // | GIC | [27-24] | n |
  48. // |--------------------------------------------------|
  49. // | AdvSIMD | [23-20] | y |
  50. // |--------------------------------------------------|
  51. // | FP | [19-16] | y |
  52. // |--------------------------------------------------|
  53. // | EL3 | [15-12] | n |
  54. // |--------------------------------------------------|
  55. // | EL2 | [11-8] | n |
  56. // |--------------------------------------------------|
  57. // | EL1 | [7-4] | n |
  58. // |--------------------------------------------------|
  59. // | EL0 | [3-0] | n |
  60. // x--------------------------------------------------x
  61. var f ArmFlags
  62. // if procFeatures&(0xf<<48) != 0 {
  63. // fmt.Println("DIT")
  64. // }
  65. if procFeatures&(0xf<<32) != 0 {
  66. f |= SVE
  67. }
  68. if procFeatures&(0xf<<20) != 15<<20 {
  69. f |= ASIMD
  70. if procFeatures&(0xf<<20) == 1<<20 {
  71. // https://developer.arm.com/docs/ddi0595/b/aarch64-system-registers/id_aa64pfr0_el1
  72. // 0b0001 --> As for 0b0000, and also includes support for half-precision floating-point arithmetic.
  73. f |= FPHP
  74. f |= ASIMDHP
  75. }
  76. }
  77. if procFeatures&(0xf<<16) != 0 {
  78. f |= FP
  79. }
  80. instAttrReg0, instAttrReg1 := getInstAttributes()
  81. // https://developer.arm.com/docs/ddi0595/b/aarch64-system-registers/id_aa64isar0_el1
  82. //
  83. // ID_AA64ISAR0_EL1 - Instruction Set Attribute Register 0
  84. // x--------------------------------------------------x
  85. // | Name | bits | visible |
  86. // |--------------------------------------------------|
  87. // | TS | [55-52] | y |
  88. // |--------------------------------------------------|
  89. // | FHM | [51-48] | y |
  90. // |--------------------------------------------------|
  91. // | DP | [47-44] | y |
  92. // |--------------------------------------------------|
  93. // | SM4 | [43-40] | y |
  94. // |--------------------------------------------------|
  95. // | SM3 | [39-36] | y |
  96. // |--------------------------------------------------|
  97. // | SHA3 | [35-32] | y |
  98. // |--------------------------------------------------|
  99. // | RDM | [31-28] | y |
  100. // |--------------------------------------------------|
  101. // | ATOMICS | [23-20] | y |
  102. // |--------------------------------------------------|
  103. // | CRC32 | [19-16] | y |
  104. // |--------------------------------------------------|
  105. // | SHA2 | [15-12] | y |
  106. // |--------------------------------------------------|
  107. // | SHA1 | [11-8] | y |
  108. // |--------------------------------------------------|
  109. // | AES | [7-4] | y |
  110. // x--------------------------------------------------x
  111. // if instAttrReg0&(0xf<<52) != 0 {
  112. // fmt.Println("TS")
  113. // }
  114. // if instAttrReg0&(0xf<<48) != 0 {
  115. // fmt.Println("FHM")
  116. // }
  117. if instAttrReg0&(0xf<<44) != 0 {
  118. f |= ASIMDDP
  119. }
  120. if instAttrReg0&(0xf<<40) != 0 {
  121. f |= SM4
  122. }
  123. if instAttrReg0&(0xf<<36) != 0 {
  124. f |= SM3
  125. }
  126. if instAttrReg0&(0xf<<32) != 0 {
  127. f |= SHA3
  128. }
  129. if instAttrReg0&(0xf<<28) != 0 {
  130. f |= ASIMDRDM
  131. }
  132. if instAttrReg0&(0xf<<20) != 0 {
  133. f |= ATOMICS
  134. }
  135. if instAttrReg0&(0xf<<16) != 0 {
  136. f |= CRC32
  137. }
  138. if instAttrReg0&(0xf<<12) != 0 {
  139. f |= SHA2
  140. }
  141. if instAttrReg0&(0xf<<12) == 2<<12 {
  142. // https://developer.arm.com/docs/ddi0595/b/aarch64-system-registers/id_aa64isar0_el1
  143. // 0b0010 --> As 0b0001, plus SHA512H, SHA512H2, SHA512SU0, and SHA512SU1 instructions implemented.
  144. f |= SHA512
  145. }
  146. if instAttrReg0&(0xf<<8) != 0 {
  147. f |= SHA1
  148. }
  149. if instAttrReg0&(0xf<<4) != 0 {
  150. f |= AES
  151. }
  152. if instAttrReg0&(0xf<<4) == 2<<4 {
  153. // https://developer.arm.com/docs/ddi0595/b/aarch64-system-registers/id_aa64isar0_el1
  154. // 0b0010 --> As for 0b0001, plus PMULL/PMULL2 instructions operating on 64-bit data quantities.
  155. f |= PMULL
  156. }
  157. // https://developer.arm.com/docs/ddi0595/b/aarch64-system-registers/id_aa64isar1_el1
  158. //
  159. // ID_AA64ISAR1_EL1 - Instruction set attribute register 1
  160. // x--------------------------------------------------x
  161. // | Name | bits | visible |
  162. // |--------------------------------------------------|
  163. // | GPI | [31-28] | y |
  164. // |--------------------------------------------------|
  165. // | GPA | [27-24] | y |
  166. // |--------------------------------------------------|
  167. // | LRCPC | [23-20] | y |
  168. // |--------------------------------------------------|
  169. // | FCMA | [19-16] | y |
  170. // |--------------------------------------------------|
  171. // | JSCVT | [15-12] | y |
  172. // |--------------------------------------------------|
  173. // | API | [11-8] | y |
  174. // |--------------------------------------------------|
  175. // | APA | [7-4] | y |
  176. // |--------------------------------------------------|
  177. // | DPB | [3-0] | y |
  178. // x--------------------------------------------------x
  179. // if instAttrReg1&(0xf<<28) != 0 {
  180. // fmt.Println("GPI")
  181. // }
  182. if instAttrReg1&(0xf<<28) != 24 {
  183. f |= GPA
  184. }
  185. if instAttrReg1&(0xf<<20) != 0 {
  186. f |= LRCPC
  187. }
  188. if instAttrReg1&(0xf<<16) != 0 {
  189. f |= FCMA
  190. }
  191. if instAttrReg1&(0xf<<12) != 0 {
  192. f |= JSCVT
  193. }
  194. // if instAttrReg1&(0xf<<8) != 0 {
  195. // fmt.Println("API")
  196. // }
  197. // if instAttrReg1&(0xf<<4) != 0 {
  198. // fmt.Println("APA")
  199. // }
  200. if instAttrReg1&(0xf<<0) != 0 {
  201. f |= DCPOP
  202. }
  203. c.Arm = f
  204. }