diff options
Diffstat (limited to 'tools/perf/util/intel-pt.c')
| -rw-r--r-- | tools/perf/util/intel-pt.c | 47 | 
1 files changed, 32 insertions, 15 deletions
diff --git a/tools/perf/util/intel-pt.c b/tools/perf/util/intel-pt.c index 48c1d415c6b0..149ff361ca78 100644 --- a/tools/perf/util/intel-pt.c +++ b/tools/perf/util/intel-pt.c @@ -206,6 +206,16 @@ static void intel_pt_dump_event(struct intel_pt *pt, unsigned char *buf,  	intel_pt_dump(pt, buf, len);  } +static void intel_pt_log_event(union perf_event *event) +{ +	FILE *f = intel_pt_log_fp(); + +	if (!intel_pt_enable_logging || !f) +		return; + +	perf_event__fprintf(event, f); +} +  static int intel_pt_do_fix_overlap(struct intel_pt *pt, struct auxtrace_buffer *a,  				   struct auxtrace_buffer *b)  { @@ -407,6 +417,13 @@ intel_pt_cache_lookup(struct dso *dso, struct machine *machine, u64 offset)  	return auxtrace_cache__lookup(dso->auxtrace_cache, offset);  } +static inline u8 intel_pt_cpumode(struct intel_pt *pt, uint64_t ip) +{ +	return ip >= pt->kernel_start ? +	       PERF_RECORD_MISC_KERNEL : +	       PERF_RECORD_MISC_USER; +} +  static int intel_pt_walk_next_insn(struct intel_pt_insn *intel_pt_insn,  				   uint64_t *insn_cnt_ptr, uint64_t *ip,  				   uint64_t to_ip, uint64_t max_insn_cnt, @@ -429,10 +446,7 @@ static int intel_pt_walk_next_insn(struct intel_pt_insn *intel_pt_insn,  	if (to_ip && *ip == to_ip)  		goto out_no_cache; -	if (*ip >= ptq->pt->kernel_start) -		cpumode = PERF_RECORD_MISC_KERNEL; -	else -		cpumode = PERF_RECORD_MISC_USER; +	cpumode = intel_pt_cpumode(ptq->pt, *ip);  	thread = ptq->thread;  	if (!thread) { @@ -759,7 +773,8 @@ static struct intel_pt_queue *intel_pt_alloc_queue(struct intel_pt *pt,  	if (pt->synth_opts.callchain) {  		size_t sz = sizeof(struct ip_callchain); -		sz += pt->synth_opts.callchain_sz * sizeof(u64); +		/* Add 1 to callchain_sz for callchain context */ +		sz += (pt->synth_opts.callchain_sz + 1) * sizeof(u64);  		ptq->chain = zalloc(sz);  		if (!ptq->chain)  			goto out_free; @@ -1058,15 +1073,11 @@ static void intel_pt_prep_b_sample(struct intel_pt *pt,  				   union perf_event *event,  				   struct perf_sample *sample)  { -	event->sample.header.type = PERF_RECORD_SAMPLE; -	event->sample.header.misc = PERF_RECORD_MISC_USER; -	event->sample.header.size = sizeof(struct perf_event_header); -  	if (!pt->timeless_decoding)  		sample->time = tsc_to_perf_time(ptq->timestamp, &pt->tc); -	sample->cpumode = PERF_RECORD_MISC_USER;  	sample->ip = ptq->state->from_ip; +	sample->cpumode = intel_pt_cpumode(pt, sample->ip);  	sample->pid = ptq->pid;  	sample->tid = ptq->tid;  	sample->addr = ptq->state->to_ip; @@ -1075,6 +1086,10 @@ static void intel_pt_prep_b_sample(struct intel_pt *pt,  	sample->flags = ptq->flags;  	sample->insn_len = ptq->insn_len;  	memcpy(sample->insn, ptq->insn, INTEL_PT_INSN_BUF_SZ); + +	event->sample.header.type = PERF_RECORD_SAMPLE; +	event->sample.header.misc = sample->cpumode; +	event->sample.header.size = sizeof(struct perf_event_header);  }  static int intel_pt_inject_event(union perf_event *event, @@ -1160,7 +1175,8 @@ static void intel_pt_prep_sample(struct intel_pt *pt,  	if (pt->synth_opts.callchain) {  		thread_stack__sample(ptq->thread, ptq->chain, -				     pt->synth_opts.callchain_sz, sample->ip); +				     pt->synth_opts.callchain_sz + 1, +				     sample->ip, pt->kernel_start);  		sample->callchain = ptq->chain;  	} @@ -2004,9 +2020,9 @@ static int intel_pt_process_event(struct perf_session *session,  		 event->header.type == PERF_RECORD_SWITCH_CPU_WIDE)  		err = intel_pt_context_switch(pt, event, sample); -	intel_pt_log("event %s (%u): cpu %d time %"PRIu64" tsc %#"PRIx64"\n", -		     perf_event__name(event->header.type), event->header.type, -		     sample->cpu, sample->time, timestamp); +	intel_pt_log("event %u: cpu %d time %"PRIu64" tsc %#"PRIx64" ", +		     event->header.type, sample->cpu, sample->time, timestamp); +	intel_pt_log_event(event);  	return err;  } @@ -2559,7 +2575,8 @@ int intel_pt_process_auxtrace_info(union perf_event *event,  	if (session->itrace_synth_opts && session->itrace_synth_opts->set) {  		pt->synth_opts = *session->itrace_synth_opts;  	} else { -		itrace_synth_opts__set_default(&pt->synth_opts); +		itrace_synth_opts__set_default(&pt->synth_opts, +				session->itrace_synth_opts->default_no_sample);  		if (use_browser != -1) {  			pt->synth_opts.branches = false;  			pt->synth_opts.callchain = true;  | 
