Merge pull request #4559 from haiodo/enable-profiler-filenames
Enable embedded profiler to display filenames.
This commit is contained in:
commit
b36849be3f
2 changed files with 23 additions and 12 deletions
|
|
@ -27,8 +27,11 @@ const
|
||||||
tickCountCorrection = 50_000
|
tickCountCorrection = 50_000
|
||||||
|
|
||||||
when not declared(system.StackTrace):
|
when not declared(system.StackTrace):
|
||||||
type StackTrace = array[0..20, cstring]
|
type StackTrace = object
|
||||||
|
lines: array[0..20, cstring]
|
||||||
|
files: array[0..20, cstring]
|
||||||
{.deprecated: [TStackTrace: StackTrace].}
|
{.deprecated: [TStackTrace: StackTrace].}
|
||||||
|
proc `[]`*(st: StackTrace, i: int): cstring = st.lines[i]
|
||||||
|
|
||||||
# We use a simple hash table of bounded size to keep track of the stack traces:
|
# We use a simple hash table of bounded size to keep track of the stack traces:
|
||||||
type
|
type
|
||||||
|
|
@ -39,7 +42,7 @@ type
|
||||||
{.deprecated: [TProfileEntry: ProfileEntry, TProfileData: ProfileData].}
|
{.deprecated: [TProfileEntry: ProfileEntry, TProfileData: ProfileData].}
|
||||||
|
|
||||||
proc `==`(a, b: StackTrace): bool =
|
proc `==`(a, b: StackTrace): bool =
|
||||||
for i in 0 .. high(a):
|
for i in 0 .. high(a.lines):
|
||||||
if a[i] != b[i]: return false
|
if a[i] != b[i]: return false
|
||||||
result = true
|
result = true
|
||||||
|
|
||||||
|
|
@ -72,7 +75,7 @@ proc hookAux(st: StackTrace, costs: int) =
|
||||||
# this is quite performance sensitive!
|
# this is quite performance sensitive!
|
||||||
when withThreads: acquire profilingLock
|
when withThreads: acquire profilingLock
|
||||||
inc totalCalls
|
inc totalCalls
|
||||||
var last = high(st)
|
var last = high(st.lines)
|
||||||
while last > 0 and isNil(st[last]): dec last
|
while last > 0 and isNil(st[last]): dec last
|
||||||
var h = hash(pointer(st[last])) and high(profileData)
|
var h = hash(pointer(st[last])) and high(profileData)
|
||||||
|
|
||||||
|
|
@ -178,7 +181,7 @@ proc writeProfile() {.noconv.} =
|
||||||
var perProc = initCountTable[string]()
|
var perProc = initCountTable[string]()
|
||||||
for i in 0..entries-1:
|
for i in 0..entries-1:
|
||||||
var dups = initSet[string]()
|
var dups = initSet[string]()
|
||||||
for ii in 0..high(StackTrace):
|
for ii in 0..high(StackTrace.lines):
|
||||||
let procname = profileData[i].st[ii]
|
let procname = profileData[i].st[ii]
|
||||||
if isNil(procname): break
|
if isNil(procname): break
|
||||||
let p = $procname
|
let p = $procname
|
||||||
|
|
@ -193,10 +196,11 @@ proc writeProfile() {.noconv.} =
|
||||||
writeLine(f, "Entry: ", i+1, "/", entries, " Calls: ",
|
writeLine(f, "Entry: ", i+1, "/", entries, " Calls: ",
|
||||||
profileData[i].total // totalCalls, " [sum: ", sum, "; ",
|
profileData[i].total // totalCalls, " [sum: ", sum, "; ",
|
||||||
sum // totalCalls, "]")
|
sum // totalCalls, "]")
|
||||||
for ii in 0..high(StackTrace):
|
for ii in 0..high(StackTrace.lines):
|
||||||
let procname = profileData[i].st[ii]
|
let procname = profileData[i].st[ii]
|
||||||
|
let filename = profileData[i].st.files[ii]
|
||||||
if isNil(procname): break
|
if isNil(procname): break
|
||||||
writeLine(f, " ", procname, " ", perProc[$procname] // totalCalls)
|
writeLine(f, " ", $filename & ": " & $procname, " ", perProc[$procname] // totalCalls)
|
||||||
close(f)
|
close(f)
|
||||||
echo "... done"
|
echo "... done"
|
||||||
else:
|
else:
|
||||||
|
|
|
||||||
|
|
@ -19,10 +19,14 @@ const
|
||||||
MaxTraceLen = 20 # tracking the last 20 calls is enough
|
MaxTraceLen = 20 # tracking the last 20 calls is enough
|
||||||
|
|
||||||
type
|
type
|
||||||
StackTrace* = array[0..MaxTraceLen-1, cstring]
|
StackTrace* = object
|
||||||
|
lines*: array[0..MaxTraceLen-1, cstring]
|
||||||
|
files*: array[0..MaxTraceLen-1, cstring]
|
||||||
ProfilerHook* = proc (st: StackTrace) {.nimcall.}
|
ProfilerHook* = proc (st: StackTrace) {.nimcall.}
|
||||||
{.deprecated: [TStackTrace: StackTrace, TProfilerHook: ProfilerHook].}
|
{.deprecated: [TStackTrace: StackTrace, TProfilerHook: ProfilerHook].}
|
||||||
|
|
||||||
|
proc `[]`*(st: StackTrace, i: int): cstring = st.lines[i]
|
||||||
|
|
||||||
proc captureStackTrace(f: PFrame, st: var StackTrace) =
|
proc captureStackTrace(f: PFrame, st: var StackTrace) =
|
||||||
const
|
const
|
||||||
firstCalls = 5
|
firstCalls = 5
|
||||||
|
|
@ -30,9 +34,10 @@ proc captureStackTrace(f: PFrame, st: var StackTrace) =
|
||||||
it = f
|
it = f
|
||||||
i = 0
|
i = 0
|
||||||
total = 0
|
total = 0
|
||||||
while it != nil and i <= high(st)-(firstCalls-1):
|
while it != nil and i <= high(st.lines)-(firstCalls-1):
|
||||||
# the (-1) is for the "..." entry
|
# the (-1) is for the "..." entry
|
||||||
st[i] = it.procname
|
st.lines[i] = it.procname
|
||||||
|
st.files[i] = it.filename
|
||||||
inc(i)
|
inc(i)
|
||||||
inc(total)
|
inc(total)
|
||||||
it = it.prev
|
it = it.prev
|
||||||
|
|
@ -43,10 +48,12 @@ proc captureStackTrace(f: PFrame, st: var StackTrace) =
|
||||||
for j in 1..total-i-(firstCalls-1):
|
for j in 1..total-i-(firstCalls-1):
|
||||||
if b != nil: b = b.prev
|
if b != nil: b = b.prev
|
||||||
if total != i:
|
if total != i:
|
||||||
st[i] = "..."
|
st.lines[i] = "..."
|
||||||
|
st.files[i] = "..."
|
||||||
inc(i)
|
inc(i)
|
||||||
while b != nil and i <= high(st):
|
while b != nil and i <= high(st.lines):
|
||||||
st[i] = b.procname
|
st.lines[i] = b.procname
|
||||||
|
st.files[i] = b.filename
|
||||||
inc(i)
|
inc(i)
|
||||||
b = b.prev
|
b = b.prev
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue