Misusing FunctionProfiling for code coverage
thomas_braun
The idea is that it is easy to see with code coverage which parts of a function have tests associated with them and which not.
I've tried using the FunctionProfiling code a la
#include <FunctionProfiling>
Function MyTest()
variable a
if(a)
a += 1
else
a += 2
endif
End
Function run()
variable i
BeginFunctionProfiling(testTime = 1)
for(i = 0; i < 1000000; i += 1)
myTest()
endfor
FuncProfilingModule#EndFunctionProfiling(normMode = 0, maxPct = 100)
End
Function MyTest()
variable a
if(a)
a += 1
else
a += 2
endif
End
Function run()
variable i
BeginFunctionProfiling(testTime = 1)
for(i = 0; i < 1000000; i += 1)
myTest()
endfor
FuncProfilingModule#EndFunctionProfiling(normMode = 0, maxPct = 100)
End
which gives
[...]
*******************************************************************************************
Function: UTF_Main.ipf MyTest; Percent total 48%
*******************************************************************************************
[17]** |Function MyTest()
[00] |
[00] | variable a
[03]* | if(a)
[00] | a += 1
[03]* | else
[22]** | a += 2
[03]* | endif
[00] |
[01]* |End
[...]
In principle this holds the information I want (the if branch is not executed but the else part is). The main drawbacks here are that I don't know how often I have to repeat it to get reasonable results (1e6 is already ridiculously large) and that it does seem not so reliable ("variable a" is never executed).
Is there something obvious I'm missing? Or does the Igor compiler not work how I seem to expect it?
Thanks,
Thomas
[1]: http://ltp.sourceforge.net/coverage/lcov/output/example/methods/iterate…
The profiling code runs in a separate thread that only periodically samples where the main thread's "program counter" is.
If the code being profiled runs very quickly, like your code does, too few samples are taken to create meaningful statistics.
The sampling interval is computed in StartProfiling():
STRUCT MyProfilingStuff &s
Variable tmax // time in seconds the test is expected to take (needed if > 100)
Variable desiredSamps= 100000 // big enough for 100 sec at 1ms sampling rate
Variable tms= round(1000*tmax/desiredSamps) // milliseconds to sleep between samples
if( tms<1 )
tms= 1
elseif( tms>100 )
tms= 100
desiredSamps= round(tmax*1000/tms)
endif
Make/O/D/FREE/N=(desiredSamps) s.w
s.tid= ThreadGroupCreate(1)
ThreadStart s.tid, 0, DoProfiling(s.w, tms)
s.testTime= StopMSTimer(-2)
End
You can see that the minimum sampling rate is 1 millisecond. run() with the loop max set to 1000000 runs in 16.4576 microseconds.
--Jim Prouty
Software Engineer, WaveMetrics, Inc.
September 12, 2017 at 12:51 pm - Permalink