seafoam 0.2
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.github/probots.yml +2 -0
- data/.github/workflows/rubocop.yml +10 -0
- data/.github/workflows/specs.yml +19 -0
- data/.gitignore +7 -0
- data/.rubocop.yml +34 -0
- data/.ruby-version +1 -0
- data/.seafoam/config +1 -0
- data/CODE_OF_CONDUCT.md +128 -0
- data/CONTRIBUTING.md +5 -0
- data/Gemfile +2 -0
- data/LICENSE.md +7 -0
- data/README.md +298 -0
- data/bin/bgv2isabelle +53 -0
- data/bin/bgv2json +42 -0
- data/bin/seafoam +24 -0
- data/docs/annotators.md +43 -0
- data/docs/bgv.md +284 -0
- data/docs/getting-graphs.md +47 -0
- data/examples/Fib.java +24 -0
- data/examples/MatMult.java +39 -0
- data/examples/fib-java.bgv +0 -0
- data/examples/fib-js.bgv +0 -0
- data/examples/fib-ruby.bgv +0 -0
- data/examples/fib.js +15 -0
- data/examples/fib.rb +15 -0
- data/examples/identity.bgv +0 -0
- data/examples/identity.rb +13 -0
- data/examples/java/Irreducible.j +35 -0
- data/examples/java/IrreducibleDecompiled.java +21 -0
- data/examples/java/JavaExamples.java +418 -0
- data/examples/java/exampleArithOperator.bgv +0 -0
- data/examples/java/exampleArithOperator.cfg +925 -0
- data/examples/java/exampleArrayAllocation.bgv +0 -0
- data/examples/java/exampleArrayAllocation.cfg +5268 -0
- data/examples/java/exampleArrayRead.bgv +0 -0
- data/examples/java/exampleArrayRead.cfg +2263 -0
- data/examples/java/exampleArrayWrite.bgv +0 -0
- data/examples/java/exampleArrayWrite.cfg +2315 -0
- data/examples/java/exampleCatch.bgv +0 -0
- data/examples/java/exampleCatch.cfg +4150 -0
- data/examples/java/exampleCompareOperator.bgv +0 -0
- data/examples/java/exampleCompareOperator.cfg +1109 -0
- data/examples/java/exampleDoubleSynchronized.bgv +0 -0
- data/examples/java/exampleDoubleSynchronized.cfg +26497 -0
- data/examples/java/exampleExactArith.bgv +0 -0
- data/examples/java/exampleExactArith.cfg +1888 -0
- data/examples/java/exampleFieldRead.bgv +0 -0
- data/examples/java/exampleFieldRead.cfg +1228 -0
- data/examples/java/exampleFieldWrite.bgv +0 -0
- data/examples/java/exampleFieldWrite.cfg +1102 -0
- data/examples/java/exampleFor.bgv +0 -0
- data/examples/java/exampleFor.cfg +3936 -0
- data/examples/java/exampleFullEscape.bgv +0 -0
- data/examples/java/exampleFullEscape.cfg +5893 -0
- data/examples/java/exampleIf.bgv +0 -0
- data/examples/java/exampleIf.cfg +2462 -0
- data/examples/java/exampleIfNeverTaken.bgv +0 -0
- data/examples/java/exampleIfNeverTaken.cfg +2476 -0
- data/examples/java/exampleInstanceOfManyImpls.bgv +0 -0
- data/examples/java/exampleInstanceOfManyImpls.cfg +6391 -0
- data/examples/java/exampleInstanceOfOneImpl.bgv +0 -0
- data/examples/java/exampleInstanceOfOneImpl.cfg +2604 -0
- data/examples/java/exampleIntSwitch.bgv +0 -0
- data/examples/java/exampleIntSwitch.cfg +3121 -0
- data/examples/java/exampleInterfaceCallManyImpls.bgv +0 -0
- data/examples/java/exampleInterfaceCallManyImpls.cfg +1358 -0
- data/examples/java/exampleInterfaceCallOneImpl.bgv +0 -0
- data/examples/java/exampleInterfaceCallOneImpl.cfg +3859 -0
- data/examples/java/exampleLocalInstanceOf.bgv +0 -0
- data/examples/java/exampleLocalInstanceOf.cfg +5276 -0
- data/examples/java/exampleLocalSynchronized.bgv +0 -0
- data/examples/java/exampleLocalSynchronized.cfg +1364 -0
- data/examples/java/exampleLocalVariables.bgv +0 -0
- data/examples/java/exampleLocalVariables.cfg +1195 -0
- data/examples/java/exampleLocalVariablesState.bgv +0 -0
- data/examples/java/exampleLocalVariablesState.cfg +1673 -0
- data/examples/java/exampleNestedWhile.bgv +0 -0
- data/examples/java/exampleNestedWhile.cfg +15499 -0
- data/examples/java/exampleNestedWhileBreak.bgv +0 -0
- data/examples/java/exampleNestedWhileBreak.cfg +11162 -0
- data/examples/java/exampleNoEscape.bgv +0 -0
- data/examples/java/exampleNoEscape.cfg +974 -0
- data/examples/java/exampleObjectAllocation.bgv +0 -0
- data/examples/java/exampleObjectAllocation.cfg +5287 -0
- data/examples/java/examplePartialEscape.bgv +0 -0
- data/examples/java/examplePartialEscape.cfg +7042 -0
- data/examples/java/examplePhi.bgv +0 -0
- data/examples/java/examplePhi.cfg +3227 -0
- data/examples/java/exampleReducible.bgv +0 -0
- data/examples/java/exampleReducible.cfg +5578 -0
- data/examples/java/exampleSimpleCall.bgv +0 -0
- data/examples/java/exampleSimpleCall.cfg +1435 -0
- data/examples/java/exampleStamp.bgv +0 -0
- data/examples/java/exampleStamp.cfg +913 -0
- data/examples/java/exampleStaticCall.bgv +0 -0
- data/examples/java/exampleStaticCall.cfg +1154 -0
- data/examples/java/exampleStringSwitch.bgv +0 -0
- data/examples/java/exampleStringSwitch.cfg +15377 -0
- data/examples/java/exampleSynchronized.bgv +0 -0
- data/examples/java/exampleSynchronized.cfg +26027 -0
- data/examples/java/exampleThrow.bgv +0 -0
- data/examples/java/exampleThrow.cfg +780 -0
- data/examples/java/exampleThrowCatch.bgv +0 -0
- data/examples/java/exampleThrowCatch.cfg +744 -0
- data/examples/java/exampleUnsafeRead.bgv +0 -0
- data/examples/java/exampleUnsafeRead.cfg +912 -0
- data/examples/java/exampleUnsafeWrite.bgv +0 -0
- data/examples/java/exampleUnsafeWrite.cfg +962 -0
- data/examples/java/exampleWhile.bgv +0 -0
- data/examples/java/exampleWhile.cfg +3936 -0
- data/examples/java/exampleWhileBreak.bgv +0 -0
- data/examples/java/exampleWhileBreak.cfg +5963 -0
- data/examples/matmult-java.bgv +0 -0
- data/examples/matmult-ruby.bgv +0 -0
- data/examples/matmult.rb +29 -0
- data/examples/overflow.bgv +0 -0
- data/examples/overflow.rb +13 -0
- data/lib/seafoam.rb +13 -0
- data/lib/seafoam/annotators.rb +54 -0
- data/lib/seafoam/annotators/fallback.rb +27 -0
- data/lib/seafoam/annotators/graal.rb +376 -0
- data/lib/seafoam/bgv/bgv_parser.rb +602 -0
- data/lib/seafoam/binary/binary_reader.rb +21 -0
- data/lib/seafoam/binary/io_binary_reader.rb +88 -0
- data/lib/seafoam/colors.rb +18 -0
- data/lib/seafoam/commands.rb +447 -0
- data/lib/seafoam/config.rb +34 -0
- data/lib/seafoam/graph.rb +91 -0
- data/lib/seafoam/graphviz_writer.rb +213 -0
- data/lib/seafoam/spotlight.rb +28 -0
- data/lib/seafoam/version.rb +5 -0
- data/seafoam.gemspec +20 -0
- data/spec/seafoam/annotators/fallback_spec.rb +69 -0
- data/spec/seafoam/annotators/graal_spec.rb +96 -0
- data/spec/seafoam/annotators_spec.rb +61 -0
- data/spec/seafoam/bgv/bgv_parser_spec.rb +144 -0
- data/spec/seafoam/bgv/fixtures/not.bgv +1 -0
- data/spec/seafoam/bgv/fixtures/unsupported.bgv +1 -0
- data/spec/seafoam/binary/io_binary_reader_spec.rb +176 -0
- data/spec/seafoam/command_spec.rb +252 -0
- data/spec/seafoam/graph_spec.rb +172 -0
- data/spec/seafoam/graphviz_writer_spec.rb +63 -0
- data/spec/seafoam/spec_helpers.rb +30 -0
- data/spec/seafoam/spotlight_spec.rb +38 -0
- data/tools/render-all +36 -0
- metadata +238 -0
data/bin/bgv2isabelle
ADDED
@@ -0,0 +1,53 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
require 'seafoam'
|
4
|
+
|
5
|
+
# definition eg_short_cut_or1 :: IRGraph where
|
6
|
+
# "eg_short_cut_or1 =
|
7
|
+
# (add_node 14 ReturnNode [13] []
|
8
|
+
# (add_node 13 PhiNode [10, 11, 12] []
|
9
|
+
# (add_node 12 (ConstantNode 0) [] []
|
10
|
+
# (add_node 11 (ConstantNode 42) [] []
|
11
|
+
# (add_node 10 MergeNode [7, 9] [14]
|
12
|
+
# (add_node 9 EndNode [] []
|
13
|
+
# (add_node 8 BeginNode [] [9]
|
14
|
+
# (add_node 7 EndNode [] []
|
15
|
+
# (add_node 6 BeginNode [] [7]
|
16
|
+
# (add_node 5 IfNode [3] [6, 8]
|
17
|
+
# (add_node 3 (ShortCircuitOrNode False False) [1, 2] []
|
18
|
+
# (add_node 2 (ParameterNode 1) [] []
|
19
|
+
# (add_node 1 (ParameterNode 0) [] []
|
20
|
+
# (add_node 0 StartNode [] [5]
|
21
|
+
# empty_graph))))))))))))))"
|
22
|
+
|
23
|
+
ARGV.each do |file|
|
24
|
+
parser = Seafoam::BGV::BGVParser.new(File.new(file))
|
25
|
+
parser.read_file_header
|
26
|
+
parser.skip_document_props
|
27
|
+
|
28
|
+
loop do
|
29
|
+
index, = parser.read_graph_preheader
|
30
|
+
break unless index
|
31
|
+
|
32
|
+
graph_header = parser.read_graph_header
|
33
|
+
graph = parser.read_graph
|
34
|
+
|
35
|
+
puts "graph#{index} = # #{parser.graph_name(graph_header)}"
|
36
|
+
|
37
|
+
graph.nodes.each_value do |node|
|
38
|
+
node_class = node.props[:node_class][:node_class]
|
39
|
+
case node_class
|
40
|
+
when 'org.graalvm.compiler.nodes.ConstantNode'
|
41
|
+
desc = "(ConstantNode #{node.props['rawvalue']})"
|
42
|
+
when 'org.graalvm.compiler.nodes.ParameterNode'
|
43
|
+
desc = "(ParameterNode #{node.props['index']})"
|
44
|
+
else
|
45
|
+
desc = node_class.split('.').last
|
46
|
+
end
|
47
|
+
inputs = node.inputs.map(&:from).map(&:id)
|
48
|
+
outputs = node.outputs.map(&:to).map(&:id)
|
49
|
+
puts " (add_node #{node.id} #{desc} #{inputs.inspect} #{outputs.inspect}"
|
50
|
+
end
|
51
|
+
puts ' empty_graph' + (')' * graph.nodes.size)
|
52
|
+
end
|
53
|
+
end
|
data/bin/bgv2json
ADDED
@@ -0,0 +1,42 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
require 'seafoam'
|
4
|
+
require 'json'
|
5
|
+
|
6
|
+
ARGV.each do |file|
|
7
|
+
parser = Seafoam::BGV::BGVParser.new(File.new(file))
|
8
|
+
parser.read_file_header
|
9
|
+
parser.skip_document_props
|
10
|
+
|
11
|
+
loop do
|
12
|
+
index, = parser.read_graph_preheader
|
13
|
+
break unless index
|
14
|
+
|
15
|
+
graph_header = parser.read_graph_header
|
16
|
+
|
17
|
+
graph = parser.read_graph
|
18
|
+
Seafoam::Annotators.apply graph
|
19
|
+
|
20
|
+
name = parser.graph_name(graph_header)
|
21
|
+
|
22
|
+
nodes = []
|
23
|
+
edges = []
|
24
|
+
|
25
|
+
graph.nodes.each_value do |node|
|
26
|
+
nodes.push({
|
27
|
+
id: node.id,
|
28
|
+
props: node.props
|
29
|
+
})
|
30
|
+
|
31
|
+
node.outputs.each do |edge|
|
32
|
+
edges.push({
|
33
|
+
from: edge.from.id,
|
34
|
+
to: edge.to.id,
|
35
|
+
props: edge.props
|
36
|
+
})
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
puts JSON.generate({name: name, props: graph.props, nodes: nodes, edges: edges})
|
41
|
+
end
|
42
|
+
end
|
data/bin/seafoam
ADDED
@@ -0,0 +1,24 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
require 'seafoam'
|
4
|
+
|
5
|
+
# This is the 'seafoam' command line entry point.
|
6
|
+
|
7
|
+
begin
|
8
|
+
# Load configuraiton.
|
9
|
+
config = Seafoam::Config.new
|
10
|
+
config.load_config
|
11
|
+
|
12
|
+
# Run the command line.
|
13
|
+
commands = Seafoam::Commands.new($stdout, config)
|
14
|
+
commands.run(*ARGV)
|
15
|
+
rescue StandardError => e
|
16
|
+
if $DEBUG
|
17
|
+
# Re-raise the exception so the user sees it, it debugging is
|
18
|
+
# enabled (ruby -d).
|
19
|
+
raise e
|
20
|
+
else
|
21
|
+
# Otherwise, just print the message.
|
22
|
+
warn "seafoam: #{e.message}"
|
23
|
+
end
|
24
|
+
end
|
data/docs/annotators.md
ADDED
@@ -0,0 +1,43 @@
|
|
1
|
+
# Annotators
|
2
|
+
|
3
|
+
The model of Seafoam is that it is a directed graph, with nodes annotated with a
|
4
|
+
bag of key-value properties. When graphs are read they'll have some initial
|
5
|
+
properties. Seafoam may add more properties. The output routines then draw the
|
6
|
+
graph using the graph structure itself and also the properties.
|
7
|
+
|
8
|
+
*Annotators* are routines that add extra properties to graphs to help the user
|
9
|
+
understand them. They usually have knowledge of how the graph is structured, and
|
10
|
+
use this to make the graph easier to read or to make important information in
|
11
|
+
them stand out.
|
12
|
+
|
13
|
+
We call properties with symbol keys *annotations*, as they're added by the
|
14
|
+
annotators.
|
15
|
+
|
16
|
+
Annotators are similar to filters in IGV.
|
17
|
+
|
18
|
+
Appropriate annotators are automatically selected and applied to graphs.
|
19
|
+
|
20
|
+
The rendering commands recognize these annotations, so annotators will probably
|
21
|
+
want to add them:
|
22
|
+
|
23
|
+
* `:label` on nodes and edges
|
24
|
+
* `:out_annotation` on nodes
|
25
|
+
* `:hidden` on nodes only, to not show them (*remove frame state* for example in IGV terminology)
|
26
|
+
* `:inlined` on nodes only, to indicate the node should be shown immediately above each node using it (*reduce edges* in IGV terminology)
|
27
|
+
* `:kind` on nodes only, which can be `info`, `input`, `control`, `effect`, `virtual`, `calc`, `guard`, or `other`
|
28
|
+
* `:kind` on edges only, which can be `info`, `control`, `loop`, or `data`
|
29
|
+
* `:reverse` on edges only
|
30
|
+
* `:spotlight` for nodes as part of spotlighting (`lit` are shown, `shaded` are shown but greyed out, and edges from `shaded` to `:hidden` nodes are also shown greyed out)
|
31
|
+
|
32
|
+
Seafoam ships with an annotator for generic GraalVM graphs. If you work with a
|
33
|
+
different compiler you'll probably want to write your own annotators - subclass
|
34
|
+
`Seafoam::Annotator` and implement `#annotate(graph)`. You can add custom
|
35
|
+
annotators by requiring them in your `.seafoam/config`. All subclasses of
|
36
|
+
`Annotator` will be found, so you just need to define the subclass.
|
37
|
+
|
38
|
+
A fallback annotator, run after all others, just labels the node with the
|
39
|
+
`'label'` property if there is one.
|
40
|
+
|
41
|
+
Options for annotations can be set on the command line with `--option key
|
42
|
+
value`. Some options are built into Seafoam commands, like `--show-frame-state`,
|
43
|
+
but they're doing the same thing as `--option hide_frame_state false`.
|
data/docs/bgv.md
ADDED
@@ -0,0 +1,284 @@
|
|
1
|
+
# BGV File Format
|
2
|
+
|
3
|
+
The BGV (*binary graph*, sometimes also called *BIGV*) file format is dumped by
|
4
|
+
Graal graphs.
|
5
|
+
|
6
|
+
The BGV parser was implemented from the [open-source writer code][graph-protocol]
|
7
|
+
in the GraalVM compiler.
|
8
|
+
|
9
|
+
[graph-protocol]: https://github.com/oracle/graal/blob/master/compiler/src/org.graalvm.graphio/src/org/graalvm/graphio/GraphProtocol.java
|
10
|
+
|
11
|
+
## Format
|
12
|
+
|
13
|
+
Seafoam supports BGV versions:
|
14
|
+
|
15
|
+
* 7.0 (GraalVM 20.1.0 and up)
|
16
|
+
* 6.1 (GraalVM 1.0.0-rc16 and up)
|
17
|
+
|
18
|
+
The BGV file format is network-endian.
|
19
|
+
|
20
|
+
```c
|
21
|
+
BGV {
|
22
|
+
char[4] = 'BIGV'
|
23
|
+
sint8 major
|
24
|
+
sint8 minor
|
25
|
+
GroupOrGraph*
|
26
|
+
}
|
27
|
+
|
28
|
+
GroupOrGraph {
|
29
|
+
BeginGroup GroupOrGraph* CloseGroup | Graph
|
30
|
+
}
|
31
|
+
|
32
|
+
BeginGroup {
|
33
|
+
sint8 token = BEGIN_GROUP
|
34
|
+
PoolObject name
|
35
|
+
PoolObject method
|
36
|
+
sint32 bci
|
37
|
+
Props props
|
38
|
+
}
|
39
|
+
|
40
|
+
Graph {
|
41
|
+
sint8 token = BEGIN_GRAPH
|
42
|
+
String format
|
43
|
+
Args args
|
44
|
+
GraphBody body
|
45
|
+
}
|
46
|
+
|
47
|
+
GraphBody {
|
48
|
+
Props props
|
49
|
+
sint32 nodes_count
|
50
|
+
Node[nodes_count] nodes
|
51
|
+
Blocks blocks
|
52
|
+
}
|
53
|
+
|
54
|
+
Node {
|
55
|
+
sint32 id
|
56
|
+
PoolObject node_class
|
57
|
+
bool has_predecessor
|
58
|
+
Pops props
|
59
|
+
Edge[node_class.inputs.size] edges_in
|
60
|
+
Edge[node_class.outputs.size] edges_out
|
61
|
+
}
|
62
|
+
|
63
|
+
Edge {
|
64
|
+
sint32[inputs_count] nodes
|
65
|
+
}
|
66
|
+
|
67
|
+
Blocks {
|
68
|
+
sint32 id
|
69
|
+
sint32 nodes_count
|
70
|
+
sint32[nodes_count] nodes
|
71
|
+
sint32 followers_count
|
72
|
+
sint32[followers_count] followers
|
73
|
+
}
|
74
|
+
|
75
|
+
CloseGroup {
|
76
|
+
sint8 token = CLOSE_GROUP
|
77
|
+
}
|
78
|
+
|
79
|
+
Props {
|
80
|
+
sint16 props_count
|
81
|
+
Prop[props_count] props
|
82
|
+
}
|
83
|
+
|
84
|
+
Prop {
|
85
|
+
PoolObject key
|
86
|
+
PropObject value
|
87
|
+
}
|
88
|
+
|
89
|
+
PropObject {
|
90
|
+
union {
|
91
|
+
struct {
|
92
|
+
sint8 PROPERTY_POOL
|
93
|
+
PoolObject object
|
94
|
+
}
|
95
|
+
struct {
|
96
|
+
sint8 PROPERTY_INT
|
97
|
+
sint32 value
|
98
|
+
}
|
99
|
+
struct {
|
100
|
+
sint8 PROPERTY_LONG
|
101
|
+
sint64 value
|
102
|
+
}
|
103
|
+
struct {
|
104
|
+
sint8 PROPERTY_DOUBLE
|
105
|
+
float64 value
|
106
|
+
}
|
107
|
+
struct {
|
108
|
+
sint8 PROPERTY_FLOAT
|
109
|
+
float32 value
|
110
|
+
}
|
111
|
+
struct {
|
112
|
+
sint8 PROPERTY_TRUE
|
113
|
+
}
|
114
|
+
struct {
|
115
|
+
sint8 PROPERTY_FALSE
|
116
|
+
}
|
117
|
+
struct {
|
118
|
+
sint8 PROPERTY_ARRAY
|
119
|
+
union {
|
120
|
+
struct {
|
121
|
+
sint8 PROPERTY_POOL
|
122
|
+
sint32 times
|
123
|
+
PoolObject[times] values
|
124
|
+
}
|
125
|
+
}
|
126
|
+
}
|
127
|
+
struct {
|
128
|
+
sint8 PROPERTY_SUBGRAPH
|
129
|
+
GraphBody graph
|
130
|
+
}
|
131
|
+
}
|
132
|
+
}
|
133
|
+
|
134
|
+
PoolObject {
|
135
|
+
union {
|
136
|
+
POOL_NULL
|
137
|
+
struct {
|
138
|
+
sint8 token = POOL_NEW
|
139
|
+
uint16 id
|
140
|
+
union {
|
141
|
+
struct {
|
142
|
+
sint8 type = POOL_STRING
|
143
|
+
String string
|
144
|
+
}
|
145
|
+
struct {
|
146
|
+
sint8 type = POOL_ENUM
|
147
|
+
PoolObject enum_class
|
148
|
+
sint32 enum_ordinal
|
149
|
+
}
|
150
|
+
struct {
|
151
|
+
sint8 type = POOL_CLASS
|
152
|
+
String type_name
|
153
|
+
union {
|
154
|
+
struct {
|
155
|
+
sint8 type = ENUM_KLASS
|
156
|
+
sint32 values_count
|
157
|
+
PoolObject values[values_count]
|
158
|
+
}
|
159
|
+
struct {
|
160
|
+
sint8 type = KLASS
|
161
|
+
}
|
162
|
+
}
|
163
|
+
}
|
164
|
+
struct {
|
165
|
+
sint8 type = POOL_METHOD
|
166
|
+
PoolObject declaring_class
|
167
|
+
PoolObject method_name
|
168
|
+
PoolObject signature
|
169
|
+
sint32 modifiers
|
170
|
+
sint32 bytes_length
|
171
|
+
uint8[bytes_length] bytes
|
172
|
+
}
|
173
|
+
struct {
|
174
|
+
sint8 type = POOL_NODE_CLASS
|
175
|
+
PoolObject node_class
|
176
|
+
String name_template
|
177
|
+
sint16 input_count
|
178
|
+
InputEdgeInfo inputs[input_count]
|
179
|
+
sint16 output_count
|
180
|
+
OutputEdgeInfo outputs[output_count]
|
181
|
+
}
|
182
|
+
struct {
|
183
|
+
sint8 type = POOL_FIELD
|
184
|
+
PoolObject field_class
|
185
|
+
PoolObject name
|
186
|
+
PoolObject type_name
|
187
|
+
sint32 modifiers
|
188
|
+
}
|
189
|
+
struct {
|
190
|
+
sint8 type = POOL_NODE_SIGNATURE
|
191
|
+
sint16 args_count
|
192
|
+
PoolObject args[args_count]
|
193
|
+
}
|
194
|
+
struct {
|
195
|
+
sint8 type = POOL_NODE_SOURCE_POSITION
|
196
|
+
PoolObject method
|
197
|
+
sint32 bci
|
198
|
+
SourcePosition source_positions[...until SourcePosition.uri = null]
|
199
|
+
PoolObject caller
|
200
|
+
}
|
201
|
+
struct {
|
202
|
+
sint8 type = POOL_NODE
|
203
|
+
sint32 node_id
|
204
|
+
PoolObject node_class
|
205
|
+
}
|
206
|
+
}
|
207
|
+
}
|
208
|
+
struct {
|
209
|
+
sint8 token = POOL_STRING | POOL_ENUM | POOL_CLASS | POOL_METHOD | POOL_NODE_CLASS | POOL_FIELD | POOL_SIGNATURE | POOL_NODE_SOURCE_POSITION | POOL_NODE
|
210
|
+
uint16 pool_id
|
211
|
+
}
|
212
|
+
}
|
213
|
+
}
|
214
|
+
|
215
|
+
InputEdgeInfo {
|
216
|
+
sint8 indirect
|
217
|
+
PoolObject name
|
218
|
+
PoolObject type
|
219
|
+
}
|
220
|
+
|
221
|
+
OutputEdgeInfo {
|
222
|
+
sint8 indirect
|
223
|
+
PoolObject name
|
224
|
+
}
|
225
|
+
|
226
|
+
SourcePosition {
|
227
|
+
PoolObject uri
|
228
|
+
String location
|
229
|
+
sint32 line
|
230
|
+
sint32 start
|
231
|
+
sint32 end
|
232
|
+
}
|
233
|
+
|
234
|
+
String {
|
235
|
+
sint32 length
|
236
|
+
char[length] chars
|
237
|
+
}
|
238
|
+
|
239
|
+
BEGIN_GROUP = 0x00
|
240
|
+
BEGIN_GRAPH = 0x01
|
241
|
+
CLOSE_GROUP = 0x02
|
242
|
+
BEGIN_DOCUMENT = 0x03
|
243
|
+
|
244
|
+
POOL_NEW = 0x00
|
245
|
+
POOL_STRING = 0x01
|
246
|
+
POOL_ENUM = 0x02
|
247
|
+
POOL_CLASS = 0x03
|
248
|
+
POOL_METHOD = 0x04
|
249
|
+
POOL_NULL = 0x05
|
250
|
+
POOL_NODE_CLASS = 0x06
|
251
|
+
POOL_FIELD = 0x07
|
252
|
+
POOL_SIGNATURE = 0x08
|
253
|
+
POOL_NODE_SOURCE_POSITION = 0x09
|
254
|
+
POOL_NODE = 0x0a
|
255
|
+
|
256
|
+
PROPERTY_POOL = 0x00
|
257
|
+
PROPERTY_INT = 0x01
|
258
|
+
PROPERTY_LONG = 0x02
|
259
|
+
PROPERTY_DOUBLE = 0x03
|
260
|
+
PROPERTY_FLOAT = 0x04
|
261
|
+
PROPERTY_TRUE = 0x05
|
262
|
+
PROPERTY_FALSE = 0x06
|
263
|
+
PROPERTY_ARRAY = 0x07
|
264
|
+
PROPERTY_SUBGRAPH = 0x08
|
265
|
+
|
266
|
+
KLASS = 0x00
|
267
|
+
ENUM_KLASS = 0x01
|
268
|
+
```
|
269
|
+
|
270
|
+
## Seeking
|
271
|
+
|
272
|
+
The BGV format is not particularly amenable to seeking. You must read each prior
|
273
|
+
graph in order to read any subsequent graph, the length of nodes and edges
|
274
|
+
depends on values within them, and there is an object pool that is incrementally
|
275
|
+
built.
|
276
|
+
|
277
|
+
In order to 'seek' BGV files we have two code paths for reading the file, one
|
278
|
+
with loads the data and one which loads as little as possible to know just how
|
279
|
+
much further to advance in the file.
|
280
|
+
|
281
|
+
## Other information
|
282
|
+
|
283
|
+
`seafoam file.bgv debug` checks that a file can be parsed and prints information
|
284
|
+
as it does so.
|