LEFT | RIGHT |
1 // Copyright 2013 The Go Authors. All rights reserved. | 1 // Copyright 2013 The Go Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style | 2 // Use of this source code is governed by a BSD-style |
3 // license that can be found in the LICENSE file. | 3 // license that can be found in the LICENSE file. |
4 | 4 |
5 package oracle | 5 package oracle |
6 | 6 |
7 import ( | 7 import ( |
8 » "encoding/json" | 8 » "go/token" |
9 "strings" | 9 "strings" |
10 | 10 |
| 11 "code.google.com/p/go.tools/oracle/json" |
11 "code.google.com/p/go.tools/pointer" | 12 "code.google.com/p/go.tools/pointer" |
12 ) | 13 ) |
13 | 14 |
14 // callgraph displays the entire callgraph of the current program. | 15 // callgraph displays the entire callgraph of the current program. |
15 // | 16 // |
16 // Nodes may be seem to appear multiple times due to (limited) | 17 // Nodes may be seem to appear multiple times due to (limited) |
17 // context sensitivity. | 18 // context sensitivity. |
18 // | 19 // |
19 // TODO(adonovan): add options for restricting the display to a region | 20 // TODO(adonovan): add options for restricting the display to a region |
20 // of interest: function, package, subgraph, dirtree, etc. | 21 // of interest: function, package, subgraph, dirtree, goroutine, etc. |
21 // | 22 // |
22 // TODO(adonovan): add an option to project away context sensitivity. | 23 // TODO(adonovan): add an option to project away context sensitivity. |
23 // The callgraph API should provide this feature. | 24 // The callgraph API should provide this feature. |
24 // | 25 // |
25 // TODO(adonovan): elide nodes for synthetic functions? | 26 // TODO(adonovan): elide nodes for synthetic functions? |
26 // | 27 // |
27 func callgraph(o *oracle) (queryResult, error) { | 28 func callgraph(o *oracle) (queryResult, error) { |
28 buildSSA(o) | 29 buildSSA(o) |
29 | 30 |
30 // Run the pointer analysis and build the complete callgraph. | 31 // Run the pointer analysis and build the complete callgraph. |
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
79 for callee := range r.callgraph[cgn] { | 80 for callee := range r.callgraph[cgn] { |
80 print(callee, indent+1) | 81 print(callee, indent+1) |
81 } | 82 } |
82 } else { | 83 } else { |
83 printf(cgn.Func(), "\t%s%s (%d)", strings.Repeat(" ",
indent), cgn.Func(), n) | 84 printf(cgn.Func(), "\t%s%s (%d)", strings.Repeat(" ",
indent), cgn.Func(), n) |
84 } | 85 } |
85 } | 86 } |
86 print(r.root, 0) | 87 print(r.root, 0) |
87 } | 88 } |
88 | 89 |
89 func (r *callgraphResult) MarshalJSON() ([]byte, error) { | 90 func (r *callgraphResult) toJSON(res *json.Result, fset *token.FileSet) { |
90 » js := make([]CallGraphJSON, len(r.numbering)) | 91 » cg := make([]json.CallGraph, len(r.numbering)) |
91 for n, i := range r.numbering { | 92 for n, i := range r.numbering { |
92 » » j := &js[i] | 93 » » j := &cg[i] |
93 fn := n.Func() | 94 fn := n.Func() |
94 j.Name = fn.String() | 95 j.Name = fn.String() |
95 j.Pos = fn.Prog.Fset.Position(fn.Pos()).String() | 96 j.Pos = fn.Prog.Fset.Position(fn.Pos()).String() |
96 for callee := range r.callgraph[n] { | 97 for callee := range r.callgraph[n] { |
97 j.Children = append(j.Children, r.numbering[callee]) | 98 j.Children = append(j.Children, r.numbering[callee]) |
98 } | 99 } |
99 } | 100 } |
100 » return json.Marshal(js) | 101 » res.Callgraph = cg |
101 } | 102 } |
LEFT | RIGHT |