perf_event_v7.c 45 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501
  1. /*
  2. * ARMv7 Cortex-A8 and Cortex-A9 Performance Events handling code.
  3. *
  4. * ARMv7 support: Jean Pihet <jpihet@mvista.com>
  5. * 2010 (c) MontaVista Software, LLC.
  6. *
  7. * Copied from ARMv6 code, with the low level code inspired
  8. * by the ARMv7 Oprofile code.
  9. *
  10. * Cortex-A8 has up to 4 configurable performance counters and
  11. * a single cycle counter.
  12. * Cortex-A9 has up to 31 configurable performance counters and
  13. * a single cycle counter.
  14. *
  15. * All counters can be enabled/disabled and IRQ masked separately. The cycle
  16. * counter and all 4 performance counters together can be reset separately.
  17. */
  18. #ifdef CONFIG_CPU_V7
  19. #include <asm/cp15.h>
  20. #include <asm/vfp.h>
  21. #include "../vfp/vfpinstr.h"
  22. /*
  23. * Common ARMv7 event types
  24. *
  25. * Note: An implementation may not be able to count all of these events
  26. * but the encodings are considered to be `reserved' in the case that
  27. * they are not available.
  28. */
  29. enum armv7_perf_types {
  30. ARMV7_PERFCTR_PMNC_SW_INCR = 0x00,
  31. ARMV7_PERFCTR_L1_ICACHE_REFILL = 0x01,
  32. ARMV7_PERFCTR_ITLB_REFILL = 0x02,
  33. ARMV7_PERFCTR_L1_DCACHE_REFILL = 0x03,
  34. ARMV7_PERFCTR_L1_DCACHE_ACCESS = 0x04,
  35. ARMV7_PERFCTR_DTLB_REFILL = 0x05,
  36. ARMV7_PERFCTR_MEM_READ = 0x06,
  37. ARMV7_PERFCTR_MEM_WRITE = 0x07,
  38. ARMV7_PERFCTR_INSTR_EXECUTED = 0x08,
  39. ARMV7_PERFCTR_EXC_TAKEN = 0x09,
  40. ARMV7_PERFCTR_EXC_EXECUTED = 0x0A,
  41. ARMV7_PERFCTR_CID_WRITE = 0x0B,
  42. /*
  43. * ARMV7_PERFCTR_PC_WRITE is equivalent to HW_BRANCH_INSTRUCTIONS.
  44. * It counts:
  45. * - all (taken) branch instructions,
  46. * - instructions that explicitly write the PC,
  47. * - exception generating instructions.
  48. */
  49. ARMV7_PERFCTR_PC_WRITE = 0x0C,
  50. ARMV7_PERFCTR_PC_IMM_BRANCH = 0x0D,
  51. ARMV7_PERFCTR_PC_PROC_RETURN = 0x0E,
  52. ARMV7_PERFCTR_MEM_UNALIGNED_ACCESS = 0x0F,
  53. ARMV7_PERFCTR_PC_BRANCH_MIS_PRED = 0x10,
  54. ARMV7_PERFCTR_CLOCK_CYCLES = 0x11,
  55. ARMV7_PERFCTR_PC_BRANCH_PRED = 0x12,
  56. /* These events are defined by the PMUv2 supplement (ARM DDI 0457A). */
  57. ARMV7_PERFCTR_MEM_ACCESS = 0x13,
  58. ARMV7_PERFCTR_L1_ICACHE_ACCESS = 0x14,
  59. ARMV7_PERFCTR_L1_DCACHE_WB = 0x15,
  60. ARMV7_PERFCTR_L2_CACHE_ACCESS = 0x16,
  61. ARMV7_PERFCTR_L2_CACHE_REFILL = 0x17,
  62. ARMV7_PERFCTR_L2_CACHE_WB = 0x18,
  63. ARMV7_PERFCTR_BUS_ACCESS = 0x19,
  64. ARMV7_PERFCTR_MEM_ERROR = 0x1A,
  65. ARMV7_PERFCTR_INSTR_SPEC = 0x1B,
  66. ARMV7_PERFCTR_TTBR_WRITE = 0x1C,
  67. ARMV7_PERFCTR_BUS_CYCLES = 0x1D,
  68. ARMV7_PERFCTR_CPU_CYCLES = 0xFF
  69. };
  70. /* ARMv7 Cortex-A8 specific event types */
  71. enum armv7_a8_perf_types {
  72. ARMV7_A8_PERFCTR_L2_CACHE_ACCESS = 0x43,
  73. ARMV7_A8_PERFCTR_L2_CACHE_REFILL = 0x44,
  74. ARMV7_A8_PERFCTR_L1_ICACHE_ACCESS = 0x50,
  75. ARMV7_A8_PERFCTR_STALL_ISIDE = 0x56,
  76. };
  77. /* ARMv7 Cortex-A9 specific event types */
  78. enum armv7_a9_perf_types {
  79. ARMV7_A9_PERFCTR_INSTR_CORE_RENAME = 0x68,
  80. ARMV7_A9_PERFCTR_STALL_ICACHE = 0x60,
  81. ARMV7_A9_PERFCTR_STALL_DISPATCH = 0x66,
  82. };
  83. /* ARMv7 Cortex-A5 specific event types */
  84. enum armv7_a5_perf_types {
  85. ARMV7_A5_PERFCTR_PREFETCH_LINEFILL = 0xc2,
  86. ARMV7_A5_PERFCTR_PREFETCH_LINEFILL_DROP = 0xc3,
  87. };
  88. /* ARMv7 Cortex-A15 specific event types */
  89. enum armv7_a15_perf_types {
  90. ARMV7_A15_PERFCTR_L1_DCACHE_ACCESS_READ = 0x40,
  91. ARMV7_A15_PERFCTR_L1_DCACHE_ACCESS_WRITE = 0x41,
  92. ARMV7_A15_PERFCTR_L1_DCACHE_REFILL_READ = 0x42,
  93. ARMV7_A15_PERFCTR_L1_DCACHE_REFILL_WRITE = 0x43,
  94. ARMV7_A15_PERFCTR_DTLB_REFILL_L1_READ = 0x4C,
  95. ARMV7_A15_PERFCTR_DTLB_REFILL_L1_WRITE = 0x4D,
  96. ARMV7_A15_PERFCTR_L2_CACHE_ACCESS_READ = 0x50,
  97. ARMV7_A15_PERFCTR_L2_CACHE_ACCESS_WRITE = 0x51,
  98. ARMV7_A15_PERFCTR_L2_CACHE_REFILL_READ = 0x52,
  99. ARMV7_A15_PERFCTR_L2_CACHE_REFILL_WRITE = 0x53,
  100. ARMV7_A15_PERFCTR_PC_WRITE_SPEC = 0x76,
  101. };
  102. /* ARMv7 Cortex-A12 specific event types */
  103. enum armv7_a12_perf_types {
  104. ARMV7_A12_PERFCTR_L1_DCACHE_ACCESS_READ = 0x40,
  105. ARMV7_A12_PERFCTR_L1_DCACHE_ACCESS_WRITE = 0x41,
  106. ARMV7_A12_PERFCTR_L2_CACHE_ACCESS_READ = 0x50,
  107. ARMV7_A12_PERFCTR_L2_CACHE_ACCESS_WRITE = 0x51,
  108. ARMV7_A12_PERFCTR_PC_WRITE_SPEC = 0x76,
  109. ARMV7_A12_PERFCTR_PF_TLB_REFILL = 0xe7,
  110. };
  111. /* ARMv7 Krait specific event types */
  112. enum krait_perf_types {
  113. KRAIT_PMRESR0_GROUP0 = 0xcc,
  114. KRAIT_PMRESR1_GROUP0 = 0xd0,
  115. KRAIT_PMRESR2_GROUP0 = 0xd4,
  116. KRAIT_VPMRESR0_GROUP0 = 0xd8,
  117. KRAIT_PERFCTR_L1_ICACHE_ACCESS = 0x10011,
  118. KRAIT_PERFCTR_L1_ICACHE_MISS = 0x10010,
  119. KRAIT_PERFCTR_L1_ITLB_ACCESS = 0x12222,
  120. KRAIT_PERFCTR_L1_DTLB_ACCESS = 0x12210,
  121. };
  122. /*
  123. * Cortex-A8 HW events mapping
  124. *
  125. * The hardware events that we support. We do support cache operations but
  126. * we have harvard caches and no way to combine instruction and data
  127. * accesses/misses in hardware.
  128. */
  129. static const unsigned armv7_a8_perf_map[PERF_COUNT_HW_MAX] = {
  130. PERF_MAP_ALL_UNSUPPORTED,
  131. [PERF_COUNT_HW_CPU_CYCLES] = ARMV7_PERFCTR_CPU_CYCLES,
  132. [PERF_COUNT_HW_INSTRUCTIONS] = ARMV7_PERFCTR_INSTR_EXECUTED,
  133. [PERF_COUNT_HW_CACHE_REFERENCES] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  134. [PERF_COUNT_HW_CACHE_MISSES] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  135. [PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = ARMV7_PERFCTR_PC_WRITE,
  136. [PERF_COUNT_HW_BRANCH_MISSES] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  137. [PERF_COUNT_HW_STALLED_CYCLES_FRONTEND] = ARMV7_A8_PERFCTR_STALL_ISIDE,
  138. };
  139. static const unsigned armv7_a8_perf_cache_map[PERF_COUNT_HW_CACHE_MAX]
  140. [PERF_COUNT_HW_CACHE_OP_MAX]
  141. [PERF_COUNT_HW_CACHE_RESULT_MAX] = {
  142. PERF_CACHE_MAP_ALL_UNSUPPORTED,
  143. /*
  144. * The performance counters don't differentiate between read and write
  145. * accesses/misses so this isn't strictly correct, but it's the best we
  146. * can do. Writes and reads get combined.
  147. */
  148. [C(L1D)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  149. [C(L1D)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  150. [C(L1D)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  151. [C(L1D)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  152. [C(L1I)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_A8_PERFCTR_L1_ICACHE_ACCESS,
  153. [C(L1I)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_ICACHE_REFILL,
  154. [C(LL)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_A8_PERFCTR_L2_CACHE_ACCESS,
  155. [C(LL)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_A8_PERFCTR_L2_CACHE_REFILL,
  156. [C(LL)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_A8_PERFCTR_L2_CACHE_ACCESS,
  157. [C(LL)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_A8_PERFCTR_L2_CACHE_REFILL,
  158. [C(DTLB)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_DTLB_REFILL,
  159. [C(DTLB)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_DTLB_REFILL,
  160. [C(ITLB)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_ITLB_REFILL,
  161. [C(ITLB)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_ITLB_REFILL,
  162. [C(BPU)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_PC_BRANCH_PRED,
  163. [C(BPU)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  164. [C(BPU)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_PC_BRANCH_PRED,
  165. [C(BPU)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  166. };
  167. /*
  168. * Cortex-A9 HW events mapping
  169. */
  170. static const unsigned armv7_a9_perf_map[PERF_COUNT_HW_MAX] = {
  171. PERF_MAP_ALL_UNSUPPORTED,
  172. [PERF_COUNT_HW_CPU_CYCLES] = ARMV7_PERFCTR_CPU_CYCLES,
  173. [PERF_COUNT_HW_INSTRUCTIONS] = ARMV7_A9_PERFCTR_INSTR_CORE_RENAME,
  174. [PERF_COUNT_HW_CACHE_REFERENCES] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  175. [PERF_COUNT_HW_CACHE_MISSES] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  176. [PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = ARMV7_PERFCTR_PC_WRITE,
  177. [PERF_COUNT_HW_BRANCH_MISSES] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  178. [PERF_COUNT_HW_STALLED_CYCLES_FRONTEND] = ARMV7_A9_PERFCTR_STALL_ICACHE,
  179. [PERF_COUNT_HW_STALLED_CYCLES_BACKEND] = ARMV7_A9_PERFCTR_STALL_DISPATCH,
  180. };
  181. static const unsigned armv7_a9_perf_cache_map[PERF_COUNT_HW_CACHE_MAX]
  182. [PERF_COUNT_HW_CACHE_OP_MAX]
  183. [PERF_COUNT_HW_CACHE_RESULT_MAX] = {
  184. PERF_CACHE_MAP_ALL_UNSUPPORTED,
  185. /*
  186. * The performance counters don't differentiate between read and write
  187. * accesses/misses so this isn't strictly correct, but it's the best we
  188. * can do. Writes and reads get combined.
  189. */
  190. [C(L1D)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  191. [C(L1D)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  192. [C(L1D)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  193. [C(L1D)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  194. [C(L1I)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_ICACHE_REFILL,
  195. [C(DTLB)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_DTLB_REFILL,
  196. [C(DTLB)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_DTLB_REFILL,
  197. [C(ITLB)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_ITLB_REFILL,
  198. [C(ITLB)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_ITLB_REFILL,
  199. [C(BPU)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_PC_BRANCH_PRED,
  200. [C(BPU)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  201. [C(BPU)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_PC_BRANCH_PRED,
  202. [C(BPU)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  203. };
  204. /*
  205. * Cortex-A5 HW events mapping
  206. */
  207. static const unsigned armv7_a5_perf_map[PERF_COUNT_HW_MAX] = {
  208. PERF_MAP_ALL_UNSUPPORTED,
  209. [PERF_COUNT_HW_CPU_CYCLES] = ARMV7_PERFCTR_CPU_CYCLES,
  210. [PERF_COUNT_HW_INSTRUCTIONS] = ARMV7_PERFCTR_INSTR_EXECUTED,
  211. [PERF_COUNT_HW_CACHE_REFERENCES] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  212. [PERF_COUNT_HW_CACHE_MISSES] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  213. [PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = ARMV7_PERFCTR_PC_WRITE,
  214. [PERF_COUNT_HW_BRANCH_MISSES] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  215. };
  216. static const unsigned armv7_a5_perf_cache_map[PERF_COUNT_HW_CACHE_MAX]
  217. [PERF_COUNT_HW_CACHE_OP_MAX]
  218. [PERF_COUNT_HW_CACHE_RESULT_MAX] = {
  219. PERF_CACHE_MAP_ALL_UNSUPPORTED,
  220. [C(L1D)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  221. [C(L1D)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  222. [C(L1D)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  223. [C(L1D)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  224. [C(L1D)][C(OP_PREFETCH)][C(RESULT_ACCESS)] = ARMV7_A5_PERFCTR_PREFETCH_LINEFILL,
  225. [C(L1D)][C(OP_PREFETCH)][C(RESULT_MISS)] = ARMV7_A5_PERFCTR_PREFETCH_LINEFILL_DROP,
  226. [C(L1I)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L1_ICACHE_ACCESS,
  227. [C(L1I)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_ICACHE_REFILL,
  228. /*
  229. * The prefetch counters don't differentiate between the I side and the
  230. * D side.
  231. */
  232. [C(L1I)][C(OP_PREFETCH)][C(RESULT_ACCESS)] = ARMV7_A5_PERFCTR_PREFETCH_LINEFILL,
  233. [C(L1I)][C(OP_PREFETCH)][C(RESULT_MISS)] = ARMV7_A5_PERFCTR_PREFETCH_LINEFILL_DROP,
  234. [C(DTLB)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_DTLB_REFILL,
  235. [C(DTLB)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_DTLB_REFILL,
  236. [C(ITLB)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_ITLB_REFILL,
  237. [C(ITLB)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_ITLB_REFILL,
  238. [C(BPU)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_PC_BRANCH_PRED,
  239. [C(BPU)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  240. [C(BPU)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_PC_BRANCH_PRED,
  241. [C(BPU)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  242. };
  243. /*
  244. * Cortex-A15 HW events mapping
  245. */
  246. static const unsigned armv7_a15_perf_map[PERF_COUNT_HW_MAX] = {
  247. PERF_MAP_ALL_UNSUPPORTED,
  248. [PERF_COUNT_HW_CPU_CYCLES] = ARMV7_PERFCTR_CPU_CYCLES,
  249. [PERF_COUNT_HW_INSTRUCTIONS] = ARMV7_PERFCTR_INSTR_EXECUTED,
  250. [PERF_COUNT_HW_CACHE_REFERENCES] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  251. [PERF_COUNT_HW_CACHE_MISSES] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  252. [PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = ARMV7_A15_PERFCTR_PC_WRITE_SPEC,
  253. [PERF_COUNT_HW_BRANCH_MISSES] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  254. [PERF_COUNT_HW_BUS_CYCLES] = ARMV7_PERFCTR_BUS_CYCLES,
  255. };
  256. static const unsigned armv7_a15_perf_cache_map[PERF_COUNT_HW_CACHE_MAX]
  257. [PERF_COUNT_HW_CACHE_OP_MAX]
  258. [PERF_COUNT_HW_CACHE_RESULT_MAX] = {
  259. PERF_CACHE_MAP_ALL_UNSUPPORTED,
  260. [C(L1D)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_A15_PERFCTR_L1_DCACHE_ACCESS_READ,
  261. [C(L1D)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_A15_PERFCTR_L1_DCACHE_REFILL_READ,
  262. [C(L1D)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_A15_PERFCTR_L1_DCACHE_ACCESS_WRITE,
  263. [C(L1D)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_A15_PERFCTR_L1_DCACHE_REFILL_WRITE,
  264. /*
  265. * Not all performance counters differentiate between read and write
  266. * accesses/misses so we're not always strictly correct, but it's the
  267. * best we can do. Writes and reads get combined in these cases.
  268. */
  269. [C(L1I)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L1_ICACHE_ACCESS,
  270. [C(L1I)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_ICACHE_REFILL,
  271. [C(LL)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_A15_PERFCTR_L2_CACHE_ACCESS_READ,
  272. [C(LL)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_A15_PERFCTR_L2_CACHE_REFILL_READ,
  273. [C(LL)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_A15_PERFCTR_L2_CACHE_ACCESS_WRITE,
  274. [C(LL)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_A15_PERFCTR_L2_CACHE_REFILL_WRITE,
  275. [C(DTLB)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_A15_PERFCTR_DTLB_REFILL_L1_READ,
  276. [C(DTLB)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_A15_PERFCTR_DTLB_REFILL_L1_WRITE,
  277. [C(ITLB)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_ITLB_REFILL,
  278. [C(ITLB)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_ITLB_REFILL,
  279. [C(BPU)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_PC_BRANCH_PRED,
  280. [C(BPU)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  281. [C(BPU)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_PC_BRANCH_PRED,
  282. [C(BPU)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  283. };
  284. /*
  285. * Cortex-A7 HW events mapping
  286. */
  287. static const unsigned armv7_a7_perf_map[PERF_COUNT_HW_MAX] = {
  288. PERF_MAP_ALL_UNSUPPORTED,
  289. [PERF_COUNT_HW_CPU_CYCLES] = ARMV7_PERFCTR_CPU_CYCLES,
  290. [PERF_COUNT_HW_INSTRUCTIONS] = ARMV7_PERFCTR_INSTR_EXECUTED,
  291. [PERF_COUNT_HW_CACHE_REFERENCES] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  292. [PERF_COUNT_HW_CACHE_MISSES] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  293. [PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = ARMV7_PERFCTR_PC_WRITE,
  294. [PERF_COUNT_HW_BRANCH_MISSES] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  295. [PERF_COUNT_HW_BUS_CYCLES] = ARMV7_PERFCTR_BUS_CYCLES,
  296. };
  297. static const unsigned armv7_a7_perf_cache_map[PERF_COUNT_HW_CACHE_MAX]
  298. [PERF_COUNT_HW_CACHE_OP_MAX]
  299. [PERF_COUNT_HW_CACHE_RESULT_MAX] = {
  300. PERF_CACHE_MAP_ALL_UNSUPPORTED,
  301. /*
  302. * The performance counters don't differentiate between read and write
  303. * accesses/misses so this isn't strictly correct, but it's the best we
  304. * can do. Writes and reads get combined.
  305. */
  306. [C(L1D)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  307. [C(L1D)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  308. [C(L1D)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  309. [C(L1D)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  310. [C(L1I)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L1_ICACHE_ACCESS,
  311. [C(L1I)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_ICACHE_REFILL,
  312. [C(LL)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L2_CACHE_ACCESS,
  313. [C(LL)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_L2_CACHE_REFILL,
  314. [C(LL)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L2_CACHE_ACCESS,
  315. [C(LL)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_L2_CACHE_REFILL,
  316. [C(DTLB)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_DTLB_REFILL,
  317. [C(DTLB)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_DTLB_REFILL,
  318. [C(ITLB)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_ITLB_REFILL,
  319. [C(ITLB)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_ITLB_REFILL,
  320. [C(BPU)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_PC_BRANCH_PRED,
  321. [C(BPU)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  322. [C(BPU)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_PC_BRANCH_PRED,
  323. [C(BPU)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  324. };
  325. /*
  326. * Cortex-A12 HW events mapping
  327. */
  328. static const unsigned armv7_a12_perf_map[PERF_COUNT_HW_MAX] = {
  329. PERF_MAP_ALL_UNSUPPORTED,
  330. [PERF_COUNT_HW_CPU_CYCLES] = ARMV7_PERFCTR_CPU_CYCLES,
  331. [PERF_COUNT_HW_INSTRUCTIONS] = ARMV7_PERFCTR_INSTR_EXECUTED,
  332. [PERF_COUNT_HW_CACHE_REFERENCES] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  333. [PERF_COUNT_HW_CACHE_MISSES] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  334. [PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = ARMV7_A12_PERFCTR_PC_WRITE_SPEC,
  335. [PERF_COUNT_HW_BRANCH_MISSES] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  336. [PERF_COUNT_HW_BUS_CYCLES] = ARMV7_PERFCTR_BUS_CYCLES,
  337. };
  338. static const unsigned armv7_a12_perf_cache_map[PERF_COUNT_HW_CACHE_MAX]
  339. [PERF_COUNT_HW_CACHE_OP_MAX]
  340. [PERF_COUNT_HW_CACHE_RESULT_MAX] = {
  341. PERF_CACHE_MAP_ALL_UNSUPPORTED,
  342. [C(L1D)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_A12_PERFCTR_L1_DCACHE_ACCESS_READ,
  343. [C(L1D)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  344. [C(L1D)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_A12_PERFCTR_L1_DCACHE_ACCESS_WRITE,
  345. [C(L1D)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  346. /*
  347. * Not all performance counters differentiate between read and write
  348. * accesses/misses so we're not always strictly correct, but it's the
  349. * best we can do. Writes and reads get combined in these cases.
  350. */
  351. [C(L1I)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L1_ICACHE_ACCESS,
  352. [C(L1I)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_ICACHE_REFILL,
  353. [C(LL)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_A12_PERFCTR_L2_CACHE_ACCESS_READ,
  354. [C(LL)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_L2_CACHE_REFILL,
  355. [C(LL)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_A12_PERFCTR_L2_CACHE_ACCESS_WRITE,
  356. [C(LL)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_L2_CACHE_REFILL,
  357. [C(DTLB)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_DTLB_REFILL,
  358. [C(DTLB)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_DTLB_REFILL,
  359. [C(DTLB)][C(OP_PREFETCH)][C(RESULT_MISS)] = ARMV7_A12_PERFCTR_PF_TLB_REFILL,
  360. [C(ITLB)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_ITLB_REFILL,
  361. [C(ITLB)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_ITLB_REFILL,
  362. [C(BPU)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_PC_BRANCH_PRED,
  363. [C(BPU)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  364. [C(BPU)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_PC_BRANCH_PRED,
  365. [C(BPU)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  366. };
  367. /*
  368. * Krait HW events mapping
  369. */
  370. static const unsigned krait_perf_map[PERF_COUNT_HW_MAX] = {
  371. PERF_MAP_ALL_UNSUPPORTED,
  372. [PERF_COUNT_HW_CPU_CYCLES] = ARMV7_PERFCTR_CPU_CYCLES,
  373. [PERF_COUNT_HW_INSTRUCTIONS] = ARMV7_PERFCTR_INSTR_EXECUTED,
  374. [PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = ARMV7_PERFCTR_PC_WRITE,
  375. [PERF_COUNT_HW_BRANCH_MISSES] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  376. [PERF_COUNT_HW_BUS_CYCLES] = ARMV7_PERFCTR_CLOCK_CYCLES,
  377. };
  378. static const unsigned krait_perf_map_no_branch[PERF_COUNT_HW_MAX] = {
  379. PERF_MAP_ALL_UNSUPPORTED,
  380. [PERF_COUNT_HW_CPU_CYCLES] = ARMV7_PERFCTR_CPU_CYCLES,
  381. [PERF_COUNT_HW_INSTRUCTIONS] = ARMV7_PERFCTR_INSTR_EXECUTED,
  382. [PERF_COUNT_HW_BRANCH_MISSES] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  383. [PERF_COUNT_HW_BUS_CYCLES] = ARMV7_PERFCTR_CLOCK_CYCLES,
  384. };
  385. static const unsigned krait_perf_cache_map[PERF_COUNT_HW_CACHE_MAX]
  386. [PERF_COUNT_HW_CACHE_OP_MAX]
  387. [PERF_COUNT_HW_CACHE_RESULT_MAX] = {
  388. PERF_CACHE_MAP_ALL_UNSUPPORTED,
  389. /*
  390. * The performance counters don't differentiate between read and write
  391. * accesses/misses so this isn't strictly correct, but it's the best we
  392. * can do. Writes and reads get combined.
  393. */
  394. [C(L1D)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  395. [C(L1D)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  396. [C(L1D)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_L1_DCACHE_ACCESS,
  397. [C(L1D)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_L1_DCACHE_REFILL,
  398. [C(L1I)][C(OP_READ)][C(RESULT_ACCESS)] = KRAIT_PERFCTR_L1_ICACHE_ACCESS,
  399. [C(L1I)][C(OP_READ)][C(RESULT_MISS)] = KRAIT_PERFCTR_L1_ICACHE_MISS,
  400. [C(DTLB)][C(OP_READ)][C(RESULT_ACCESS)] = KRAIT_PERFCTR_L1_DTLB_ACCESS,
  401. [C(DTLB)][C(OP_WRITE)][C(RESULT_ACCESS)] = KRAIT_PERFCTR_L1_DTLB_ACCESS,
  402. [C(ITLB)][C(OP_READ)][C(RESULT_ACCESS)] = KRAIT_PERFCTR_L1_ITLB_ACCESS,
  403. [C(ITLB)][C(OP_WRITE)][C(RESULT_ACCESS)] = KRAIT_PERFCTR_L1_ITLB_ACCESS,
  404. [C(BPU)][C(OP_READ)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_PC_BRANCH_PRED,
  405. [C(BPU)][C(OP_READ)][C(RESULT_MISS)] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  406. [C(BPU)][C(OP_WRITE)][C(RESULT_ACCESS)] = ARMV7_PERFCTR_PC_BRANCH_PRED,
  407. [C(BPU)][C(OP_WRITE)][C(RESULT_MISS)] = ARMV7_PERFCTR_PC_BRANCH_MIS_PRED,
  408. };
  409. /*
  410. * Perf Events' indices
  411. */
  412. #define ARMV7_IDX_CYCLE_COUNTER 0
  413. #define ARMV7_IDX_COUNTER0 1
  414. #define ARMV7_IDX_COUNTER_LAST(cpu_pmu) \
  415. (ARMV7_IDX_CYCLE_COUNTER + cpu_pmu->num_events - 1)
  416. #define ARMV7_MAX_COUNTERS 32
  417. #define ARMV7_COUNTER_MASK (ARMV7_MAX_COUNTERS - 1)
  418. /*
  419. * ARMv7 low level PMNC access
  420. */
  421. /*
  422. * Perf Event to low level counters mapping
  423. */
  424. #define ARMV7_IDX_TO_COUNTER(x) \
  425. (((x) - ARMV7_IDX_COUNTER0) & ARMV7_COUNTER_MASK)
  426. /*
  427. * Per-CPU PMNC: config reg
  428. */
  429. #define ARMV7_PMNC_E (1 << 0) /* Enable all counters */
  430. #define ARMV7_PMNC_P (1 << 1) /* Reset all counters */
  431. #define ARMV7_PMNC_C (1 << 2) /* Cycle counter reset */
  432. #define ARMV7_PMNC_D (1 << 3) /* CCNT counts every 64th cpu cycle */
  433. #define ARMV7_PMNC_X (1 << 4) /* Export to ETM */
  434. #define ARMV7_PMNC_DP (1 << 5) /* Disable CCNT if non-invasive debug*/
  435. #define ARMV7_PMNC_N_SHIFT 11 /* Number of counters supported */
  436. #define ARMV7_PMNC_N_MASK 0x1f
  437. #define ARMV7_PMNC_MASK 0x3f /* Mask for writable bits */
  438. /*
  439. * FLAG: counters overflow flag status reg
  440. */
  441. #define ARMV7_FLAG_MASK 0xffffffff /* Mask for writable bits */
  442. #define ARMV7_OVERFLOWED_MASK ARMV7_FLAG_MASK
  443. /*
  444. * PMXEVTYPER: Event selection reg
  445. */
  446. #define ARMV7_EVTYPE_MASK 0xc80000ff /* Mask for writable bits */
  447. #define ARMV7_EVTYPE_EVENT 0xff /* Mask for EVENT bits */
  448. /*
  449. * Event filters for PMUv2
  450. */
  451. #define ARMV7_EXCLUDE_PL1 (1 << 31)
  452. #define ARMV7_EXCLUDE_USER (1 << 30)
  453. #define ARMV7_INCLUDE_HYP (1 << 27)
  454. static inline u32 armv7_pmnc_read(void)
  455. {
  456. u32 val;
  457. asm volatile("mrc p15, 0, %0, c9, c12, 0" : "=r"(val));
  458. return val;
  459. }
  460. static inline void armv7_pmnc_write(u32 val)
  461. {
  462. val &= ARMV7_PMNC_MASK;
  463. isb();
  464. asm volatile("mcr p15, 0, %0, c9, c12, 0" : : "r"(val));
  465. }
  466. static inline int armv7_pmnc_has_overflowed(u32 pmnc)
  467. {
  468. return pmnc & ARMV7_OVERFLOWED_MASK;
  469. }
  470. static inline int armv7_pmnc_counter_valid(struct arm_pmu *cpu_pmu, int idx)
  471. {
  472. return idx >= ARMV7_IDX_CYCLE_COUNTER &&
  473. idx <= ARMV7_IDX_COUNTER_LAST(cpu_pmu);
  474. }
  475. static inline int armv7_pmnc_counter_has_overflowed(u32 pmnc, int idx)
  476. {
  477. return pmnc & BIT(ARMV7_IDX_TO_COUNTER(idx));
  478. }
  479. static inline void armv7_pmnc_select_counter(int idx)
  480. {
  481. u32 counter = ARMV7_IDX_TO_COUNTER(idx);
  482. asm volatile("mcr p15, 0, %0, c9, c12, 5" : : "r" (counter));
  483. isb();
  484. }
  485. static inline u32 armv7pmu_read_counter(struct perf_event *event)
  486. {
  487. struct arm_pmu *cpu_pmu = to_arm_pmu(event->pmu);
  488. struct hw_perf_event *hwc = &event->hw;
  489. int idx = hwc->idx;
  490. u32 value = 0;
  491. if (!armv7_pmnc_counter_valid(cpu_pmu, idx)) {
  492. pr_err("CPU%u reading wrong counter %d\n",
  493. smp_processor_id(), idx);
  494. } else if (idx == ARMV7_IDX_CYCLE_COUNTER) {
  495. asm volatile("mrc p15, 0, %0, c9, c13, 0" : "=r" (value));
  496. } else {
  497. armv7_pmnc_select_counter(idx);
  498. asm volatile("mrc p15, 0, %0, c9, c13, 2" : "=r" (value));
  499. }
  500. return value;
  501. }
  502. static inline void armv7pmu_write_counter(struct perf_event *event, u32 value)
  503. {
  504. struct arm_pmu *cpu_pmu = to_arm_pmu(event->pmu);
  505. struct hw_perf_event *hwc = &event->hw;
  506. int idx = hwc->idx;
  507. if (!armv7_pmnc_counter_valid(cpu_pmu, idx)) {
  508. pr_err("CPU%u writing wrong counter %d\n",
  509. smp_processor_id(), idx);
  510. } else if (idx == ARMV7_IDX_CYCLE_COUNTER) {
  511. asm volatile("mcr p15, 0, %0, c9, c13, 0" : : "r" (value));
  512. } else {
  513. armv7_pmnc_select_counter(idx);
  514. asm volatile("mcr p15, 0, %0, c9, c13, 2" : : "r" (value));
  515. }
  516. }
  517. static inline void armv7_pmnc_write_evtsel(int idx, u32 val)
  518. {
  519. armv7_pmnc_select_counter(idx);
  520. val &= ARMV7_EVTYPE_MASK;
  521. asm volatile("mcr p15, 0, %0, c9, c13, 1" : : "r" (val));
  522. }
  523. static inline void armv7_pmnc_enable_counter(int idx)
  524. {
  525. u32 counter = ARMV7_IDX_TO_COUNTER(idx);
  526. asm volatile("mcr p15, 0, %0, c9, c12, 1" : : "r" (BIT(counter)));
  527. }
  528. static inline void armv7_pmnc_disable_counter(int idx)
  529. {
  530. u32 counter = ARMV7_IDX_TO_COUNTER(idx);
  531. asm volatile("mcr p15, 0, %0, c9, c12, 2" : : "r" (BIT(counter)));
  532. }
  533. static inline void armv7_pmnc_enable_intens(int idx)
  534. {
  535. u32 counter = ARMV7_IDX_TO_COUNTER(idx);
  536. asm volatile("mcr p15, 0, %0, c9, c14, 1" : : "r" (BIT(counter)));
  537. }
  538. static inline void armv7_pmnc_disable_intens(int idx)
  539. {
  540. u32 counter = ARMV7_IDX_TO_COUNTER(idx);
  541. asm volatile("mcr p15, 0, %0, c9, c14, 2" : : "r" (BIT(counter)));
  542. isb();
  543. /* Clear the overflow flag in case an interrupt is pending. */
  544. asm volatile("mcr p15, 0, %0, c9, c12, 3" : : "r" (BIT(counter)));
  545. isb();
  546. }
  547. static inline u32 armv7_pmnc_getreset_flags(void)
  548. {
  549. u32 val;
  550. /* Read */
  551. asm volatile("mrc p15, 0, %0, c9, c12, 3" : "=r" (val));
  552. /* Write to clear flags */
  553. val &= ARMV7_FLAG_MASK;
  554. asm volatile("mcr p15, 0, %0, c9, c12, 3" : : "r" (val));
  555. return val;
  556. }
  557. #ifdef DEBUG
  558. static void armv7_pmnc_dump_regs(struct arm_pmu *cpu_pmu)
  559. {
  560. u32 val;
  561. unsigned int cnt;
  562. pr_info("PMNC registers dump:\n");
  563. asm volatile("mrc p15, 0, %0, c9, c12, 0" : "=r" (val));
  564. pr_info("PMNC =0x%08x\n", val);
  565. asm volatile("mrc p15, 0, %0, c9, c12, 1" : "=r" (val));
  566. pr_info("CNTENS=0x%08x\n", val);
  567. asm volatile("mrc p15, 0, %0, c9, c14, 1" : "=r" (val));
  568. pr_info("INTENS=0x%08x\n", val);
  569. asm volatile("mrc p15, 0, %0, c9, c12, 3" : "=r" (val));
  570. pr_info("FLAGS =0x%08x\n", val);
  571. asm volatile("mrc p15, 0, %0, c9, c12, 5" : "=r" (val));
  572. pr_info("SELECT=0x%08x\n", val);
  573. asm volatile("mrc p15, 0, %0, c9, c13, 0" : "=r" (val));
  574. pr_info("CCNT =0x%08x\n", val);
  575. for (cnt = ARMV7_IDX_COUNTER0;
  576. cnt <= ARMV7_IDX_COUNTER_LAST(cpu_pmu); cnt++) {
  577. armv7_pmnc_select_counter(cnt);
  578. asm volatile("mrc p15, 0, %0, c9, c13, 2" : "=r" (val));
  579. pr_info("CNT[%d] count =0x%08x\n",
  580. ARMV7_IDX_TO_COUNTER(cnt), val);
  581. asm volatile("mrc p15, 0, %0, c9, c13, 1" : "=r" (val));
  582. pr_info("CNT[%d] evtsel=0x%08x\n",
  583. ARMV7_IDX_TO_COUNTER(cnt), val);
  584. }
  585. }
  586. #endif
  587. static void armv7pmu_enable_event(struct perf_event *event)
  588. {
  589. unsigned long flags;
  590. struct hw_perf_event *hwc = &event->hw;
  591. struct arm_pmu *cpu_pmu = to_arm_pmu(event->pmu);
  592. struct pmu_hw_events *events = this_cpu_ptr(cpu_pmu->hw_events);
  593. int idx = hwc->idx;
  594. if (!armv7_pmnc_counter_valid(cpu_pmu, idx)) {
  595. pr_err("CPU%u enabling wrong PMNC counter IRQ enable %d\n",
  596. smp_processor_id(), idx);
  597. return;
  598. }
  599. /*
  600. * Enable counter and interrupt, and set the counter to count
  601. * the event that we're interested in.
  602. */
  603. raw_spin_lock_irqsave(&events->pmu_lock, flags);
  604. /*
  605. * Disable counter
  606. */
  607. armv7_pmnc_disable_counter(idx);
  608. /*
  609. * Set event (if destined for PMNx counters)
  610. * We only need to set the event for the cycle counter if we
  611. * have the ability to perform event filtering.
  612. */
  613. if (cpu_pmu->set_event_filter || idx != ARMV7_IDX_CYCLE_COUNTER)
  614. armv7_pmnc_write_evtsel(idx, hwc->config_base);
  615. /*
  616. * Enable interrupt for this counter
  617. */
  618. armv7_pmnc_enable_intens(idx);
  619. /*
  620. * Enable counter
  621. */
  622. armv7_pmnc_enable_counter(idx);
  623. raw_spin_unlock_irqrestore(&events->pmu_lock, flags);
  624. }
  625. static void armv7pmu_disable_event(struct perf_event *event)
  626. {
  627. unsigned long flags;
  628. struct hw_perf_event *hwc = &event->hw;
  629. struct arm_pmu *cpu_pmu = to_arm_pmu(event->pmu);
  630. struct pmu_hw_events *events = this_cpu_ptr(cpu_pmu->hw_events);
  631. int idx = hwc->idx;
  632. if (!armv7_pmnc_counter_valid(cpu_pmu, idx)) {
  633. pr_err("CPU%u disabling wrong PMNC counter IRQ enable %d\n",
  634. smp_processor_id(), idx);
  635. return;
  636. }
  637. /*
  638. * Disable counter and interrupt
  639. */
  640. raw_spin_lock_irqsave(&events->pmu_lock, flags);
  641. /*
  642. * Disable counter
  643. */
  644. armv7_pmnc_disable_counter(idx);
  645. /*
  646. * Disable interrupt for this counter
  647. */
  648. armv7_pmnc_disable_intens(idx);
  649. raw_spin_unlock_irqrestore(&events->pmu_lock, flags);
  650. }
  651. static irqreturn_t armv7pmu_handle_irq(int irq_num, void *dev)
  652. {
  653. u32 pmnc;
  654. struct perf_sample_data data;
  655. struct arm_pmu *cpu_pmu = (struct arm_pmu *)dev;
  656. struct pmu_hw_events *cpuc = this_cpu_ptr(cpu_pmu->hw_events);
  657. struct pt_regs *regs;
  658. int idx;
  659. /*
  660. * Get and reset the IRQ flags
  661. */
  662. pmnc = armv7_pmnc_getreset_flags();
  663. /*
  664. * Did an overflow occur?
  665. */
  666. if (!armv7_pmnc_has_overflowed(pmnc))
  667. return IRQ_NONE;
  668. /*
  669. * Handle the counter(s) overflow(s)
  670. */
  671. regs = get_irq_regs();
  672. for (idx = 0; idx < cpu_pmu->num_events; ++idx) {
  673. struct perf_event *event = cpuc->events[idx];
  674. struct hw_perf_event *hwc;
  675. /* Ignore if we don't have an event. */
  676. if (!event)
  677. continue;
  678. /*
  679. * We have a single interrupt for all counters. Check that
  680. * each counter has overflowed before we process it.
  681. */
  682. if (!armv7_pmnc_counter_has_overflowed(pmnc, idx))
  683. continue;
  684. hwc = &event->hw;
  685. armpmu_event_update(event);
  686. perf_sample_data_init(&data, 0, hwc->last_period);
  687. if (!armpmu_event_set_period(event))
  688. continue;
  689. if (perf_event_overflow(event, &data, regs))
  690. cpu_pmu->disable(event);
  691. }
  692. /*
  693. * Handle the pending perf events.
  694. *
  695. * Note: this call *must* be run with interrupts disabled. For
  696. * platforms that can have the PMU interrupts raised as an NMI, this
  697. * will not work.
  698. */
  699. irq_work_run();
  700. return IRQ_HANDLED;
  701. }
  702. static void armv7pmu_start(struct arm_pmu *cpu_pmu)
  703. {
  704. unsigned long flags;
  705. struct pmu_hw_events *events = this_cpu_ptr(cpu_pmu->hw_events);
  706. raw_spin_lock_irqsave(&events->pmu_lock, flags);
  707. /* Enable all counters */
  708. armv7_pmnc_write(armv7_pmnc_read() | ARMV7_PMNC_E);
  709. raw_spin_unlock_irqrestore(&events->pmu_lock, flags);
  710. }
  711. static void armv7pmu_stop(struct arm_pmu *cpu_pmu)
  712. {
  713. unsigned long flags;
  714. struct pmu_hw_events *events = this_cpu_ptr(cpu_pmu->hw_events);
  715. raw_spin_lock_irqsave(&events->pmu_lock, flags);
  716. /* Disable all counters */
  717. armv7_pmnc_write(armv7_pmnc_read() & ~ARMV7_PMNC_E);
  718. raw_spin_unlock_irqrestore(&events->pmu_lock, flags);
  719. }
  720. static int armv7pmu_get_event_idx(struct pmu_hw_events *cpuc,
  721. struct perf_event *event)
  722. {
  723. int idx;
  724. struct arm_pmu *cpu_pmu = to_arm_pmu(event->pmu);
  725. struct hw_perf_event *hwc = &event->hw;
  726. unsigned long evtype = hwc->config_base & ARMV7_EVTYPE_EVENT;
  727. /* Always place a cycle counter into the cycle counter. */
  728. if (evtype == ARMV7_PERFCTR_CPU_CYCLES) {
  729. if (test_and_set_bit(ARMV7_IDX_CYCLE_COUNTER, cpuc->used_mask))
  730. return -EAGAIN;
  731. return ARMV7_IDX_CYCLE_COUNTER;
  732. }
  733. /*
  734. * For anything other than a cycle counter, try and use
  735. * the events counters
  736. */
  737. for (idx = ARMV7_IDX_COUNTER0; idx < cpu_pmu->num_events; ++idx) {
  738. if (!test_and_set_bit(idx, cpuc->used_mask))
  739. return idx;
  740. }
  741. /* The counters are all in use. */
  742. return -EAGAIN;
  743. }
  744. /*
  745. * Add an event filter to a given event. This will only work for PMUv2 PMUs.
  746. */
  747. static int armv7pmu_set_event_filter(struct hw_perf_event *event,
  748. struct perf_event_attr *attr)
  749. {
  750. unsigned long config_base = 0;
  751. if (attr->exclude_idle)
  752. return -EPERM;
  753. if (attr->exclude_user)
  754. config_base |= ARMV7_EXCLUDE_USER;
  755. if (attr->exclude_kernel)
  756. config_base |= ARMV7_EXCLUDE_PL1;
  757. if (!attr->exclude_hv)
  758. config_base |= ARMV7_INCLUDE_HYP;
  759. /*
  760. * Install the filter into config_base as this is used to
  761. * construct the event type.
  762. */
  763. event->config_base = config_base;
  764. return 0;
  765. }
  766. static void armv7pmu_reset(void *info)
  767. {
  768. struct arm_pmu *cpu_pmu = (struct arm_pmu *)info;
  769. u32 idx, nb_cnt = cpu_pmu->num_events;
  770. /* The counter and interrupt enable registers are unknown at reset. */
  771. for (idx = ARMV7_IDX_CYCLE_COUNTER; idx < nb_cnt; ++idx) {
  772. armv7_pmnc_disable_counter(idx);
  773. armv7_pmnc_disable_intens(idx);
  774. }
  775. /* Initialize & Reset PMNC: C and P bits */
  776. armv7_pmnc_write(ARMV7_PMNC_P | ARMV7_PMNC_C);
  777. }
  778. static int armv7_a8_map_event(struct perf_event *event)
  779. {
  780. return armpmu_map_event(event, &armv7_a8_perf_map,
  781. &armv7_a8_perf_cache_map, 0xFF);
  782. }
  783. static int armv7_a9_map_event(struct perf_event *event)
  784. {
  785. return armpmu_map_event(event, &armv7_a9_perf_map,
  786. &armv7_a9_perf_cache_map, 0xFF);
  787. }
  788. static int armv7_a5_map_event(struct perf_event *event)
  789. {
  790. return armpmu_map_event(event, &armv7_a5_perf_map,
  791. &armv7_a5_perf_cache_map, 0xFF);
  792. }
  793. static int armv7_a15_map_event(struct perf_event *event)
  794. {
  795. return armpmu_map_event(event, &armv7_a15_perf_map,
  796. &armv7_a15_perf_cache_map, 0xFF);
  797. }
  798. static int armv7_a7_map_event(struct perf_event *event)
  799. {
  800. return armpmu_map_event(event, &armv7_a7_perf_map,
  801. &armv7_a7_perf_cache_map, 0xFF);
  802. }
  803. static int armv7_a12_map_event(struct perf_event *event)
  804. {
  805. return armpmu_map_event(event, &armv7_a12_perf_map,
  806. &armv7_a12_perf_cache_map, 0xFF);
  807. }
  808. static int krait_map_event(struct perf_event *event)
  809. {
  810. return armpmu_map_event(event, &krait_perf_map,
  811. &krait_perf_cache_map, 0xFFFFF);
  812. }
  813. static int krait_map_event_no_branch(struct perf_event *event)
  814. {
  815. return armpmu_map_event(event, &krait_perf_map_no_branch,
  816. &krait_perf_cache_map, 0xFFFFF);
  817. }
  818. static void armv7pmu_init(struct arm_pmu *cpu_pmu)
  819. {
  820. cpu_pmu->handle_irq = armv7pmu_handle_irq;
  821. cpu_pmu->enable = armv7pmu_enable_event;
  822. cpu_pmu->disable = armv7pmu_disable_event;
  823. cpu_pmu->read_counter = armv7pmu_read_counter;
  824. cpu_pmu->write_counter = armv7pmu_write_counter;
  825. cpu_pmu->get_event_idx = armv7pmu_get_event_idx;
  826. cpu_pmu->start = armv7pmu_start;
  827. cpu_pmu->stop = armv7pmu_stop;
  828. cpu_pmu->reset = armv7pmu_reset;
  829. cpu_pmu->max_period = (1LLU << 32) - 1;
  830. };
  831. static u32 armv7_read_num_pmnc_events(void)
  832. {
  833. u32 nb_cnt;
  834. /* Read the nb of CNTx counters supported from PMNC */
  835. nb_cnt = (armv7_pmnc_read() >> ARMV7_PMNC_N_SHIFT) & ARMV7_PMNC_N_MASK;
  836. /* Add the CPU cycles counter and return */
  837. return nb_cnt + 1;
  838. }
  839. static int armv7_a8_pmu_init(struct arm_pmu *cpu_pmu)
  840. {
  841. armv7pmu_init(cpu_pmu);
  842. cpu_pmu->name = "armv7_cortex_a8";
  843. cpu_pmu->map_event = armv7_a8_map_event;
  844. cpu_pmu->num_events = armv7_read_num_pmnc_events();
  845. return 0;
  846. }
  847. static int armv7_a9_pmu_init(struct arm_pmu *cpu_pmu)
  848. {
  849. armv7pmu_init(cpu_pmu);
  850. cpu_pmu->name = "armv7_cortex_a9";
  851. cpu_pmu->map_event = armv7_a9_map_event;
  852. cpu_pmu->num_events = armv7_read_num_pmnc_events();
  853. return 0;
  854. }
  855. static int armv7_a5_pmu_init(struct arm_pmu *cpu_pmu)
  856. {
  857. armv7pmu_init(cpu_pmu);
  858. cpu_pmu->name = "armv7_cortex_a5";
  859. cpu_pmu->map_event = armv7_a5_map_event;
  860. cpu_pmu->num_events = armv7_read_num_pmnc_events();
  861. return 0;
  862. }
  863. static int armv7_a15_pmu_init(struct arm_pmu *cpu_pmu)
  864. {
  865. armv7pmu_init(cpu_pmu);
  866. cpu_pmu->name = "armv7_cortex_a15";
  867. cpu_pmu->map_event = armv7_a15_map_event;
  868. cpu_pmu->num_events = armv7_read_num_pmnc_events();
  869. cpu_pmu->set_event_filter = armv7pmu_set_event_filter;
  870. return 0;
  871. }
  872. static int armv7_a7_pmu_init(struct arm_pmu *cpu_pmu)
  873. {
  874. armv7pmu_init(cpu_pmu);
  875. cpu_pmu->name = "armv7_cortex_a7";
  876. cpu_pmu->map_event = armv7_a7_map_event;
  877. cpu_pmu->num_events = armv7_read_num_pmnc_events();
  878. cpu_pmu->set_event_filter = armv7pmu_set_event_filter;
  879. return 0;
  880. }
  881. static int armv7_a12_pmu_init(struct arm_pmu *cpu_pmu)
  882. {
  883. armv7pmu_init(cpu_pmu);
  884. cpu_pmu->name = "armv7_cortex_a12";
  885. cpu_pmu->map_event = armv7_a12_map_event;
  886. cpu_pmu->num_events = armv7_read_num_pmnc_events();
  887. cpu_pmu->set_event_filter = armv7pmu_set_event_filter;
  888. return 0;
  889. }
  890. static int armv7_a17_pmu_init(struct arm_pmu *cpu_pmu)
  891. {
  892. armv7_a12_pmu_init(cpu_pmu);
  893. cpu_pmu->name = "armv7_cortex_a17";
  894. return 0;
  895. }
  896. /*
  897. * Krait Performance Monitor Region Event Selection Register (PMRESRn)
  898. *
  899. * 31 30 24 16 8 0
  900. * +--------------------------------+
  901. * PMRESR0 | EN | CC | CC | CC | CC | N = 1, R = 0
  902. * +--------------------------------+
  903. * PMRESR1 | EN | CC | CC | CC | CC | N = 1, R = 1
  904. * +--------------------------------+
  905. * PMRESR2 | EN | CC | CC | CC | CC | N = 1, R = 2
  906. * +--------------------------------+
  907. * VPMRESR0 | EN | CC | CC | CC | CC | N = 2, R = ?
  908. * +--------------------------------+
  909. * EN | G=3 | G=2 | G=1 | G=0
  910. *
  911. * Event Encoding:
  912. *
  913. * hwc->config_base = 0xNRCCG
  914. *
  915. * N = prefix, 1 for Krait CPU (PMRESRn), 2 for Venum VFP (VPMRESR)
  916. * R = region register
  917. * CC = class of events the group G is choosing from
  918. * G = group or particular event
  919. *
  920. * Example: 0x12021 is a Krait CPU event in PMRESR2's group 1 with code 2
  921. *
  922. * A region (R) corresponds to a piece of the CPU (execution unit, instruction
  923. * unit, etc.) while the event code (CC) corresponds to a particular class of
  924. * events (interrupts for example). An event code is broken down into
  925. * groups (G) that can be mapped into the PMU (irq, fiqs, and irq+fiqs for
  926. * example).
  927. */
  928. #define KRAIT_EVENT (1 << 16)
  929. #define VENUM_EVENT (2 << 16)
  930. #define KRAIT_EVENT_MASK (KRAIT_EVENT | VENUM_EVENT)
  931. #define PMRESRn_EN BIT(31)
  932. static u32 krait_read_pmresrn(int n)
  933. {
  934. u32 val;
  935. switch (n) {
  936. case 0:
  937. asm volatile("mrc p15, 1, %0, c9, c15, 0" : "=r" (val));
  938. break;
  939. case 1:
  940. asm volatile("mrc p15, 1, %0, c9, c15, 1" : "=r" (val));
  941. break;
  942. case 2:
  943. asm volatile("mrc p15, 1, %0, c9, c15, 2" : "=r" (val));
  944. break;
  945. default:
  946. BUG(); /* Should be validated in krait_pmu_get_event_idx() */
  947. }
  948. return val;
  949. }
  950. static void krait_write_pmresrn(int n, u32 val)
  951. {
  952. switch (n) {
  953. case 0:
  954. asm volatile("mcr p15, 1, %0, c9, c15, 0" : : "r" (val));
  955. break;
  956. case 1:
  957. asm volatile("mcr p15, 1, %0, c9, c15, 1" : : "r" (val));
  958. break;
  959. case 2:
  960. asm volatile("mcr p15, 1, %0, c9, c15, 2" : : "r" (val));
  961. break;
  962. default:
  963. BUG(); /* Should be validated in krait_pmu_get_event_idx() */
  964. }
  965. }
  966. static u32 krait_read_vpmresr0(void)
  967. {
  968. u32 val;
  969. asm volatile("mrc p10, 7, %0, c11, c0, 0" : "=r" (val));
  970. return val;
  971. }
  972. static void krait_write_vpmresr0(u32 val)
  973. {
  974. asm volatile("mcr p10, 7, %0, c11, c0, 0" : : "r" (val));
  975. }
  976. static void krait_pre_vpmresr0(u32 *venum_orig_val, u32 *fp_orig_val)
  977. {
  978. u32 venum_new_val;
  979. u32 fp_new_val;
  980. BUG_ON(preemptible());
  981. /* CPACR Enable CP10 and CP11 access */
  982. *venum_orig_val = get_copro_access();
  983. venum_new_val = *venum_orig_val | CPACC_SVC(10) | CPACC_SVC(11);
  984. set_copro_access(venum_new_val);
  985. /* Enable FPEXC */
  986. *fp_orig_val = fmrx(FPEXC);
  987. fp_new_val = *fp_orig_val | FPEXC_EN;
  988. fmxr(FPEXC, fp_new_val);
  989. }
  990. static void krait_post_vpmresr0(u32 venum_orig_val, u32 fp_orig_val)
  991. {
  992. BUG_ON(preemptible());
  993. /* Restore FPEXC */
  994. fmxr(FPEXC, fp_orig_val);
  995. isb();
  996. /* Restore CPACR */
  997. set_copro_access(venum_orig_val);
  998. }
  999. static u32 krait_get_pmresrn_event(unsigned int region)
  1000. {
  1001. static const u32 pmresrn_table[] = { KRAIT_PMRESR0_GROUP0,
  1002. KRAIT_PMRESR1_GROUP0,
  1003. KRAIT_PMRESR2_GROUP0 };
  1004. return pmresrn_table[region];
  1005. }
  1006. static void krait_evt_setup(int idx, u32 config_base)
  1007. {
  1008. u32 val;
  1009. u32 mask;
  1010. u32 vval, fval;
  1011. unsigned int region;
  1012. unsigned int group;
  1013. unsigned int code;
  1014. unsigned int group_shift;
  1015. bool venum_event;
  1016. venum_event = !!(config_base & VENUM_EVENT);
  1017. region = (config_base >> 12) & 0xf;
  1018. code = (config_base >> 4) & 0xff;
  1019. group = (config_base >> 0) & 0xf;
  1020. group_shift = group * 8;
  1021. mask = 0xff << group_shift;
  1022. /* Configure evtsel for the region and group */
  1023. if (venum_event)
  1024. val = KRAIT_VPMRESR0_GROUP0;
  1025. else
  1026. val = krait_get_pmresrn_event(region);
  1027. val += group;
  1028. /* Mix in mode-exclusion bits */
  1029. val |= config_base & (ARMV7_EXCLUDE_USER | ARMV7_EXCLUDE_PL1);
  1030. armv7_pmnc_write_evtsel(idx, val);
  1031. asm volatile("mcr p15, 0, %0, c9, c15, 0" : : "r" (0));
  1032. if (venum_event) {
  1033. krait_pre_vpmresr0(&vval, &fval);
  1034. val = krait_read_vpmresr0();
  1035. val &= ~mask;
  1036. val |= code << group_shift;
  1037. val |= PMRESRn_EN;
  1038. krait_write_vpmresr0(val);
  1039. krait_post_vpmresr0(vval, fval);
  1040. } else {
  1041. val = krait_read_pmresrn(region);
  1042. val &= ~mask;
  1043. val |= code << group_shift;
  1044. val |= PMRESRn_EN;
  1045. krait_write_pmresrn(region, val);
  1046. }
  1047. }
  1048. static u32 krait_clear_pmresrn_group(u32 val, int group)
  1049. {
  1050. u32 mask;
  1051. int group_shift;
  1052. group_shift = group * 8;
  1053. mask = 0xff << group_shift;
  1054. val &= ~mask;
  1055. /* Don't clear enable bit if entire region isn't disabled */
  1056. if (val & ~PMRESRn_EN)
  1057. return val |= PMRESRn_EN;
  1058. return 0;
  1059. }
  1060. static void krait_clearpmu(u32 config_base)
  1061. {
  1062. u32 val;
  1063. u32 vval, fval;
  1064. unsigned int region;
  1065. unsigned int group;
  1066. bool venum_event;
  1067. venum_event = !!(config_base & VENUM_EVENT);
  1068. region = (config_base >> 12) & 0xf;
  1069. group = (config_base >> 0) & 0xf;
  1070. if (venum_event) {
  1071. krait_pre_vpmresr0(&vval, &fval);
  1072. val = krait_read_vpmresr0();
  1073. val = krait_clear_pmresrn_group(val, group);
  1074. krait_write_vpmresr0(val);
  1075. krait_post_vpmresr0(vval, fval);
  1076. } else {
  1077. val = krait_read_pmresrn(region);
  1078. val = krait_clear_pmresrn_group(val, group);
  1079. krait_write_pmresrn(region, val);
  1080. }
  1081. }
  1082. static void krait_pmu_disable_event(struct perf_event *event)
  1083. {
  1084. unsigned long flags;
  1085. struct hw_perf_event *hwc = &event->hw;
  1086. int idx = hwc->idx;
  1087. struct arm_pmu *cpu_pmu = to_arm_pmu(event->pmu);
  1088. struct pmu_hw_events *events = this_cpu_ptr(cpu_pmu->hw_events);
  1089. /* Disable counter and interrupt */
  1090. raw_spin_lock_irqsave(&events->pmu_lock, flags);
  1091. /* Disable counter */
  1092. armv7_pmnc_disable_counter(idx);
  1093. /*
  1094. * Clear pmresr code (if destined for PMNx counters)
  1095. */
  1096. if (hwc->config_base & KRAIT_EVENT_MASK)
  1097. krait_clearpmu(hwc->config_base);
  1098. /* Disable interrupt for this counter */
  1099. armv7_pmnc_disable_intens(idx);
  1100. raw_spin_unlock_irqrestore(&events->pmu_lock, flags);
  1101. }
  1102. static void krait_pmu_enable_event(struct perf_event *event)
  1103. {
  1104. unsigned long flags;
  1105. struct hw_perf_event *hwc = &event->hw;
  1106. int idx = hwc->idx;
  1107. struct arm_pmu *cpu_pmu = to_arm_pmu(event->pmu);
  1108. struct pmu_hw_events *events = this_cpu_ptr(cpu_pmu->hw_events);
  1109. /*
  1110. * Enable counter and interrupt, and set the counter to count
  1111. * the event that we're interested in.
  1112. */
  1113. raw_spin_lock_irqsave(&events->pmu_lock, flags);
  1114. /* Disable counter */
  1115. armv7_pmnc_disable_counter(idx);
  1116. /*
  1117. * Set event (if destined for PMNx counters)
  1118. * We set the event for the cycle counter because we
  1119. * have the ability to perform event filtering.
  1120. */
  1121. if (hwc->config_base & KRAIT_EVENT_MASK)
  1122. krait_evt_setup(idx, hwc->config_base);
  1123. else
  1124. armv7_pmnc_write_evtsel(idx, hwc->config_base);
  1125. /* Enable interrupt for this counter */
  1126. armv7_pmnc_enable_intens(idx);
  1127. /* Enable counter */
  1128. armv7_pmnc_enable_counter(idx);
  1129. raw_spin_unlock_irqrestore(&events->pmu_lock, flags);
  1130. }
  1131. static void krait_pmu_reset(void *info)
  1132. {
  1133. u32 vval, fval;
  1134. armv7pmu_reset(info);
  1135. /* Clear all pmresrs */
  1136. krait_write_pmresrn(0, 0);
  1137. krait_write_pmresrn(1, 0);
  1138. krait_write_pmresrn(2, 0);
  1139. krait_pre_vpmresr0(&vval, &fval);
  1140. krait_write_vpmresr0(0);
  1141. krait_post_vpmresr0(vval, fval);
  1142. }
  1143. static int krait_event_to_bit(struct perf_event *event, unsigned int region,
  1144. unsigned int group)
  1145. {
  1146. int bit;
  1147. struct hw_perf_event *hwc = &event->hw;
  1148. struct arm_pmu *cpu_pmu = to_arm_pmu(event->pmu);
  1149. if (hwc->config_base & VENUM_EVENT)
  1150. bit = KRAIT_VPMRESR0_GROUP0;
  1151. else
  1152. bit = krait_get_pmresrn_event(region);
  1153. bit -= krait_get_pmresrn_event(0);
  1154. bit += group;
  1155. /*
  1156. * Lower bits are reserved for use by the counters (see
  1157. * armv7pmu_get_event_idx() for more info)
  1158. */
  1159. bit += ARMV7_IDX_COUNTER_LAST(cpu_pmu) + 1;
  1160. return bit;
  1161. }
  1162. /*
  1163. * We check for column exclusion constraints here.
  1164. * Two events cant use the same group within a pmresr register.
  1165. */
  1166. static int krait_pmu_get_event_idx(struct pmu_hw_events *cpuc,
  1167. struct perf_event *event)
  1168. {
  1169. int idx;
  1170. int bit = -1;
  1171. unsigned int prefix;
  1172. unsigned int region;
  1173. unsigned int code;
  1174. unsigned int group;
  1175. bool krait_event;
  1176. struct hw_perf_event *hwc = &event->hw;
  1177. region = (hwc->config_base >> 12) & 0xf;
  1178. code = (hwc->config_base >> 4) & 0xff;
  1179. group = (hwc->config_base >> 0) & 0xf;
  1180. krait_event = !!(hwc->config_base & KRAIT_EVENT_MASK);
  1181. if (krait_event) {
  1182. /* Ignore invalid events */
  1183. if (group > 3 || region > 2)
  1184. return -EINVAL;
  1185. prefix = hwc->config_base & KRAIT_EVENT_MASK;
  1186. if (prefix != KRAIT_EVENT && prefix != VENUM_EVENT)
  1187. return -EINVAL;
  1188. if (prefix == VENUM_EVENT && (code & 0xe0))
  1189. return -EINVAL;
  1190. bit = krait_event_to_bit(event, region, group);
  1191. if (test_and_set_bit(bit, cpuc->used_mask))
  1192. return -EAGAIN;
  1193. }
  1194. idx = armv7pmu_get_event_idx(cpuc, event);
  1195. if (idx < 0 && bit >= 0)
  1196. clear_bit(bit, cpuc->used_mask);
  1197. return idx;
  1198. }
  1199. static void krait_pmu_clear_event_idx(struct pmu_hw_events *cpuc,
  1200. struct perf_event *event)
  1201. {
  1202. int bit;
  1203. struct hw_perf_event *hwc = &event->hw;
  1204. unsigned int region;
  1205. unsigned int group;
  1206. bool krait_event;
  1207. region = (hwc->config_base >> 12) & 0xf;
  1208. group = (hwc->config_base >> 0) & 0xf;
  1209. krait_event = !!(hwc->config_base & KRAIT_EVENT_MASK);
  1210. if (krait_event) {
  1211. bit = krait_event_to_bit(event, region, group);
  1212. clear_bit(bit, cpuc->used_mask);
  1213. }
  1214. }
  1215. static int krait_pmu_init(struct arm_pmu *cpu_pmu)
  1216. {
  1217. armv7pmu_init(cpu_pmu);
  1218. cpu_pmu->name = "armv7_krait";
  1219. /* Some early versions of Krait don't support PC write events */
  1220. if (of_property_read_bool(cpu_pmu->plat_device->dev.of_node,
  1221. "qcom,no-pc-write"))
  1222. cpu_pmu->map_event = krait_map_event_no_branch;
  1223. else
  1224. cpu_pmu->map_event = krait_map_event;
  1225. cpu_pmu->num_events = armv7_read_num_pmnc_events();
  1226. cpu_pmu->set_event_filter = armv7pmu_set_event_filter;
  1227. cpu_pmu->reset = krait_pmu_reset;
  1228. cpu_pmu->enable = krait_pmu_enable_event;
  1229. cpu_pmu->disable = krait_pmu_disable_event;
  1230. cpu_pmu->get_event_idx = krait_pmu_get_event_idx;
  1231. cpu_pmu->clear_event_idx = krait_pmu_clear_event_idx;
  1232. return 0;
  1233. }
  1234. #else
  1235. static inline int armv7_a8_pmu_init(struct arm_pmu *cpu_pmu)
  1236. {
  1237. return -ENODEV;
  1238. }
  1239. static inline int armv7_a9_pmu_init(struct arm_pmu *cpu_pmu)
  1240. {
  1241. return -ENODEV;
  1242. }
  1243. static inline int armv7_a5_pmu_init(struct arm_pmu *cpu_pmu)
  1244. {
  1245. return -ENODEV;
  1246. }
  1247. static inline int armv7_a15_pmu_init(struct arm_pmu *cpu_pmu)
  1248. {
  1249. return -ENODEV;
  1250. }
  1251. static inline int armv7_a7_pmu_init(struct arm_pmu *cpu_pmu)
  1252. {
  1253. return -ENODEV;
  1254. }
  1255. static inline int armv7_a12_pmu_init(struct arm_pmu *cpu_pmu)
  1256. {
  1257. return -ENODEV;
  1258. }
  1259. static inline int armv7_a17_pmu_init(struct arm_pmu *cpu_pmu)
  1260. {
  1261. return -ENODEV;
  1262. }
  1263. static inline int krait_pmu_init(struct arm_pmu *cpu_pmu)
  1264. {
  1265. return -ENODEV;
  1266. }
  1267. #endif /* CONFIG_CPU_V7 */