Skip to content
Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
42 changes: 23 additions & 19 deletions src/CodeTracking.jl
Original file line number Diff line number Diff line change
Expand Up @@ -245,36 +245,40 @@ function definition(::Type{String}, method::Method)
# Step forward to the definition of this method, keeping track of positions of newlines
# Issue: in-code `'\n'`. To fix, presumably we'd have to parse the entire file.
eol = isequal('\n')
linestarts = Int[]
slop = 20
linestarts = zeros(Int, slop)
istart = 1
for _ = 1:line-1
push!(linestarts, istart)
lineindex = 1
for i in 1:line-1
if i > line - slop
linestarts[lineindex] = istart
lineindex += 1
end
istart = findnext(eol, src, istart) + 1
end
push!(linestarts, length(src) + 1)
# Parse the function definition (hoping that we've found the right location to start)
ex, iend = Meta.parse(src, istart; raise=false)
linestarts[lineindex] = istart
# The function declaration may have been on a previous line,
# allow some slop
lineindex = lastindex(linestarts)
linestop = max(0, lineindex - 20)
while !is_func_expr(ex, method) && lineindex > linestop
if isexpr(ex, :call) && length(ex.args) > 1 && first(ex.args) == :eval && isexpr(last(ex.args), :quote) && length(last(ex.args).args) > 0
actual_ex = first(last(ex.args).args)
if is_func_expr(actual_ex, method)
return clean_source(string(actual_ex)), line
end
end
while lineindex > 0
istart = linestarts[lineindex]
try
ex, iend = Meta.parse(src, istart)
# Parse the function definition (hoping that we've found the right location to start)
ex, iend = try
Meta.parse(src, istart)
catch
nothing, nothing
end

is_func_expr(ex, method) && return clean_source(src[istart:prevind(src, iend)]), line

if isexpr(ex, :call) && length(ex.args) > 1 && first(ex.args) == :eval && isexpr(last(ex.args), :quote) && length(last(ex.args).args) > 0
ex = first(last(ex.args).args)
is_func_expr(ex, method) && return clean_source(string(ex)), line
end

lineindex -= 1
line -= 1
end
lineindex <= linestop && return nothing
return clean_source(src[istart:prevind(src, iend)]), line
return nothing
end

function clean_source(src)
Expand Down