Lines Matching +full:cpu +full:- +full:offset

1 // SPDX-License-Identifier: GPL-2.0
11 #include <linux/coresight-pmu.h>
18 #include "cs-etm.h"
29 #include "../../util/cs-etm.h"
60 static bool cs_etm_is_etmv4(struct auxtrace_record *itr, int cpu);
63 struct evsel *evsel, int cpu) in cs_etm_set_context_id() argument
68 int err = -EINVAL; in cs_etm_set_context_id()
72 cs_etm_pmu = ptr->cs_etm_pmu; in cs_etm_set_context_id()
74 if (!cs_etm_is_etmv4(itr, cpu)) in cs_etm_set_context_id()
78 snprintf(path, PATH_MAX, "cpu%d/%s", in cs_etm_set_context_id()
79 cpu, metadata_etmv4_ro[CS_ETMV4_TRCIDR2]); in cs_etm_set_context_id()
90 * TRCIDR2.CIDSIZE, bit [9-5], indicates whether contextID tracing in cs_etm_set_context_id()
93 * 0b00100 Maximum of 32-bit Context ID size. in cs_etm_set_context_id()
98 err = -EINVAL; in cs_etm_set_context_id()
103 evsel->core.attr.config |= (1 << ETM_OPT_CTXTID); in cs_etm_set_context_id()
112 struct evsel *evsel, int cpu) in cs_etm_set_timestamp() argument
117 int err = -EINVAL; in cs_etm_set_timestamp()
121 cs_etm_pmu = ptr->cs_etm_pmu; in cs_etm_set_timestamp()
123 if (!cs_etm_is_etmv4(itr, cpu)) in cs_etm_set_timestamp()
127 snprintf(path, PATH_MAX, "cpu%d/%s", in cs_etm_set_timestamp()
128 cpu, metadata_etmv4_ro[CS_ETMV4_TRCIDR0]); in cs_etm_set_timestamp()
139 * TRCIDR0.TSSIZE, bit [28-24], indicates whether global timestamping in cs_etm_set_timestamp()
147 err = -EINVAL; in cs_etm_set_timestamp()
152 evsel->core.attr.config |= (1 << ETM_OPT_TS); in cs_etm_set_timestamp()
162 int i, err = -EINVAL; in cs_etm_set_option()
163 struct perf_cpu_map *event_cpus = evsel->evlist->core.cpus; in cs_etm_set_option()
166 /* Set option of each CPU we have */ in cs_etm_set_option()
205 return -1; in cs_etm_parse_snapshot_options()
208 opts->auxtrace_snapshot_mode = true; in cs_etm_parse_snapshot_options()
209 opts->auxtrace_snapshot_size = snapshot_size; in cs_etm_parse_snapshot_options()
210 ptr->snapshot_size = snapshot_size; in cs_etm_parse_snapshot_options()
220 int ret = -EINVAL; in cs_etm_set_sink_attr()
223 if (evsel->core.attr.config2 & GENMASK(31, 0)) in cs_etm_set_sink_attr()
226 list_for_each_entry(term, &evsel->config_terms, list) { in cs_etm_set_sink_attr()
227 if (term->type != EVSEL__CONFIG_TERM_DRV_CFG) in cs_etm_set_sink_attr()
230 sink = term->val.str; in cs_etm_set_sink_attr()
241 evsel->core.attr.config2 |= hash; in cs_etm_set_sink_attr()
246 * No sink was provided on the command line - allow the CoreSight in cs_etm_set_sink_attr()
259 struct perf_pmu *cs_etm_pmu = ptr->cs_etm_pmu; in cs_etm_recording_options()
261 struct perf_cpu_map *cpus = evlist->core.cpus; in cs_etm_recording_options()
262 bool privileged = perf_event_paranoid_check(-1); in cs_etm_recording_options()
265 ptr->evlist = evlist; in cs_etm_recording_options()
266 ptr->snapshot_mode = opts->auxtrace_snapshot_mode; in cs_etm_recording_options()
270 opts->record_switch_events = true; in cs_etm_recording_options()
273 if (evsel->core.attr.type == cs_etm_pmu->type) { in cs_etm_recording_options()
277 return -EINVAL; in cs_etm_recording_options()
279 evsel->core.attr.freq = 0; in cs_etm_recording_options()
280 evsel->core.attr.sample_period = 1; in cs_etm_recording_options()
282 opts->full_auxtrace = true; in cs_etm_recording_options()
294 if (opts->use_clockid) { in cs_etm_recording_options()
295 pr_err("Cannot use clockid (-k option) with %s\n", in cs_etm_recording_options()
297 return -EINVAL; in cs_etm_recording_options()
301 if (opts->auxtrace_snapshot_mode) { in cs_etm_recording_options()
303 * No size were given to '-S' or '-m,', so go with in cs_etm_recording_options()
306 if (!opts->auxtrace_snapshot_size && in cs_etm_recording_options()
307 !opts->auxtrace_mmap_pages) { in cs_etm_recording_options()
309 opts->auxtrace_mmap_pages = MiB(4) / page_size; in cs_etm_recording_options()
311 opts->auxtrace_mmap_pages = in cs_etm_recording_options()
313 if (opts->mmap_pages == UINT_MAX) in cs_etm_recording_options()
314 opts->mmap_pages = KiB(256) / page_size; in cs_etm_recording_options()
316 } else if (!opts->auxtrace_mmap_pages && !privileged && in cs_etm_recording_options()
317 opts->mmap_pages == UINT_MAX) { in cs_etm_recording_options()
318 opts->mmap_pages = KiB(256) / page_size; in cs_etm_recording_options()
322 * '-m,xyz' was specified but no snapshot size, so make the in cs_etm_recording_options()
325 if (!opts->auxtrace_snapshot_size) { in cs_etm_recording_options()
326 opts->auxtrace_snapshot_size = in cs_etm_recording_options()
327 opts->auxtrace_mmap_pages * (size_t)page_size; in cs_etm_recording_options()
331 * -Sxyz was specified but no auxtrace mmap area, so make the in cs_etm_recording_options()
335 if (!opts->auxtrace_mmap_pages) { in cs_etm_recording_options()
336 size_t sz = opts->auxtrace_snapshot_size; in cs_etm_recording_options()
339 opts->auxtrace_mmap_pages = roundup_pow_of_two(sz); in cs_etm_recording_options()
343 if (opts->auxtrace_snapshot_size > in cs_etm_recording_options()
344 opts->auxtrace_mmap_pages * (size_t)page_size) { in cs_etm_recording_options()
346 opts->auxtrace_snapshot_size, in cs_etm_recording_options()
347 opts->auxtrace_mmap_pages * (size_t)page_size); in cs_etm_recording_options()
348 return -EINVAL; in cs_etm_recording_options()
351 /* Something went wrong somewhere - this shouldn't happen */ in cs_etm_recording_options()
352 if (!opts->auxtrace_snapshot_size || in cs_etm_recording_options()
353 !opts->auxtrace_mmap_pages) { in cs_etm_recording_options()
355 return -EINVAL; in cs_etm_recording_options()
359 /* We are in full trace mode but '-m,xyz' wasn't specified */ in cs_etm_recording_options()
360 if (opts->full_auxtrace && !opts->auxtrace_mmap_pages) { in cs_etm_recording_options()
362 opts->auxtrace_mmap_pages = MiB(4) / page_size; in cs_etm_recording_options()
364 opts->auxtrace_mmap_pages = KiB(128) / page_size; in cs_etm_recording_options()
365 if (opts->mmap_pages == UINT_MAX) in cs_etm_recording_options()
366 opts->mmap_pages = KiB(256) / page_size; in cs_etm_recording_options()
372 if (opts->auxtrace_mmap_pages) { in cs_etm_recording_options()
374 size_t sz = opts->auxtrace_mmap_pages * (size_t)page_size; in cs_etm_recording_options()
377 opts->auxtrace_mmap_pages > max_page) { in cs_etm_recording_options()
378 opts->auxtrace_mmap_pages = max_page; in cs_etm_recording_options()
386 return -EINVAL; in cs_etm_recording_options()
390 if (opts->auxtrace_snapshot_mode) in cs_etm_recording_options()
392 opts->auxtrace_snapshot_size); in cs_etm_recording_options()
401 * In the case of per-cpu mmaps, we need the CPU on the in cs_etm_recording_options()
406 evsel__set_sample_bit(cs_etm_evsel, CPU); in cs_etm_recording_options()
415 if (opts->full_auxtrace) { in cs_etm_recording_options()
425 tracking_evsel->core.attr.freq = 0; in cs_etm_recording_options()
426 tracking_evsel->core.attr.sample_period = 1; in cs_etm_recording_options()
428 /* In per-cpu case, always need the time of mmap events etc */ in cs_etm_recording_options()
442 struct perf_pmu *cs_etm_pmu = ptr->cs_etm_pmu; in cs_etm_get_config()
443 struct evlist *evlist = ptr->evlist; in cs_etm_get_config()
447 if (evsel->core.attr.type == cs_etm_pmu->type) { in cs_etm_get_config()
453 * drivers/hwtracing/coresight/coresight-perf.c for in cs_etm_get_config()
456 config = evsel->core.attr.config; in cs_etm_get_config()
498 struct perf_cpu_map *event_cpus = evlist->core.cpus; in cs_etm_info_priv_size()
501 /* cpu map is not empty, we have specific CPUs to work with */ in cs_etm_info_priv_size()
533 static bool cs_etm_is_etmv4(struct auxtrace_record *itr, int cpu) in cs_etm_is_etmv4() argument
541 struct perf_pmu *cs_etm_pmu = ptr->cs_etm_pmu; in cs_etm_is_etmv4()
544 snprintf(path, PATH_MAX, "cpu%d/%s", in cs_etm_is_etmv4()
545 cpu, metadata_etmv4_ro[CS_ETMV4_TRCIDR0]); in cs_etm_is_etmv4()
555 static int cs_etm_get_ro(struct perf_pmu *pmu, int cpu, const char *path) in cs_etm_get_ro() argument
562 snprintf(pmu_path, PATH_MAX, "cpu%d/%s", cpu, path); in cs_etm_get_ro()
571 static void cs_etm_get_metadata(int cpu, u32 *offset, in cs_etm_get_metadata() argument
579 struct perf_pmu *cs_etm_pmu = ptr->cs_etm_pmu; in cs_etm_get_metadata()
581 /* first see what kind of tracer this cpu is affined to */ in cs_etm_get_metadata()
582 if (cs_etm_is_etmv4(itr, cpu)) { in cs_etm_get_metadata()
585 info->priv[*offset + CS_ETMV4_TRCCONFIGR] = in cs_etm_get_metadata()
588 info->priv[*offset + CS_ETMV4_TRCTRACEIDR] = in cs_etm_get_metadata()
589 coresight_get_trace_id(cpu); in cs_etm_get_metadata()
590 /* Get read-only information from sysFS */ in cs_etm_get_metadata()
591 info->priv[*offset + CS_ETMV4_TRCIDR0] = in cs_etm_get_metadata()
592 cs_etm_get_ro(cs_etm_pmu, cpu, in cs_etm_get_metadata()
594 info->priv[*offset + CS_ETMV4_TRCIDR1] = in cs_etm_get_metadata()
595 cs_etm_get_ro(cs_etm_pmu, cpu, in cs_etm_get_metadata()
597 info->priv[*offset + CS_ETMV4_TRCIDR2] = in cs_etm_get_metadata()
598 cs_etm_get_ro(cs_etm_pmu, cpu, in cs_etm_get_metadata()
600 info->priv[*offset + CS_ETMV4_TRCIDR8] = in cs_etm_get_metadata()
601 cs_etm_get_ro(cs_etm_pmu, cpu, in cs_etm_get_metadata()
603 info->priv[*offset + CS_ETMV4_TRCAUTHSTATUS] = in cs_etm_get_metadata()
604 cs_etm_get_ro(cs_etm_pmu, cpu, in cs_etm_get_metadata()
613 info->priv[*offset + CS_ETM_ETMCR] = cs_etm_get_config(itr); in cs_etm_get_metadata()
615 info->priv[*offset + CS_ETM_ETMTRACEIDR] = in cs_etm_get_metadata()
616 coresight_get_trace_id(cpu); in cs_etm_get_metadata()
617 /* Get read-only information from sysFS */ in cs_etm_get_metadata()
618 info->priv[*offset + CS_ETM_ETMCCER] = in cs_etm_get_metadata()
619 cs_etm_get_ro(cs_etm_pmu, cpu, in cs_etm_get_metadata()
621 info->priv[*offset + CS_ETM_ETMIDR] = in cs_etm_get_metadata()
622 cs_etm_get_ro(cs_etm_pmu, cpu, in cs_etm_get_metadata()
630 info->priv[*offset + CS_ETM_MAGIC] = magic; in cs_etm_get_metadata()
631 info->priv[*offset + CS_ETM_CPU] = cpu; in cs_etm_get_metadata()
632 /* Where the next CPU entry should start from */ in cs_etm_get_metadata()
633 *offset += increment; in cs_etm_get_metadata()
642 u32 offset; in cs_etm_info_fill() local
645 struct perf_cpu_map *event_cpus = session->evlist->core.cpus; in cs_etm_info_fill()
649 struct perf_pmu *cs_etm_pmu = ptr->cs_etm_pmu; in cs_etm_info_fill()
651 if (priv_size != cs_etm_info_priv_size(itr, session->evlist)) in cs_etm_info_fill()
652 return -EINVAL; in cs_etm_info_fill()
654 if (!session->evlist->core.nr_mmaps) in cs_etm_info_fill()
655 return -EINVAL; in cs_etm_info_fill()
665 return -EINVAL; in cs_etm_info_fill()
673 type = cs_etm_pmu->type; in cs_etm_info_fill()
676 info->type = PERF_AUXTRACE_CS_ETM; in cs_etm_info_fill()
677 info->priv[CS_HEADER_VERSION_0] = 0; in cs_etm_info_fill()
678 info->priv[CS_PMU_TYPE_CPUS] = type << 32; in cs_etm_info_fill()
679 info->priv[CS_PMU_TYPE_CPUS] |= nr_cpu; in cs_etm_info_fill()
680 info->priv[CS_ETM_SNAPSHOT] = ptr->snapshot_mode; in cs_etm_info_fill()
682 offset = CS_ETM_SNAPSHOT + 1; in cs_etm_info_fill()
684 for (i = 0; i < cpu__max_cpu() && offset < priv_size; i++) in cs_etm_info_fill()
686 cs_etm_get_metadata(i, &offset, itr, info); in cs_etm_info_fill()
696 int cnt = ptr->wrapped_cnt; in cs_etm_alloc_wrapped_array()
698 /* Make @ptr->wrapped as big as @idx */ in cs_etm_alloc_wrapped_array()
707 wrapped = realloc(ptr->wrapped, cnt * sizeof(bool)); in cs_etm_alloc_wrapped_array()
709 return -ENOMEM; in cs_etm_alloc_wrapped_array()
711 wrapped[cnt - 1] = false; in cs_etm_alloc_wrapped_array()
712 ptr->wrapped_cnt = cnt; in cs_etm_alloc_wrapped_array()
713 ptr->wrapped = wrapped; in cs_etm_alloc_wrapped_array()
729 watermark = buf_size - 512; in cs_etm_buffer_has_wrapped()
732 * @head is continuously increasing - if its value is equal or greater in cs_etm_buffer_has_wrapped()
783 if (idx >= ptr->wrapped_cnt) { in cs_etm_find_snapshot()
795 wrapped = ptr->wrapped[idx]; in cs_etm_find_snapshot()
796 if (!wrapped && cs_etm_buffer_has_wrapped(data, mm->len, *head)) { in cs_etm_find_snapshot()
798 ptr->wrapped[idx] = true; in cs_etm_find_snapshot()
802 __func__, idx, (size_t)*old, (size_t)*head, mm->len); in cs_etm_find_snapshot()
809 * *head has wrapped around - adjust *head and *old to pickup the in cs_etm_find_snapshot()
812 if (*head >= mm->len) { in cs_etm_find_snapshot()
813 *old = *head - mm->len; in cs_etm_find_snapshot()
815 *head += mm->len; in cs_etm_find_snapshot()
816 *old = *head - mm->len; in cs_etm_find_snapshot()
828 evlist__for_each_entry(ptr->evlist, evsel) { in cs_etm_snapshot_start()
829 if (evsel->core.attr.type == ptr->cs_etm_pmu->type) in cs_etm_snapshot_start()
832 return -EINVAL; in cs_etm_snapshot_start()
841 evlist__for_each_entry(ptr->evlist, evsel) { in cs_etm_snapshot_finish()
842 if (evsel->core.attr.type == ptr->cs_etm_pmu->type) in cs_etm_snapshot_finish()
845 return -EINVAL; in cs_etm_snapshot_finish()
859 zfree(&ptr->wrapped); in cs_etm_recording_free()
871 *err = -EINVAL; in cs_etm_record_init()
877 *err = -ENOMEM; in cs_etm_record_init()
881 ptr->cs_etm_pmu = cs_etm_pmu; in cs_etm_record_init()
882 ptr->itr.pmu = cs_etm_pmu; in cs_etm_record_init()
883 ptr->itr.parse_snapshot_options = cs_etm_parse_snapshot_options; in cs_etm_record_init()
884 ptr->itr.recording_options = cs_etm_recording_options; in cs_etm_record_init()
885 ptr->itr.info_priv_size = cs_etm_info_priv_size; in cs_etm_record_init()
886 ptr->itr.info_fill = cs_etm_info_fill; in cs_etm_record_init()
887 ptr->itr.find_snapshot = cs_etm_find_snapshot; in cs_etm_record_init()
888 ptr->itr.snapshot_start = cs_etm_snapshot_start; in cs_etm_record_init()
889 ptr->itr.snapshot_finish = cs_etm_snapshot_finish; in cs_etm_record_init()
890 ptr->itr.reference = cs_etm_reference; in cs_etm_record_init()
891 ptr->itr.free = cs_etm_recording_free; in cs_etm_record_init()
892 ptr->itr.read_finish = auxtrace_record__read_finish; in cs_etm_record_init()
895 return &ptr->itr; in cs_etm_record_init()