intel-bts.c 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458
  1. /*
  2. * intel-bts.c: Intel Processor Trace support
  3. * Copyright (c) 2013-2015, Intel Corporation.
  4. *
  5. * This program is free software; you can redistribute it and/or modify it
  6. * under the terms and conditions of the GNU General Public License,
  7. * version 2, as published by the Free Software Foundation.
  8. *
  9. * This program is distributed in the hope it will be useful, but WITHOUT
  10. * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11. * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
  12. * more details.
  13. *
  14. */
  15. #include <linux/kernel.h>
  16. #include <linux/types.h>
  17. #include <linux/bitops.h>
  18. #include <linux/log2.h>
  19. #include "../../util/cpumap.h"
  20. #include "../../util/evsel.h"
  21. #include "../../util/evlist.h"
  22. #include "../../util/session.h"
  23. #include "../../util/util.h"
  24. #include "../../util/pmu.h"
  25. #include "../../util/debug.h"
  26. #include "../../util/tsc.h"
  27. #include "../../util/auxtrace.h"
  28. #include "../../util/intel-bts.h"
  29. #define KiB(x) ((x) * 1024)
  30. #define MiB(x) ((x) * 1024 * 1024)
  31. #define KiB_MASK(x) (KiB(x) - 1)
  32. #define MiB_MASK(x) (MiB(x) - 1)
  33. #define INTEL_BTS_DFLT_SAMPLE_SIZE KiB(4)
  34. #define INTEL_BTS_MAX_SAMPLE_SIZE KiB(60)
  35. struct intel_bts_snapshot_ref {
  36. void *ref_buf;
  37. size_t ref_offset;
  38. bool wrapped;
  39. };
  40. struct intel_bts_recording {
  41. struct auxtrace_record itr;
  42. struct perf_pmu *intel_bts_pmu;
  43. struct perf_evlist *evlist;
  44. bool snapshot_mode;
  45. size_t snapshot_size;
  46. int snapshot_ref_cnt;
  47. struct intel_bts_snapshot_ref *snapshot_refs;
  48. };
  49. struct branch {
  50. u64 from;
  51. u64 to;
  52. u64 misc;
  53. };
  54. static size_t intel_bts_info_priv_size(struct auxtrace_record *itr __maybe_unused)
  55. {
  56. return INTEL_BTS_AUXTRACE_PRIV_SIZE;
  57. }
  58. static int intel_bts_info_fill(struct auxtrace_record *itr,
  59. struct perf_session *session,
  60. struct auxtrace_info_event *auxtrace_info,
  61. size_t priv_size)
  62. {
  63. struct intel_bts_recording *btsr =
  64. container_of(itr, struct intel_bts_recording, itr);
  65. struct perf_pmu *intel_bts_pmu = btsr->intel_bts_pmu;
  66. struct perf_event_mmap_page *pc;
  67. struct perf_tsc_conversion tc = { .time_mult = 0, };
  68. bool cap_user_time_zero = false;
  69. int err;
  70. if (priv_size != INTEL_BTS_AUXTRACE_PRIV_SIZE)
  71. return -EINVAL;
  72. if (!session->evlist->nr_mmaps)
  73. return -EINVAL;
  74. pc = session->evlist->mmap[0].base;
  75. if (pc) {
  76. err = perf_read_tsc_conversion(pc, &tc);
  77. if (err) {
  78. if (err != -EOPNOTSUPP)
  79. return err;
  80. } else {
  81. cap_user_time_zero = tc.time_mult != 0;
  82. }
  83. if (!cap_user_time_zero)
  84. ui__warning("Intel BTS: TSC not available\n");
  85. }
  86. auxtrace_info->type = PERF_AUXTRACE_INTEL_BTS;
  87. auxtrace_info->priv[INTEL_BTS_PMU_TYPE] = intel_bts_pmu->type;
  88. auxtrace_info->priv[INTEL_BTS_TIME_SHIFT] = tc.time_shift;
  89. auxtrace_info->priv[INTEL_BTS_TIME_MULT] = tc.time_mult;
  90. auxtrace_info->priv[INTEL_BTS_TIME_ZERO] = tc.time_zero;
  91. auxtrace_info->priv[INTEL_BTS_CAP_USER_TIME_ZERO] = cap_user_time_zero;
  92. auxtrace_info->priv[INTEL_BTS_SNAPSHOT_MODE] = btsr->snapshot_mode;
  93. return 0;
  94. }
  95. static int intel_bts_recording_options(struct auxtrace_record *itr,
  96. struct perf_evlist *evlist,
  97. struct record_opts *opts)
  98. {
  99. struct intel_bts_recording *btsr =
  100. container_of(itr, struct intel_bts_recording, itr);
  101. struct perf_pmu *intel_bts_pmu = btsr->intel_bts_pmu;
  102. struct perf_evsel *evsel, *intel_bts_evsel = NULL;
  103. const struct cpu_map *cpus = evlist->cpus;
  104. bool privileged = geteuid() == 0 || perf_event_paranoid() < 0;
  105. btsr->evlist = evlist;
  106. btsr->snapshot_mode = opts->auxtrace_snapshot_mode;
  107. evlist__for_each(evlist, evsel) {
  108. if (evsel->attr.type == intel_bts_pmu->type) {
  109. if (intel_bts_evsel) {
  110. pr_err("There may be only one " INTEL_BTS_PMU_NAME " event\n");
  111. return -EINVAL;
  112. }
  113. evsel->attr.freq = 0;
  114. evsel->attr.sample_period = 1;
  115. intel_bts_evsel = evsel;
  116. opts->full_auxtrace = true;
  117. }
  118. }
  119. if (opts->auxtrace_snapshot_mode && !opts->full_auxtrace) {
  120. pr_err("Snapshot mode (-S option) requires " INTEL_BTS_PMU_NAME " PMU event (-e " INTEL_BTS_PMU_NAME ")\n");
  121. return -EINVAL;
  122. }
  123. if (!opts->full_auxtrace)
  124. return 0;
  125. if (opts->full_auxtrace && !cpu_map__empty(cpus)) {
  126. pr_err(INTEL_BTS_PMU_NAME " does not support per-cpu recording\n");
  127. return -EINVAL;
  128. }
  129. /* Set default sizes for snapshot mode */
  130. if (opts->auxtrace_snapshot_mode) {
  131. if (!opts->auxtrace_snapshot_size && !opts->auxtrace_mmap_pages) {
  132. if (privileged) {
  133. opts->auxtrace_mmap_pages = MiB(4) / page_size;
  134. } else {
  135. opts->auxtrace_mmap_pages = KiB(128) / page_size;
  136. if (opts->mmap_pages == UINT_MAX)
  137. opts->mmap_pages = KiB(256) / page_size;
  138. }
  139. } else if (!opts->auxtrace_mmap_pages && !privileged &&
  140. opts->mmap_pages == UINT_MAX) {
  141. opts->mmap_pages = KiB(256) / page_size;
  142. }
  143. if (!opts->auxtrace_snapshot_size)
  144. opts->auxtrace_snapshot_size =
  145. opts->auxtrace_mmap_pages * (size_t)page_size;
  146. if (!opts->auxtrace_mmap_pages) {
  147. size_t sz = opts->auxtrace_snapshot_size;
  148. sz = round_up(sz, page_size) / page_size;
  149. opts->auxtrace_mmap_pages = roundup_pow_of_two(sz);
  150. }
  151. if (opts->auxtrace_snapshot_size >
  152. opts->auxtrace_mmap_pages * (size_t)page_size) {
  153. pr_err("Snapshot size %zu must not be greater than AUX area tracing mmap size %zu\n",
  154. opts->auxtrace_snapshot_size,
  155. opts->auxtrace_mmap_pages * (size_t)page_size);
  156. return -EINVAL;
  157. }
  158. if (!opts->auxtrace_snapshot_size || !opts->auxtrace_mmap_pages) {
  159. pr_err("Failed to calculate default snapshot size and/or AUX area tracing mmap pages\n");
  160. return -EINVAL;
  161. }
  162. pr_debug2("Intel BTS snapshot size: %zu\n",
  163. opts->auxtrace_snapshot_size);
  164. }
  165. /* Set default sizes for full trace mode */
  166. if (opts->full_auxtrace && !opts->auxtrace_mmap_pages) {
  167. if (privileged) {
  168. opts->auxtrace_mmap_pages = MiB(4) / page_size;
  169. } else {
  170. opts->auxtrace_mmap_pages = KiB(128) / page_size;
  171. if (opts->mmap_pages == UINT_MAX)
  172. opts->mmap_pages = KiB(256) / page_size;
  173. }
  174. }
  175. /* Validate auxtrace_mmap_pages */
  176. if (opts->auxtrace_mmap_pages) {
  177. size_t sz = opts->auxtrace_mmap_pages * (size_t)page_size;
  178. size_t min_sz;
  179. if (opts->auxtrace_snapshot_mode)
  180. min_sz = KiB(4);
  181. else
  182. min_sz = KiB(8);
  183. if (sz < min_sz || !is_power_of_2(sz)) {
  184. pr_err("Invalid mmap size for Intel BTS: must be at least %zuKiB and a power of 2\n",
  185. min_sz / 1024);
  186. return -EINVAL;
  187. }
  188. }
  189. if (intel_bts_evsel) {
  190. /*
  191. * To obtain the auxtrace buffer file descriptor, the auxtrace event
  192. * must come first.
  193. */
  194. perf_evlist__to_front(evlist, intel_bts_evsel);
  195. /*
  196. * In the case of per-cpu mmaps, we need the CPU on the
  197. * AUX event.
  198. */
  199. if (!cpu_map__empty(cpus))
  200. perf_evsel__set_sample_bit(intel_bts_evsel, CPU);
  201. }
  202. /* Add dummy event to keep tracking */
  203. if (opts->full_auxtrace) {
  204. struct perf_evsel *tracking_evsel;
  205. int err;
  206. err = parse_events(evlist, "dummy:u", NULL);
  207. if (err)
  208. return err;
  209. tracking_evsel = perf_evlist__last(evlist);
  210. perf_evlist__set_tracking_event(evlist, tracking_evsel);
  211. tracking_evsel->attr.freq = 0;
  212. tracking_evsel->attr.sample_period = 1;
  213. }
  214. return 0;
  215. }
  216. static int intel_bts_parse_snapshot_options(struct auxtrace_record *itr,
  217. struct record_opts *opts,
  218. const char *str)
  219. {
  220. struct intel_bts_recording *btsr =
  221. container_of(itr, struct intel_bts_recording, itr);
  222. unsigned long long snapshot_size = 0;
  223. char *endptr;
  224. if (str) {
  225. snapshot_size = strtoull(str, &endptr, 0);
  226. if (*endptr || snapshot_size > SIZE_MAX)
  227. return -1;
  228. }
  229. opts->auxtrace_snapshot_mode = true;
  230. opts->auxtrace_snapshot_size = snapshot_size;
  231. btsr->snapshot_size = snapshot_size;
  232. return 0;
  233. }
  234. static u64 intel_bts_reference(struct auxtrace_record *itr __maybe_unused)
  235. {
  236. return rdtsc();
  237. }
  238. static int intel_bts_alloc_snapshot_refs(struct intel_bts_recording *btsr,
  239. int idx)
  240. {
  241. const size_t sz = sizeof(struct intel_bts_snapshot_ref);
  242. int cnt = btsr->snapshot_ref_cnt, new_cnt = cnt * 2;
  243. struct intel_bts_snapshot_ref *refs;
  244. if (!new_cnt)
  245. new_cnt = 16;
  246. while (new_cnt <= idx)
  247. new_cnt *= 2;
  248. refs = calloc(new_cnt, sz);
  249. if (!refs)
  250. return -ENOMEM;
  251. memcpy(refs, btsr->snapshot_refs, cnt * sz);
  252. btsr->snapshot_refs = refs;
  253. btsr->snapshot_ref_cnt = new_cnt;
  254. return 0;
  255. }
  256. static void intel_bts_free_snapshot_refs(struct intel_bts_recording *btsr)
  257. {
  258. int i;
  259. for (i = 0; i < btsr->snapshot_ref_cnt; i++)
  260. zfree(&btsr->snapshot_refs[i].ref_buf);
  261. zfree(&btsr->snapshot_refs);
  262. }
  263. static void intel_bts_recording_free(struct auxtrace_record *itr)
  264. {
  265. struct intel_bts_recording *btsr =
  266. container_of(itr, struct intel_bts_recording, itr);
  267. intel_bts_free_snapshot_refs(btsr);
  268. free(btsr);
  269. }
  270. static int intel_bts_snapshot_start(struct auxtrace_record *itr)
  271. {
  272. struct intel_bts_recording *btsr =
  273. container_of(itr, struct intel_bts_recording, itr);
  274. struct perf_evsel *evsel;
  275. evlist__for_each(btsr->evlist, evsel) {
  276. if (evsel->attr.type == btsr->intel_bts_pmu->type)
  277. return perf_evlist__disable_event(btsr->evlist, evsel);
  278. }
  279. return -EINVAL;
  280. }
  281. static int intel_bts_snapshot_finish(struct auxtrace_record *itr)
  282. {
  283. struct intel_bts_recording *btsr =
  284. container_of(itr, struct intel_bts_recording, itr);
  285. struct perf_evsel *evsel;
  286. evlist__for_each(btsr->evlist, evsel) {
  287. if (evsel->attr.type == btsr->intel_bts_pmu->type)
  288. return perf_evlist__enable_event(btsr->evlist, evsel);
  289. }
  290. return -EINVAL;
  291. }
  292. static bool intel_bts_first_wrap(u64 *data, size_t buf_size)
  293. {
  294. int i, a, b;
  295. b = buf_size >> 3;
  296. a = b - 512;
  297. if (a < 0)
  298. a = 0;
  299. for (i = a; i < b; i++) {
  300. if (data[i])
  301. return true;
  302. }
  303. return false;
  304. }
  305. static int intel_bts_find_snapshot(struct auxtrace_record *itr, int idx,
  306. struct auxtrace_mmap *mm, unsigned char *data,
  307. u64 *head, u64 *old)
  308. {
  309. struct intel_bts_recording *btsr =
  310. container_of(itr, struct intel_bts_recording, itr);
  311. bool wrapped;
  312. int err;
  313. pr_debug3("%s: mmap index %d old head %zu new head %zu\n",
  314. __func__, idx, (size_t)*old, (size_t)*head);
  315. if (idx >= btsr->snapshot_ref_cnt) {
  316. err = intel_bts_alloc_snapshot_refs(btsr, idx);
  317. if (err)
  318. goto out_err;
  319. }
  320. wrapped = btsr->snapshot_refs[idx].wrapped;
  321. if (!wrapped && intel_bts_first_wrap((u64 *)data, mm->len)) {
  322. btsr->snapshot_refs[idx].wrapped = true;
  323. wrapped = true;
  324. }
  325. /*
  326. * In full trace mode 'head' continually increases. However in snapshot
  327. * mode 'head' is an offset within the buffer. Here 'old' and 'head'
  328. * are adjusted to match the full trace case which expects that 'old' is
  329. * always less than 'head'.
  330. */
  331. if (wrapped) {
  332. *old = *head;
  333. *head += mm->len;
  334. } else {
  335. if (mm->mask)
  336. *old &= mm->mask;
  337. else
  338. *old %= mm->len;
  339. if (*old > *head)
  340. *head += mm->len;
  341. }
  342. pr_debug3("%s: wrap-around %sdetected, adjusted old head %zu adjusted new head %zu\n",
  343. __func__, wrapped ? "" : "not ", (size_t)*old, (size_t)*head);
  344. return 0;
  345. out_err:
  346. pr_err("%s: failed, error %d\n", __func__, err);
  347. return err;
  348. }
  349. static int intel_bts_read_finish(struct auxtrace_record *itr, int idx)
  350. {
  351. struct intel_bts_recording *btsr =
  352. container_of(itr, struct intel_bts_recording, itr);
  353. struct perf_evsel *evsel;
  354. evlist__for_each(btsr->evlist, evsel) {
  355. if (evsel->attr.type == btsr->intel_bts_pmu->type)
  356. return perf_evlist__enable_event_idx(btsr->evlist,
  357. evsel, idx);
  358. }
  359. return -EINVAL;
  360. }
  361. struct auxtrace_record *intel_bts_recording_init(int *err)
  362. {
  363. struct perf_pmu *intel_bts_pmu = perf_pmu__find(INTEL_BTS_PMU_NAME);
  364. struct intel_bts_recording *btsr;
  365. if (!intel_bts_pmu)
  366. return NULL;
  367. btsr = zalloc(sizeof(struct intel_bts_recording));
  368. if (!btsr) {
  369. *err = -ENOMEM;
  370. return NULL;
  371. }
  372. btsr->intel_bts_pmu = intel_bts_pmu;
  373. btsr->itr.recording_options = intel_bts_recording_options;
  374. btsr->itr.info_priv_size = intel_bts_info_priv_size;
  375. btsr->itr.info_fill = intel_bts_info_fill;
  376. btsr->itr.free = intel_bts_recording_free;
  377. btsr->itr.snapshot_start = intel_bts_snapshot_start;
  378. btsr->itr.snapshot_finish = intel_bts_snapshot_finish;
  379. btsr->itr.find_snapshot = intel_bts_find_snapshot;
  380. btsr->itr.parse_snapshot_options = intel_bts_parse_snapshot_options;
  381. btsr->itr.reference = intel_bts_reference;
  382. btsr->itr.read_finish = intel_bts_read_finish;
  383. btsr->itr.alignment = sizeof(struct branch);
  384. return &btsr->itr;
  385. }