diff options
Diffstat (limited to 'tools/perf/util/annotate.c')
| -rw-r--r-- | tools/perf/util/annotate.c | 49 | 
1 files changed, 45 insertions, 4 deletions
diff --git a/tools/perf/util/annotate.c b/tools/perf/util/annotate.c index 6936daf89ddd..ac9805e0bc76 100644 --- a/tools/perf/util/annotate.c +++ b/tools/perf/util/annotate.c @@ -134,6 +134,7 @@ static int arch__associate_ins_ops(struct arch* arch, const char *name, struct i  	return 0;  } +#include "arch/arc/annotate/instructions.c"  #include "arch/arm/annotate/instructions.c"  #include "arch/arm64/annotate/instructions.c"  #include "arch/x86/annotate/instructions.c" @@ -143,6 +144,10 @@ static int arch__associate_ins_ops(struct arch* arch, const char *name, struct i  static struct arch architectures[] = {  	{ +		.name = "arc", +		.init = arc__annotate_init, +	}, +	{  		.name = "arm",  		.init = arm__annotate_init,  	}, @@ -1000,6 +1005,7 @@ static unsigned annotation__count_insn(struct annotation *notes, u64 start, u64  static void annotation__count_and_fill(struct annotation *notes, u64 start, u64 end, struct cyc_hist *ch)  {  	unsigned n_insn; +	unsigned int cover_insn = 0;  	u64 offset;  	n_insn = annotation__count_insn(notes, start, end); @@ -1013,21 +1019,34 @@ static void annotation__count_and_fill(struct annotation *notes, u64 start, u64  		for (offset = start; offset <= end; offset++) {  			struct annotation_line *al = notes->offsets[offset]; -			if (al) +			if (al && al->ipc == 0.0) {  				al->ipc = ipc; +				cover_insn++; +			} +		} + +		if (cover_insn) { +			notes->hit_cycles += ch->cycles; +			notes->hit_insn += n_insn * ch->num; +			notes->cover_insn += cover_insn;  		}  	}  }  void annotation__compute_ipc(struct annotation *notes, size_t size)  { -	u64 offset; +	s64 offset;  	if (!notes->src || !notes->src->cycles_hist)  		return; +	notes->total_insn = annotation__count_insn(notes, 0, size - 1); +	notes->hit_cycles = 0; +	notes->hit_insn = 0; +	notes->cover_insn = 0; +  	pthread_mutex_lock(¬es->lock); -	for (offset = 0; offset < size; ++offset) { +	for (offset = size - 1; offset >= 0; --offset) {  		struct cyc_hist *ch;  		ch = ¬es->src->cycles_hist[offset]; @@ -1758,7 +1777,7 @@ static int symbol__disassemble(struct symbol *sym, struct annotate_args *args)  	while (!feof(file)) {  		/*  		 * The source code line number (lineno) needs to be kept in -		 * accross calls to symbol__parse_objdump_line(), so that it +		 * across calls to symbol__parse_objdump_line(), so that it  		 * can associate it with the instructions till the next one.  		 * See disasm_line__new() and struct disasm_line::line_nr.  		 */ @@ -2563,6 +2582,22 @@ call_like:  	disasm_line__scnprintf(dl, bf, size, !notes->options->use_offset);  } +static void ipc_coverage_string(char *bf, int size, struct annotation *notes) +{ +	double ipc = 0.0, coverage = 0.0; + +	if (notes->hit_cycles) +		ipc = notes->hit_insn / ((double)notes->hit_cycles); + +	if (notes->total_insn) { +		coverage = notes->cover_insn * 100.0 / +			((double)notes->total_insn); +	} + +	scnprintf(bf, size, "(Average IPC: %.2f, IPC Coverage: %.1f%%)", +		  ipc, coverage); +} +  static void __annotation_line__write(struct annotation_line *al, struct annotation *notes,  				     bool first_line, bool current_entry, bool change_color, int width,  				     void *obj, unsigned int percent_type, @@ -2658,6 +2693,11 @@ static void __annotation_line__write(struct annotation_line *al, struct annotati  					    ANNOTATION__MINMAX_CYCLES_WIDTH - 1,  					    "Cycle(min/max)");  		} + +		if (show_title && !*al->line) { +			ipc_coverage_string(bf, sizeof(bf), notes); +			obj__printf(obj, "%*s", ANNOTATION__AVG_IPC_WIDTH, bf); +		}  	}  	obj__printf(obj, " "); @@ -2763,6 +2803,7 @@ int symbol__annotate2(struct symbol *sym, struct map *map, struct perf_evsel *ev  	notes->nr_events = nr_pcnt;  	annotation__update_column_widths(notes); +	sym->annotate2 = true;  	return 0;  | 
