Commit 1cf4df03 authored by Namhyung Kim's avatar Namhyung Kim

perf annotate-data: Handle macro fusion on x86

When a sample was come from a conditional branch without a memory
operand, it could be due to a macro fusion with a previous instruction.
So it needs to check the memory operand in the previous one.

This improves the stat like below:

  Annotate data type stats:
  total 294, ok 147 (50.0%), bad 147 (50.0%)
  -----------------------------------------------------------
          30 : no_sym
          32 : no_mem_ops
          71 : no_var
           6 : no_typeinfo
           8 : bad_offset
Reviewed-by: default avatarIan Rogers <irogers@google.com>
Cc: Stephane Eranian <eranian@google.com>
Cc: Masami Hiramatsu <mhiramat@kernel.org>
Link: https://lore.kernel.org/r/20240117062657.985479-3-namhyung@kernel.orgSigned-off-by: default avatarNamhyung Kim <namhyung@kernel.org>
parent a3397d69
...@@ -3751,6 +3751,7 @@ struct annotated_data_type *hist_entry__get_data_type(struct hist_entry *he) ...@@ -3751,6 +3751,7 @@ struct annotated_data_type *hist_entry__get_data_type(struct hist_entry *he)
return NULL; return NULL;
} }
retry:
istat = annotate_data_stat(&ann_insn_stat, dl->ins.name); istat = annotate_data_stat(&ann_insn_stat, dl->ins.name);
if (istat == NULL) { if (istat == NULL) {
ann_data_stat.no_insn++; ann_data_stat.no_insn++;
...@@ -3767,7 +3768,7 @@ struct annotated_data_type *hist_entry__get_data_type(struct hist_entry *he) ...@@ -3767,7 +3768,7 @@ struct annotated_data_type *hist_entry__get_data_type(struct hist_entry *he)
if (!op_loc->mem_ref) if (!op_loc->mem_ref)
continue; continue;
/* Recalculate IP since it can be changed due to LOCK prefix */ /* Recalculate IP because of LOCK prefix or insn fusion */
ip = ms->sym->start + dl->al.offset; ip = ms->sym->start + dl->al.offset;
mem_type = find_data_type(ms, ip, op_loc->reg, op_loc->offset); mem_type = find_data_type(ms, ip, op_loc->reg, op_loc->offset);
...@@ -3786,6 +3787,20 @@ struct annotated_data_type *hist_entry__get_data_type(struct hist_entry *he) ...@@ -3786,6 +3787,20 @@ struct annotated_data_type *hist_entry__get_data_type(struct hist_entry *he)
return mem_type; return mem_type;
} }
/*
* Some instructions can be fused and the actual memory access came
* from the previous instruction.
*/
if (dl->al.offset > 0) {
struct disasm_line *prev_dl;
prev_dl = list_prev_entry(dl, al.node);
if (ins__is_fused(arch, prev_dl->ins.name, dl->ins.name)) {
dl = prev_dl;
goto retry;
}
}
ann_data_stat.no_mem_ops++; ann_data_stat.no_mem_ops++;
istat->bad++; istat->bad++;
return NULL; return NULL;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment