forked from zzet/gortex
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathhelpers.go
More file actions
59 lines (55 loc) · 1.53 KB
/
Copy pathhelpers.go
File metadata and controls
59 lines (55 loc) · 1.53 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
package forest
import (
"github.com/zzet/gortex/internal/graph"
"github.com/zzet/gortex/internal/parser"
)
// funcRange is one definition's line span, used to attribute call
// references to their enclosing function.
type funcRange struct {
id string
startLine int
endLine int
}
// buildFuncRanges walks the already-emitted nodes and returns a
// flat slice of every function/method's span. Linear scan is fine —
// even large files emit only hundreds of definitions, and the
// per-call lookup walks this slice in O(N).
func buildFuncRanges(result *parser.ExtractionResult) []funcRange {
if result == nil {
return nil
}
var ranges []funcRange
for _, n := range result.Nodes {
if n == nil {
continue
}
// Forest defs that can host a call: anything code-bearing.
switch n.Kind {
case graph.KindFunction, graph.KindMethod:
ranges = append(ranges, funcRange{
id: n.ID, startLine: n.StartLine, endLine: n.EndLine,
})
}
}
return ranges
}
// findEnclosingFunc returns the most-tightly-enclosing function ID
// for a given 1-based line, or "" if no def covers the line. When
// definitions nest (e.g. a closure inside a function), the
// inner-most range wins because we prefer the smallest covering
// span.
func findEnclosingFunc(ranges []funcRange, line int) string {
bestID := ""
bestSpan := 0
for _, r := range ranges {
if line < r.startLine || line > r.endLine {
continue
}
span := r.endLine - r.startLine
if bestID == "" || span < bestSpan {
bestID = r.id
bestSpan = span
}
}
return bestID
}