tools/perf/arch/x86/util/intel-bts.c

Source file repositories/reference/linux-study-clean/tools/perf/arch/x86/util/intel-bts.c

File Facts

System
Linux kernel
Corpus path
tools/perf/arch/x86/util/intel-bts.c
Extension
.c
Size
11907 bytes
Lines
450
Domain
Support Tooling And Documentation
Bucket
tools
Inferred role
Support Tooling And Documentation: implementation source
Status
source implementation candidate

Why This File Exists

Repository support layer: documentation, build tooling, samples, user-space helper tools, generated initramfs support, licenses, and validation utilities.

Dependency Surface

Detected Declarations

Annotated Snippet

struct intel_bts_snapshot_ref {
	void	*ref_buf;
	size_t	ref_offset;
	bool	wrapped;
};

struct intel_bts_recording {
	struct auxtrace_record		itr;
	struct perf_pmu			*intel_bts_pmu;
	struct evlist		*evlist;
	bool				snapshot_mode;
	size_t				snapshot_size;
	int				snapshot_ref_cnt;
	struct intel_bts_snapshot_ref	*snapshot_refs;
};

struct branch {
	u64 from;
	u64 to;
	u64 misc;
};

static size_t
intel_bts_info_priv_size(struct auxtrace_record *itr __maybe_unused,
			 struct evlist *evlist __maybe_unused)
{
	return INTEL_BTS_AUXTRACE_PRIV_SIZE;
}

static int intel_bts_info_fill(struct auxtrace_record *itr,
			       struct perf_session *session,
			       struct perf_record_auxtrace_info *auxtrace_info,
			       size_t priv_size)
{
	struct intel_bts_recording *btsr =
			container_of(itr, struct intel_bts_recording, itr);
	struct perf_pmu *intel_bts_pmu = btsr->intel_bts_pmu;
	struct perf_event_mmap_page *pc;
	struct perf_tsc_conversion tc = { .time_mult = 0, };
	bool cap_user_time_zero = false;
	int err;

	if (priv_size != INTEL_BTS_AUXTRACE_PRIV_SIZE)
		return -EINVAL;

	if (!session->evlist->core.nr_mmaps)
		return -EINVAL;

	pc = session->evlist->mmap[0].core.base;
	if (pc) {
		err = perf_read_tsc_conversion(pc, &tc);
		if (err) {
			if (err != -EOPNOTSUPP)
				return err;
		} else {
			cap_user_time_zero = tc.time_mult != 0;
		}
		if (!cap_user_time_zero)
			ui__warning("Intel BTS: TSC not available\n");
	}

	auxtrace_info->type = PERF_AUXTRACE_INTEL_BTS;
	auxtrace_info->priv[INTEL_BTS_PMU_TYPE] = intel_bts_pmu->type;
	auxtrace_info->priv[INTEL_BTS_TIME_SHIFT] = tc.time_shift;
	auxtrace_info->priv[INTEL_BTS_TIME_MULT] = tc.time_mult;
	auxtrace_info->priv[INTEL_BTS_TIME_ZERO] = tc.time_zero;
	auxtrace_info->priv[INTEL_BTS_CAP_USER_TIME_ZERO] = cap_user_time_zero;
	auxtrace_info->priv[INTEL_BTS_SNAPSHOT_MODE] = btsr->snapshot_mode;

	return 0;
}

static int intel_bts_recording_options(struct auxtrace_record *itr,
				       struct evlist *evlist,
				       struct record_opts *opts)
{
	struct intel_bts_recording *btsr =
			container_of(itr, struct intel_bts_recording, itr);
	struct perf_pmu *intel_bts_pmu = btsr->intel_bts_pmu;
	struct evsel *evsel, *intel_bts_evsel = NULL;
	const struct perf_cpu_map *cpus = evlist->core.user_requested_cpus;
	bool privileged = perf_event_paranoid_check(-1);

	if (opts->auxtrace_sample_mode) {
		pr_err("Intel BTS does not support AUX area sampling\n");
		return -EINVAL;
	}

	btsr->evlist = evlist;
	btsr->snapshot_mode = opts->auxtrace_snapshot_mode;

Annotation

Implementation Notes