Skip to content

Commit

Permalink
i#2130, i#1569: Port api/samples/div.c to AArch64 and enable it.
Browse files Browse the repository at this point in the history
Also port to AArch32 and reverse the condition: it was counting
divisions by a non-power of 2 instead of by a power of 2.

Review-URL: https://codereview.appspot.com/318340043
  • Loading branch information
egrimley-arm committed Jan 27, 2017
1 parent 3bfb964 commit 9973461
Show file tree
Hide file tree
Showing 2 changed files with 29 additions and 6 deletions.
4 changes: 3 additions & 1 deletion api/samples/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -212,7 +212,9 @@ if (X86) # FIXME i#1551, i#1569: port to ARM and AArch64
add_sample_client(bbcount "bbcount.c" "drmgr;drreg")
add_sample_client(cbr "cbr.c" "drmgr")
add_sample_client(countcalls "countcalls.c" "drmgr;drreg")
add_sample_client(div "div.c" "drmgr")
endif (X86)
add_sample_client(div "div.c" "drmgr")
if (X86) # FIXME i#1551, i#1569: port to ARM and AArch64
add_sample_client(inc2add "inc2add.c" "")
add_sample_client(memtrace_x86_binary "memtrace_x86.c;utils.c"
"drcontainers;drmgr;drreg;drutil;drx")
Expand Down
31 changes: 26 additions & 5 deletions api/samples/div.c
Original file line number Diff line number Diff line change
Expand Up @@ -97,23 +97,44 @@ callback(app_pc addr, uint divisor)

div_count++;

/* check for power of 2 */
if ((divisor & (divisor - 1)) != 0)
/* check for power of 2 or zero */
if ((divisor & (divisor - 1)) == 0)
div_p2_count++;

dr_mutex_unlock(count_mutex);
}

/* If instr is unsigned division, return true and set *opnd to divisor. */
static bool
instr_is_div(instr_t *instr, OUT opnd_t *opnd)
{
int opc = instr_get_opcode(instr);
#if defined(X86)
if (opc == OP_div) {
*opnd = instr_get_src(instr, 0); /* divisor is 1st src */
return true;
}
#elif defined(AARCHXX)
if (opc == OP_udiv) {
*opnd = instr_get_src(instr, 1); /* divisor is 2nd src */
return true;
}
#else
# error NYI
#endif
return false;
}

static dr_emit_flags_t
event_app_instruction(void* drcontext, void *tag, instrlist_t *bb, instr_t *instr,
bool for_trace, bool translating, void *user_data)
{
/* if find div, insert a clean call to our instrumentation routine */
if (instr_get_opcode(instr) == OP_div) {
opnd_t opnd;
if (instr_is_div(instr, &opnd)) {
dr_insert_clean_call(drcontext, bb, instr, (void *)callback,
false /*no fp save*/, 2,
OPND_CREATE_INTPTR(instr_get_app_pc(instr)),
instr_get_src(instr, 0) /*divisor is 1st src*/);
OPND_CREATE_INTPTR(instr_get_app_pc(instr)), opnd);
}
return DR_EMIT_DEFAULT;
}
Expand Down

0 comments on commit 9973461

Please sign in to comment.