How to measure the number of assembler instructions executed?

I want to somehow get the "number of assembler instructions executed" from a binary file. Consider the following code snippet:

if(password[0] == 'p') { if(password[1] == 'a') { ...... printf("Correct Password\n"); } } 

Then, if I would run the program, for example. "abc" this will not occupy the first branch, so fewer instructions will be executed. If I type "pbc", it will occupy the first branch, so a little more (about 4-5) instructions will be executed. (This is some research for CTF (Capture the Flag) files). Therefore, my idea is not to change the binary code and try to understand the algorithm, but I use a faster approach when counting the number of assembler instructions executed for different settings (for example, different characters or password lengths, etc., to see, I can whether I take another branch using a different input, thereby creating additional assembler instructions).

My main idea would be to write a simple debugger by simply placing int3 after the current instruction, increasing the counter there, the disassembler of the next instruction and placing int3 right after this instruction (a strong simplified version of my idea).

Is there any program / library / ... that has already done this? (Because I see that some problems arise when a program deals with signals, ...)

(I already tried using high precision timers to measure time, but it was a complete failure due to a difference of only 4-5 instructions)

+6
source share
1 answer

The Linux perf tool can use hardware performance counters to give you accurate numbers for a variety of things, including instructions that have been followed.

 $ perf stat true Performance counter stats for 'true': 0.183734 task-clock # 0.314 CPUs utilized 0 context-switches # 0.000 M/sec 0 CPU-migrations # 0.000 M/sec 118 page-faults # 0.642 M/sec 627,313 cycles # 3.414 GHz 396,604 stalled-cycles-frontend # 63.22% frontend cycles idle 268,222 stalled-cycles-backend # 42.76% backend cycles idle 404,935 instructions # 0.65 insns per cycle # 0.98 stalled cycles per insn 75,949 branches # 413.364 M/sec 3,602 branch-misses # 4.74% of all branches 0.000584503 seconds time elapsed 

To get only user-mode instructions:

 $ perf stat -e instructions:u true Performance counter stats for 'true': 92,687 instructions:u # 0.00 insns per cycle 0.000520925 seconds time elapsed 

I see a slight variation in this, though, like instructions 5-6. Not sure if this is real or just an artifact of measurement. To get more reliable results, I am thinking of invoking a simulator like Valgrind. I was lucky to get stable team counts, which vary only for one team from these two teams:

 $ valgrind --tool=callgrind true $ valgrind --tool=exp-bbv true 
+5
source

Source: https://habr.com/ru/post/944016/


All Articles