Lines Matching +full:t +full:- +full:head
1 // SPDX-License-Identifier: GPL-2.0
4 * Copyright (c) 2017-2018, Arm Ltd.
25 #include "../../../util/arm-spe.h"
53 struct perf_pmu *arm_spe_pmu = sper->arm_spe_pmu; in arm_spe_info_fill()
56 return -EINVAL; in arm_spe_info_fill()
58 if (!session->evlist->core.nr_mmaps) in arm_spe_info_fill()
59 return -EINVAL; in arm_spe_info_fill()
61 auxtrace_info->type = PERF_AUXTRACE_ARM_SPE; in arm_spe_info_fill()
62 auxtrace_info->priv[ARM_SPE_PMU_TYPE] = arm_spe_pmu->type; in arm_spe_info_fill()
83 * No size were given to '-S' or '-m,', so go with the default in arm_spe_snapshot_resolve_auxtrace_defaults()
85 if (!opts->auxtrace_snapshot_size && !opts->auxtrace_mmap_pages) { in arm_spe_snapshot_resolve_auxtrace_defaults()
87 opts->auxtrace_mmap_pages = MiB(4) / page_size; in arm_spe_snapshot_resolve_auxtrace_defaults()
89 opts->auxtrace_mmap_pages = KiB(128) / page_size; in arm_spe_snapshot_resolve_auxtrace_defaults()
90 if (opts->mmap_pages == UINT_MAX) in arm_spe_snapshot_resolve_auxtrace_defaults()
91 opts->mmap_pages = KiB(256) / page_size; in arm_spe_snapshot_resolve_auxtrace_defaults()
93 } else if (!opts->auxtrace_mmap_pages && !privileged && opts->mmap_pages == UINT_MAX) { in arm_spe_snapshot_resolve_auxtrace_defaults()
94 opts->mmap_pages = KiB(256) / page_size; in arm_spe_snapshot_resolve_auxtrace_defaults()
98 * '-m,xyz' was specified but no snapshot size, so make the snapshot size as big as the in arm_spe_snapshot_resolve_auxtrace_defaults()
101 if (!opts->auxtrace_snapshot_size) in arm_spe_snapshot_resolve_auxtrace_defaults()
102 opts->auxtrace_snapshot_size = opts->auxtrace_mmap_pages * (size_t)page_size; in arm_spe_snapshot_resolve_auxtrace_defaults()
105 * '-Sxyz' was specified but no auxtrace mmap area, so make the auxtrace mmap area big in arm_spe_snapshot_resolve_auxtrace_defaults()
108 if (!opts->auxtrace_mmap_pages) { in arm_spe_snapshot_resolve_auxtrace_defaults()
109 size_t sz = opts->auxtrace_snapshot_size; in arm_spe_snapshot_resolve_auxtrace_defaults()
112 opts->auxtrace_mmap_pages = roundup_pow_of_two(sz); in arm_spe_snapshot_resolve_auxtrace_defaults()
124 * If kernel driver doesn't advertise a minimum, in arm_spe_pmu__sample_period()
129 pr_debug("arm_spe driver doesn't advertise a min. interval. Using 4096\n"); in arm_spe_pmu__sample_period()
141 struct perf_pmu *arm_spe_pmu = sper->arm_spe_pmu; in arm_spe_recording_options()
143 struct perf_cpu_map *cpus = evlist->core.user_requested_cpus; in arm_spe_recording_options()
144 bool privileged = perf_event_paranoid_check(-1); in arm_spe_recording_options()
149 sper->evlist = evlist; in arm_spe_recording_options()
152 if (evsel->core.attr.type == arm_spe_pmu->type) { in arm_spe_recording_options()
155 return -EINVAL; in arm_spe_recording_options()
157 evsel->core.attr.freq = 0; in arm_spe_recording_options()
158 evsel->core.attr.sample_period = arm_spe_pmu__sample_period(arm_spe_pmu); in arm_spe_recording_options()
159 evsel->needs_auxtrace_mmap = true; in arm_spe_recording_options()
161 opts->full_auxtrace = true; in arm_spe_recording_options()
165 if (!opts->full_auxtrace) in arm_spe_recording_options()
171 if (opts->auxtrace_snapshot_mode) { in arm_spe_recording_options()
173 * Command arguments '-Sxyz' and/or '-m,xyz' are missing, so fill those in with in arm_spe_recording_options()
176 if (!opts->auxtrace_snapshot_size || !opts->auxtrace_mmap_pages) in arm_spe_recording_options()
180 * Snapshot size can't be bigger than the auxtrace area. in arm_spe_recording_options()
182 if (opts->auxtrace_snapshot_size > opts->auxtrace_mmap_pages * (size_t)page_size) { in arm_spe_recording_options()
184 opts->auxtrace_snapshot_size, in arm_spe_recording_options()
185 opts->auxtrace_mmap_pages * (size_t)page_size); in arm_spe_recording_options()
186 return -EINVAL; in arm_spe_recording_options()
190 * Something went wrong somewhere - this shouldn't happen. in arm_spe_recording_options()
192 if (!opts->auxtrace_snapshot_size || !opts->auxtrace_mmap_pages) { in arm_spe_recording_options()
194 return -EINVAL; in arm_spe_recording_options()
198 /* We are in full trace mode but '-m,xyz' wasn't specified */ in arm_spe_recording_options()
199 if (!opts->auxtrace_mmap_pages) { in arm_spe_recording_options()
201 opts->auxtrace_mmap_pages = MiB(4) / page_size; in arm_spe_recording_options()
203 opts->auxtrace_mmap_pages = KiB(128) / page_size; in arm_spe_recording_options()
204 if (opts->mmap_pages == UINT_MAX) in arm_spe_recording_options()
205 opts->mmap_pages = KiB(256) / page_size; in arm_spe_recording_options()
210 if (opts->auxtrace_mmap_pages) { in arm_spe_recording_options()
211 size_t sz = opts->auxtrace_mmap_pages * (size_t)page_size; in arm_spe_recording_options()
217 return -EINVAL; in arm_spe_recording_options()
221 if (opts->auxtrace_snapshot_mode) in arm_spe_recording_options()
223 opts->auxtrace_snapshot_size); in arm_spe_recording_options()
232 * In the case of per-cpu mmaps, sample CPU for AUX event; in arm_spe_recording_options()
253 if (arm_spe_evsel->core.attr.config & bit) in arm_spe_recording_options()
264 tracking_evsel->core.attr.freq = 0; in arm_spe_recording_options()
265 tracking_evsel->core.attr.sample_period = 1; in arm_spe_recording_options()
267 /* In per-cpu case, always need the time of mmap events etc */ in arm_spe_recording_options()
274 tracking_evsel->core.attr.context_switch = 1; in arm_spe_recording_options()
290 return -1; in arm_spe_parse_snapshot_options()
293 opts->auxtrace_snapshot_mode = true; in arm_spe_parse_snapshot_options()
294 opts->auxtrace_snapshot_size = snapshot_size; in arm_spe_parse_snapshot_options()
305 evlist__for_each_entry(ptr->evlist, evsel) { in arm_spe_snapshot_start()
306 if (evsel->core.attr.type == ptr->arm_spe_pmu->type) in arm_spe_snapshot_start()
309 return -EINVAL; in arm_spe_snapshot_start()
318 evlist__for_each_entry(ptr->evlist, evsel) { in arm_spe_snapshot_finish()
319 if (evsel->core.attr.type == ptr->arm_spe_pmu->type) in arm_spe_snapshot_finish()
322 return -EINVAL; in arm_spe_snapshot_finish()
328 int cnt = ptr->wrapped_cnt, new_cnt, i; in arm_spe_alloc_wrapped_array()
337 * Make ptr->wrapped as big as idx. in arm_spe_alloc_wrapped_array()
344 wrapped = reallocarray(ptr->wrapped, new_cnt, sizeof(bool)); in arm_spe_alloc_wrapped_array()
346 return -ENOMEM; in arm_spe_alloc_wrapped_array()
354 ptr->wrapped_cnt = new_cnt; in arm_spe_alloc_wrapped_array()
355 ptr->wrapped = wrapped; in arm_spe_alloc_wrapped_array()
361 size_t buffer_size, u64 head) in arm_spe_buffer_has_wrapped() argument
368 * Defensively handle the case where head might be continually increasing - if its value is in arm_spe_buffer_has_wrapped()
370 * wrapped around. Otherwise, continue to detect if head might have wrapped. in arm_spe_buffer_has_wrapped()
372 if (head >= buffer_size) in arm_spe_buffer_has_wrapped()
378 watermark = buf_size - 512; in arm_spe_buffer_has_wrapped()
381 * The value of head is somewhere within the size of the ring buffer. This can be that there in arm_spe_buffer_has_wrapped()
382 * hasn't been enough data to fill the ring buffer yet or the trace time was so long that in arm_spe_buffer_has_wrapped()
383 * head has numerically wrapped around. To find we need to check if we have data at the in arm_spe_buffer_has_wrapped()
389 * head is less than 512 byte from the end of the ring buffer. in arm_spe_buffer_has_wrapped()
391 if (head > watermark) in arm_spe_buffer_has_wrapped()
392 watermark = head; in arm_spe_buffer_has_wrapped()
401 * If we find trace data at the end of the ring buffer, head has been there and has in arm_spe_buffer_has_wrapped()
413 u64 *head, u64 *old) in arm_spe_find_snapshot() argument
424 if (idx >= ptr->wrapped_cnt) { in arm_spe_find_snapshot()
431 * Check to see if *head has wrapped around. If it hasn't only the in arm_spe_find_snapshot()
432 * amount of data between *head and *old is snapshot'ed to avoid in arm_spe_find_snapshot()
433 * bloating the perf.data file with zeros. But as soon as *head has in arm_spe_find_snapshot()
436 wrapped = ptr->wrapped[idx]; in arm_spe_find_snapshot()
437 if (!wrapped && arm_spe_buffer_has_wrapped(data, mm->len, *head)) { in arm_spe_find_snapshot()
439 ptr->wrapped[idx] = true; in arm_spe_find_snapshot()
442 pr_debug3("%s: mmap index %d old head %zu new head %zu size %zu\n", in arm_spe_find_snapshot()
443 __func__, idx, (size_t)*old, (size_t)*head, mm->len); in arm_spe_find_snapshot()
446 * No wrap has occurred, we can just use *head and *old. in arm_spe_find_snapshot()
452 * *head has wrapped around - adjust *head and *old to pickup the in arm_spe_find_snapshot()
455 if (*head >= mm->len) { in arm_spe_find_snapshot()
456 *old = *head - mm->len; in arm_spe_find_snapshot()
458 *head += mm->len; in arm_spe_find_snapshot()
459 *old = *head - mm->len; in arm_spe_find_snapshot()
479 zfree(&sper->wrapped); in arm_spe_recording_free()
489 *err = -ENODEV; in arm_spe_recording_init()
495 *err = -ENOMEM; in arm_spe_recording_init()
499 sper->arm_spe_pmu = arm_spe_pmu; in arm_spe_recording_init()
500 sper->itr.pmu = arm_spe_pmu; in arm_spe_recording_init()
501 sper->itr.snapshot_start = arm_spe_snapshot_start; in arm_spe_recording_init()
502 sper->itr.snapshot_finish = arm_spe_snapshot_finish; in arm_spe_recording_init()
503 sper->itr.find_snapshot = arm_spe_find_snapshot; in arm_spe_recording_init()
504 sper->itr.parse_snapshot_options = arm_spe_parse_snapshot_options; in arm_spe_recording_init()
505 sper->itr.recording_options = arm_spe_recording_options; in arm_spe_recording_init()
506 sper->itr.info_priv_size = arm_spe_info_priv_size; in arm_spe_recording_init()
507 sper->itr.info_fill = arm_spe_info_fill; in arm_spe_recording_init()
508 sper->itr.free = arm_spe_recording_free; in arm_spe_recording_init()
509 sper->itr.reference = arm_spe_reference; in arm_spe_recording_init()
510 sper->itr.read_finish = auxtrace_record__read_finish; in arm_spe_recording_init()
511 sper->itr.alignment = 0; in arm_spe_recording_init()
514 return &sper->itr; in arm_spe_recording_init()
520 attr->sample_period = arm_spe_pmu__sample_period(arm_spe_pmu); in arm_spe_pmu_default_config()