erlang-etf 1.1.1 → 2.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.editorconfig +20 -0
- data/.gitignore +10 -18
- data/.ruby-gemset +1 -0
- data/.ruby-version +1 -0
- data/.travis.yml +15 -4
- data/CHANGELOG.md +7 -0
- data/Gemfile +10 -6
- data/LICENSE.txt +1 -1
- data/README.md +13 -13
- data/Rakefile +8 -6
- data/erlang-etf.gemspec +10 -10
- data/lib/erlang-etf.rb +1 -0
- data/lib/erlang/etf.rb +363 -30
- data/lib/erlang/etf/atom.rb +28 -48
- data/lib/erlang/etf/atom_utf8.rb +28 -48
- data/lib/erlang/etf/binary.rb +24 -23
- data/lib/erlang/etf/bit_binary.rb +35 -27
- data/lib/erlang/etf/compressed.rb +61 -35
- data/lib/erlang/etf/export.rb +44 -21
- data/lib/erlang/etf/float.rb +33 -29
- data/lib/erlang/etf/fun.rb +54 -32
- data/lib/erlang/etf/integer.rb +24 -12
- data/lib/erlang/etf/large_big.rb +31 -37
- data/lib/erlang/etf/large_tuple.rb +41 -30
- data/lib/erlang/etf/list.rb +55 -25
- data/lib/erlang/etf/map.rb +58 -28
- data/lib/erlang/etf/new_float.rb +25 -14
- data/lib/erlang/etf/new_fun.rb +70 -47
- data/lib/erlang/etf/new_reference.rb +51 -24
- data/lib/erlang/etf/nil.rb +21 -6
- data/lib/erlang/etf/pid.rb +48 -21
- data/lib/erlang/etf/port.rb +49 -13
- data/lib/erlang/etf/reference.rb +49 -13
- data/lib/erlang/etf/small_atom.rb +31 -27
- data/lib/erlang/etf/small_atom_utf8.rb +31 -27
- data/lib/erlang/etf/small_big.rb +30 -39
- data/lib/erlang/etf/small_integer.rb +27 -12
- data/lib/erlang/etf/small_tuple.rb +41 -30
- data/lib/erlang/etf/string.rb +23 -23
- data/lib/erlang/etf/term.rb +109 -70
- data/lib/erlang/etf/version.rb +1 -1
- metadata +33 -169
- data/.rspec +0 -2
- data/lib/erlang/etf/bert.rb +0 -74
- data/lib/erlang/etf/extensions.rb +0 -144
- data/lib/erlang/etf/extensions/array.rb +0 -27
- data/lib/erlang/etf/extensions/big_decimal.rb +0 -20
- data/lib/erlang/etf/extensions/erlang-export.rb +0 -24
- data/lib/erlang/etf/extensions/erlang-list.rb +0 -29
- data/lib/erlang/etf/extensions/erlang-map.rb +0 -26
- data/lib/erlang/etf/extensions/erlang-nil.rb +0 -20
- data/lib/erlang/etf/extensions/erlang-pid.rb +0 -20
- data/lib/erlang/etf/extensions/erlang-string.rb +0 -31
- data/lib/erlang/etf/extensions/erlang-tuple.rb +0 -29
- data/lib/erlang/etf/extensions/false_class.rb +0 -26
- data/lib/erlang/etf/extensions/float.rb +0 -18
- data/lib/erlang/etf/extensions/hash.rb +0 -30
- data/lib/erlang/etf/extensions/integer.rb +0 -46
- data/lib/erlang/etf/extensions/nil_class.rb +0 -27
- data/lib/erlang/etf/extensions/object.rb +0 -22
- data/lib/erlang/etf/extensions/regexp.rb +0 -32
- data/lib/erlang/etf/extensions/string.rb +0 -33
- data/lib/erlang/etf/extensions/symbol.rb +0 -43
- data/lib/erlang/etf/extensions/time.rb +0 -27
- data/lib/erlang/etf/extensions/true_class.rb +0 -26
- data/lib/erlang/etf/terms.rb +0 -132
- data/spec/erlang/etf/atom_spec.rb +0 -90
- data/spec/erlang/etf/atom_utf8_spec.rb +0 -90
- data/spec/erlang/etf/binary_spec.rb +0 -90
- data/spec/erlang/etf/bit_binary_spec.rb +0 -99
- data/spec/erlang/etf/compressed_spec.rb +0 -37
- data/spec/erlang/etf/export_spec.rb +0 -58
- data/spec/erlang/etf/extensions/array_spec.rb +0 -40
- data/spec/erlang/etf/extensions/big_decimal_spec.rb +0 -26
- data/spec/erlang/etf/extensions/erlang-export_spec.rb +0 -32
- data/spec/erlang/etf/extensions/erlang-list_spec.rb +0 -76
- data/spec/erlang/etf/extensions/erlang-map_spec.rb +0 -48
- data/spec/erlang/etf/extensions/erlang-nil_spec.rb +0 -24
- data/spec/erlang/etf/extensions/erlang-pid_spec.rb +0 -33
- data/spec/erlang/etf/extensions/erlang-string_spec.rb +0 -41
- data/spec/erlang/etf/extensions/erlang-tuple_spec.rb +0 -57
- data/spec/erlang/etf/extensions/false_class_spec.rb +0 -29
- data/spec/erlang/etf/extensions/float_spec.rb +0 -24
- data/spec/erlang/etf/extensions/hash_spec.rb +0 -90
- data/spec/erlang/etf/extensions/integer_spec.rb +0 -259
- data/spec/erlang/etf/extensions/nil_class_spec.rb +0 -29
- data/spec/erlang/etf/extensions/object_spec.rb +0 -30
- data/spec/erlang/etf/extensions/regexp_spec.rb +0 -35
- data/spec/erlang/etf/extensions/string_spec.rb +0 -43
- data/spec/erlang/etf/extensions/symbol_spec.rb +0 -64
- data/spec/erlang/etf/extensions/time_spec.rb +0 -32
- data/spec/erlang/etf/extensions/true_class_spec.rb +0 -29
- data/spec/erlang/etf/float_spec.rb +0 -92
- data/spec/erlang/etf/fun_spec.rb +0 -132
- data/spec/erlang/etf/integer_spec.rb +0 -57
- data/spec/erlang/etf/large_big_spec.rb +0 -67
- data/spec/erlang/etf/large_tuple_spec.rb +0 -119
- data/spec/erlang/etf/list_spec.rb +0 -159
- data/spec/erlang/etf/map_spec.rb +0 -100
- data/spec/erlang/etf/new_float_spec.rb +0 -92
- data/spec/erlang/etf/new_fun_spec.rb +0 -146
- data/spec/erlang/etf/new_reference_spec.rb +0 -60
- data/spec/erlang/etf/nil_spec.rb +0 -50
- data/spec/erlang/etf/pid_spec.rb +0 -61
- data/spec/erlang/etf/port_spec.rb +0 -58
- data/spec/erlang/etf/reference_spec.rb +0 -58
- data/spec/erlang/etf/small_atom_spec.rb +0 -90
- data/spec/erlang/etf/small_atom_utf8_spec.rb +0 -90
- data/spec/erlang/etf/small_big_spec.rb +0 -67
- data/spec/erlang/etf/small_integer_spec.rb +0 -57
- data/spec/erlang/etf/small_tuple_spec.rb +0 -112
- data/spec/erlang/etf/string_spec.rb +0 -92
- data/spec/erlang/etf/term_spec.rb +0 -27
- data/spec/erlang/etf/terms_spec.rb +0 -23
- data/spec/erlang/etf_spec.rb +0 -23
- data/spec/erlang_spec.rb +0 -95
- data/spec/spec_helper.rb +0 -31
data/lib/erlang/etf/list.rb
CHANGED
@@ -2,9 +2,9 @@ module Erlang
|
|
2
2
|
module ETF
|
3
3
|
|
4
4
|
#
|
5
|
-
# 1 | 4
|
6
|
-
# --- |
|
7
|
-
# 108 |
|
5
|
+
# | 1 | 4 | | |
|
6
|
+
# | --- | ------ | -------- | ---- |
|
7
|
+
# | 108 | Length | Elements | Tail |
|
8
8
|
#
|
9
9
|
# `Length` is the number of elements that follows in the `Elements`
|
10
10
|
# section. `Tail` is the final tail of the list; it is [`NIL_EXT`] for a
|
@@ -17,39 +17,69 @@ module Erlang
|
|
17
17
|
# [`LIST_EXT`]: http://erlang.org/doc/apps/erts/erl_ext_dist.html#LIST_EXT
|
18
18
|
#
|
19
19
|
class List
|
20
|
-
include Term
|
20
|
+
include Erlang::ETF::Term
|
21
21
|
|
22
|
-
|
22
|
+
UINT32BE = Erlang::ETF::Term::UINT32BE
|
23
23
|
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
24
|
+
class << self
|
25
|
+
def [](term, elements = nil, tail = nil)
|
26
|
+
return term if term.kind_of?(Erlang::ETF::Term)
|
27
|
+
term = Erlang.from(term)
|
28
|
+
return new(term, elements, tail)
|
29
|
+
end
|
28
30
|
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
31
|
+
def erlang_load(buffer)
|
32
|
+
length, = buffer.read(4).unpack(UINT32BE)
|
33
|
+
elements = Array.new(length)
|
34
|
+
length.times { |i| elements[i] = Erlang::ETF.read_term(buffer) }
|
35
|
+
tail = Erlang::ETF.read_term(buffer)
|
36
|
+
return tail if length == 0
|
37
|
+
list = Erlang::List.from_enum(elements) + tail
|
38
|
+
return new(list, elements, tail)
|
34
39
|
end
|
35
|
-
deserialize_tail(buffer)
|
36
|
-
self
|
37
40
|
end
|
38
41
|
|
39
|
-
|
42
|
+
def initialize(term, elements = nil, tail = nil)
|
43
|
+
raise ArgumentError, "term must be of any type" if not Erlang.is_any(term)
|
44
|
+
@term = term
|
45
|
+
@elements = elements.freeze
|
46
|
+
@tail = tail.freeze
|
47
|
+
end
|
40
48
|
|
41
|
-
def
|
42
|
-
|
43
|
-
|
49
|
+
def erlang_dump(buffer = ::String.new.force_encoding(BINARY_ENCODING))
|
50
|
+
buffer << LIST_EXT
|
51
|
+
elements = nil
|
52
|
+
tail = nil
|
53
|
+
if not Erlang.is_list(term)
|
54
|
+
elements = @elements || []
|
55
|
+
tail = @tail || @term
|
56
|
+
else
|
57
|
+
elements = @elements || (@term.improper? ? @term.to_proper_list : @term)
|
58
|
+
tail = @tail || (@term.improper? ? @term.last(true) : Erlang::Nil)
|
59
|
+
end
|
60
|
+
length = elements.size
|
61
|
+
buffer << [length].pack(UINT32BE)
|
62
|
+
elements.each { |element| Erlang::ETF.write_term(element, buffer) }
|
63
|
+
Erlang::ETF.write_term(tail, buffer)
|
64
|
+
return buffer
|
44
65
|
end
|
45
66
|
|
46
|
-
def
|
47
|
-
|
67
|
+
def inspect
|
68
|
+
if @elements.nil? and @tail.nil?
|
69
|
+
return super
|
70
|
+
else
|
71
|
+
return "#{self.class}[#{@term.inspect}, #{@elements.inspect}, #{@tail.inspect}]"
|
72
|
+
end
|
48
73
|
end
|
49
74
|
|
50
|
-
def
|
51
|
-
|
75
|
+
def pretty_print(pp)
|
76
|
+
state = [@term]
|
77
|
+
state.push(@elements, @tail) if not @elements.nil? or not @tail.nil?
|
78
|
+
return pp.group(1, "#{self.class}[", "]") do
|
79
|
+
pp.breakable ''
|
80
|
+
pp.seplist(state) { |obj| obj.pretty_print(pp) }
|
81
|
+
end
|
52
82
|
end
|
53
83
|
end
|
54
84
|
end
|
55
|
-
end
|
85
|
+
end
|
data/lib/erlang/etf/map.rb
CHANGED
@@ -2,50 +2,80 @@ module Erlang
|
|
2
2
|
module ETF
|
3
3
|
|
4
4
|
#
|
5
|
-
# 1 | 4
|
6
|
-
# --- |
|
7
|
-
# 116 |
|
5
|
+
# | 1 | 4 | N |
|
6
|
+
# | --- | ----- | ----- |
|
7
|
+
# | 116 | Arity | Pairs |
|
8
8
|
#
|
9
|
-
# The
|
10
|
-
#
|
9
|
+
# `MAP_EXT` encodes a map. The `Arity` field is an unsigned 4 byte integer
|
10
|
+
# in big endian format that determines the number of key-value pairs in the
|
11
|
+
# map. Key and value pairs (`Ki => Vi`) are encoded in the `Pairs` section
|
12
|
+
# in the following order: `K1, V1, K2, V2,..., Kn, Vn`. Duplicate keys are
|
13
|
+
# **not allowed** within the same map.
|
11
14
|
#
|
12
15
|
# (see [`MAP_EXT`])
|
13
16
|
#
|
14
17
|
# [`MAP_EXT`]: http://erlang.org/doc/apps/erts/erl_ext_dist.html#MAP_EXT
|
15
18
|
#
|
16
19
|
class Map
|
17
|
-
include Term
|
20
|
+
include Erlang::ETF::Term
|
18
21
|
|
19
|
-
|
22
|
+
UINT32BE = Erlang::ETF::Term::UINT32BE
|
20
23
|
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
deserialize do |buffer|
|
27
|
-
size, = buffer.read(BYTES_32).unpack(UINT32BE_PACK)
|
28
|
-
self.keys = []
|
29
|
-
size.times do
|
30
|
-
self.keys << Terms.deserialize(buffer)
|
24
|
+
class << self
|
25
|
+
def [](term, pairs = nil)
|
26
|
+
return term if term.kind_of?(Erlang::ETF::Term)
|
27
|
+
term = Erlang.from(term)
|
28
|
+
return new(term, pairs)
|
31
29
|
end
|
32
|
-
|
33
|
-
|
34
|
-
|
30
|
+
|
31
|
+
def erlang_load(buffer)
|
32
|
+
arity, = buffer.read(4).unpack(UINT32BE)
|
33
|
+
pairs = Array.new(arity * 2)
|
34
|
+
(arity * 2).times { |i| pairs[i] = Erlang::ETF.read_term(buffer) }
|
35
|
+
map = Erlang::Map[*pairs]
|
36
|
+
return new(map, pairs)
|
35
37
|
end
|
36
|
-
self
|
37
38
|
end
|
38
39
|
|
39
|
-
|
40
|
+
def initialize(term, pairs = nil)
|
41
|
+
raise ArgumentError, "term must be of type Map" if not Erlang.is_map(term)
|
42
|
+
@term = term
|
43
|
+
@pairs = pairs.freeze
|
44
|
+
end
|
40
45
|
|
41
|
-
def
|
42
|
-
|
43
|
-
@
|
46
|
+
def erlang_dump(buffer = ::String.new.force_encoding(BINARY_ENCODING))
|
47
|
+
buffer << MAP_EXT
|
48
|
+
if @pairs
|
49
|
+
arity = @pairs.length.div(2)
|
50
|
+
buffer << [arity].pack(UINT32BE)
|
51
|
+
(arity * 2).times { |i| Erlang::ETF.write_term(@pairs[i], buffer) }
|
52
|
+
else
|
53
|
+
arity = @term.size
|
54
|
+
buffer << [arity].pack(UINT32BE)
|
55
|
+
@term.sort.each { |key, val|
|
56
|
+
Erlang::ETF.write_term(key, buffer)
|
57
|
+
Erlang::ETF.write_term(val, buffer)
|
58
|
+
}
|
59
|
+
end
|
60
|
+
return buffer
|
44
61
|
end
|
45
62
|
|
46
|
-
def
|
47
|
-
|
63
|
+
def inspect
|
64
|
+
if @pairs.nil?
|
65
|
+
return super
|
66
|
+
else
|
67
|
+
return "#{self.class}[#{@term.inspect}, #{@pairs.inspect}]"
|
68
|
+
end
|
69
|
+
end
|
70
|
+
|
71
|
+
def pretty_print(pp)
|
72
|
+
state = [@term]
|
73
|
+
state.push(@pairs) if not @pairs.nil?
|
74
|
+
return pp.group(1, "#{self.class}[", "]") do
|
75
|
+
pp.breakable ''
|
76
|
+
pp.seplist(state) { |obj| obj.pretty_print(pp) }
|
77
|
+
end
|
48
78
|
end
|
49
79
|
end
|
50
80
|
end
|
51
|
-
end
|
81
|
+
end
|
data/lib/erlang/etf/new_float.rb
CHANGED
@@ -1,12 +1,10 @@
|
|
1
|
-
require 'bigdecimal'
|
2
|
-
|
3
1
|
module Erlang
|
4
2
|
module ETF
|
5
3
|
|
6
4
|
#
|
7
|
-
# 1 | 8
|
8
|
-
# --- | ----------
|
9
|
-
# 70 | IEEE Float
|
5
|
+
# | 1 | 8 |
|
6
|
+
# | --- | ---------- |
|
7
|
+
# | 70 | IEEE Float |
|
10
8
|
#
|
11
9
|
# A float is stored as 8 bytes in big-endian IEEE format.
|
12
10
|
#
|
@@ -17,21 +15,34 @@ module Erlang
|
|
17
15
|
# [`NEW_FLOAT_EXT`]: http://erlang.org/doc/apps/erts/erl_ext_dist.html#NEW_FLOAT_EXT
|
18
16
|
#
|
19
17
|
class NewFloat
|
20
|
-
include Term
|
18
|
+
include Erlang::ETF::Term
|
21
19
|
|
22
|
-
|
20
|
+
DOUBLEBE = Erlang::ETF::Term::DOUBLEBE
|
23
21
|
|
24
|
-
|
22
|
+
class << self
|
23
|
+
def [](term)
|
24
|
+
return term if term.kind_of?(Erlang::ETF::Term)
|
25
|
+
term = Erlang.from(term)
|
26
|
+
return new(term)
|
27
|
+
end
|
25
28
|
|
26
|
-
|
29
|
+
def erlang_load(buffer)
|
30
|
+
float, = buffer.read(8).unpack(DOUBLEBE)
|
31
|
+
term = Erlang::Float[float]
|
32
|
+
return new(term)
|
33
|
+
end
|
34
|
+
end
|
27
35
|
|
28
|
-
def initialize(
|
29
|
-
|
36
|
+
def initialize(term)
|
37
|
+
raise ArgumentError, "term must be of type Erlang::Float" if not Erlang.is_float(term) or term.old
|
38
|
+
@term = term
|
30
39
|
end
|
31
40
|
|
32
|
-
def
|
33
|
-
|
41
|
+
def erlang_dump(buffer = ::String.new.force_encoding(BINARY_ENCODING))
|
42
|
+
buffer << NEW_FLOAT_EXT
|
43
|
+
buffer << [@term.data].pack(DOUBLEBE)
|
44
|
+
return buffer
|
34
45
|
end
|
35
46
|
end
|
36
47
|
end
|
37
|
-
end
|
48
|
+
end
|
data/lib/erlang/etf/new_fun.rb
CHANGED
@@ -2,9 +2,9 @@ module Erlang
|
|
2
2
|
module ETF
|
3
3
|
|
4
4
|
#
|
5
|
-
# 1 | 4 | 1 | 16 | 4 | 4 | N1 | N2 | N3 | N4 | N5
|
6
|
-
# --- | ---- | ----- | ---- | ----- | ------- | ------ | -------- | ------- | --- | ---------
|
7
|
-
# 112 | Size | Arity | Uniq | Index | NumFree | Module | Oldindex | OldUniq | Pid | Free Vars
|
5
|
+
# | 1 | 4 | 1 | 16 | 4 | 4 | N1 | N2 | N3 | N4 | N5 |
|
6
|
+
# | --- | ---- | ----- | ---- | ----- | ------- | ------ | -------- | ------- | --- | --------- |
|
7
|
+
# | 112 | Size | Arity | Uniq | Index | NumFree | Module | Oldindex | OldUniq | Pid | Free Vars |
|
8
8
|
#
|
9
9
|
# This is the new encoding of internal funs:
|
10
10
|
#
|
@@ -60,61 +60,84 @@ module Erlang
|
|
60
60
|
# [`NEW_FUN_EXT`]: http://erlang.org/doc/apps/erts/erl_ext_dist.html#NEW_FUN_EXT
|
61
61
|
#
|
62
62
|
class NewFun
|
63
|
-
include Term
|
63
|
+
include Erlang::ETF::Term
|
64
64
|
|
65
|
-
|
65
|
+
UINT8 = Erlang::ETF::Term::UINT8
|
66
|
+
UINT32BE = Erlang::ETF::Term::UINT32BE
|
67
|
+
UINT128BE = Erlang::ETF::Term::UINT128BE
|
68
|
+
HEAD = (UINT32BE + UINT8 + UINT128BE + UINT32BE + UINT32BE).freeze
|
66
69
|
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
70
|
+
class << self
|
71
|
+
def [](term, arity = nil, uniq = nil, index = nil, mod = nil, old_index = nil, old_uniq = nil, pid = nil, free_vars = nil)
|
72
|
+
return new(term, arity, uniq, index, mod, old_index, old_uniq, pid, free_vars)
|
73
|
+
end
|
74
|
+
|
75
|
+
def erlang_load(buffer)
|
76
|
+
_, arity, uniq_hi, uniq_lo, index, num_free = buffer.read(29).unpack(HEAD)
|
77
|
+
uniq = (uniq_hi << 64) + uniq_lo
|
78
|
+
mod = Erlang::ETF.read_term(buffer)
|
79
|
+
old_index = Erlang::ETF.read_term(buffer)
|
80
|
+
old_uniq = Erlang::ETF.read_term(buffer)
|
81
|
+
pid = Erlang::ETF.read_term(buffer)
|
82
|
+
free_vars = Array.new(num_free); num_free.times { |i| free_vars[i] = Erlang::ETF.read_term(buffer) }
|
83
|
+
term = Erlang::Function[arity: Erlang.from(arity), uniq: Erlang.from(uniq), index: Erlang.from(index), mod: Erlang.from(mod), old_index: Erlang.from(old_index), old_uniq: Erlang.from(old_uniq), pid: Erlang.from(pid), free_vars: Erlang.from(free_vars)]
|
84
|
+
return new(term, arity, uniq, index, mod, old_index, old_uniq, pid, free_vars)
|
85
|
+
end
|
77
86
|
end
|
78
87
|
|
79
|
-
|
80
|
-
|
81
|
-
|
88
|
+
def initialize(term, arity = nil, uniq = nil, index = nil, mod = nil, old_index = nil, old_uniq = nil, pid = nil, free_vars = nil)
|
89
|
+
raise ArgumentError, "term must be of type Erlang::Function" if not term.kind_of?(Erlang::Function) or not term.new_function?
|
90
|
+
@term = term
|
91
|
+
@arity = arity
|
92
|
+
@uniq = uniq
|
93
|
+
@index = index
|
94
|
+
@mod = mod
|
95
|
+
@old_index = old_index
|
96
|
+
@old_uniq = old_uniq
|
97
|
+
@pid = pid
|
98
|
+
@free_vars = free_vars
|
82
99
|
end
|
83
100
|
|
84
|
-
|
85
|
-
|
86
|
-
|
101
|
+
def erlang_dump(buffer = ::String.new.force_encoding(BINARY_ENCODING))
|
102
|
+
buffer << NEW_FUN_EXT
|
103
|
+
size = 0
|
104
|
+
arity = @arity || @term.arity
|
105
|
+
uniq = @uniq || @term.uniq
|
106
|
+
index = @index || @term.index
|
107
|
+
free_vars = @free_vars || @term.free_vars
|
108
|
+
num_free = free_vars.length
|
109
|
+
sizestart = buffer.bytesize
|
110
|
+
buffer << [size, arity, uniq >> 64, uniq, index, num_free].pack(HEAD)
|
111
|
+
Erlang::ETF.write_term(@mod || @term.mod, buffer)
|
112
|
+
Erlang::ETF.write_term(@old_index || @term.old_index, buffer)
|
113
|
+
Erlang::ETF.write_term(@old_uniq || @term.old_uniq, buffer)
|
114
|
+
Erlang::ETF.write_term(@pid || @term.pid, buffer)
|
115
|
+
num_free.times { |i| Erlang::ETF.write_term(free_vars[i], buffer) }
|
116
|
+
sizeend = buffer.bytesize
|
117
|
+
size = sizeend - sizestart
|
118
|
+
buffer.setbyte(sizestart + 0, size >> 24)
|
119
|
+
buffer.setbyte(sizestart + 1, size >> 16)
|
120
|
+
buffer.setbyte(sizestart + 2, size >> 8)
|
121
|
+
buffer.setbyte(sizestart + 3, size)
|
122
|
+
return buffer
|
87
123
|
end
|
88
124
|
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
num_free, = buffer.read(BYTES_32).unpack(UINT32BE_PACK)
|
95
|
-
deserialize_mod(buffer)
|
96
|
-
deserialize_old_index(buffer)
|
97
|
-
deserialize_old_uniq(buffer)
|
98
|
-
deserialize_pid(buffer)
|
99
|
-
self.free_vars = []
|
100
|
-
num_free.times do
|
101
|
-
self.free_vars << Terms.deserialize(buffer)
|
125
|
+
def inspect
|
126
|
+
if @arity.nil? and @uniq.nil? and @index.nil? and @mod.nil? and @old_index.nil? and @old_uniq.nil? and @pid.nil? and @free_vars.nil?
|
127
|
+
return super
|
128
|
+
else
|
129
|
+
return "#{self.class}[#{@term.inspect}, #{@arity.inspect}, #{@uniq.inspect}, #{@index.inspect}, #{@mod.inspect}, #{@old_index.inspect}, #{@old_uniq.inspect}, #{@pid.inspect}, #{@free_vars.inspect}]"
|
102
130
|
end
|
103
|
-
self
|
104
131
|
end
|
105
132
|
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
self.
|
110
|
-
|
111
|
-
|
112
|
-
|
113
|
-
self.old_index = old_index
|
114
|
-
self.old_uniq = old_uniq
|
115
|
-
self.pid = pid
|
116
|
-
self.free_vars = free_vars
|
133
|
+
def pretty_print(pp)
|
134
|
+
state = [@term]
|
135
|
+
state.push(@arity, @uniq, @index, @mod, @old_index, @old_uniq, @pid, @free_vars) if not @arity.nil? or not @uniq.nil? or not @index.nil? or not @mod.nil? or not @old_index.nil? or not @old_uniq.nil? or not @pid.nil? or not @free_vars.nil?
|
136
|
+
return pp.group(1, "#{self.class}[", "]") do
|
137
|
+
pp.breakable ''
|
138
|
+
pp.seplist(state) { |obj| obj.pretty_print(pp) }
|
139
|
+
end
|
117
140
|
end
|
118
141
|
end
|
119
142
|
end
|
120
|
-
end
|
143
|
+
end
|
@@ -2,9 +2,9 @@ module Erlang
|
|
2
2
|
module ETF
|
3
3
|
|
4
4
|
#
|
5
|
-
# 1 | 2 | N | 1 | N'
|
6
|
-
# --- | --- | ---- | -------- | ------
|
7
|
-
# 114 | Len | Node | Creation | ID ...
|
5
|
+
# | 1 | 2 | N | 1 | N' |
|
6
|
+
# | --- | --- | ---- | -------- | ------ |
|
7
|
+
# | 114 | Len | Node | Creation | ID ... |
|
8
8
|
#
|
9
9
|
# `Node` and `Creation` are as in [`REFERENCE_EXT`].
|
10
10
|
#
|
@@ -29,36 +29,63 @@ module Erlang
|
|
29
29
|
# [`NEW_REFERENCE_EXT`]: http://erlang.org/doc/apps/erts/erl_ext_dist.html#NEW_REFERENCE_EXT
|
30
30
|
#
|
31
31
|
class NewReference
|
32
|
-
include Term
|
32
|
+
include Erlang::ETF::Term
|
33
33
|
|
34
|
-
|
34
|
+
UINT8 = Erlang::ETF::Term::UINT8
|
35
|
+
UINT16BE = Erlang::ETF::Term::UINT16BE
|
36
|
+
UINT32BE = Erlang::ETF::Term::UINT32BE
|
35
37
|
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
int8 :creation, maximum: (1 << 2) - 1
|
41
|
-
|
42
|
-
uint32be :ids, type: :array, default: []
|
38
|
+
class << self
|
39
|
+
def [](term, node = nil, creation = nil, ids = nil)
|
40
|
+
return new(term, node, creation, ids)
|
41
|
+
end
|
43
42
|
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
self.ids << buffer.read(BYTES_32).unpack(UINT32BE_PACK).at(0)
|
43
|
+
def erlang_load(buffer)
|
44
|
+
length, = buffer.read(2).unpack(UINT16BE)
|
45
|
+
node = Erlang::ETF.read_term(buffer)
|
46
|
+
creation, *ids = buffer.read(1 + (4 * length)).unpack("#{UINT8}#{UINT32BE}#{length}")
|
47
|
+
term = Erlang::Reference[Erlang.from(node), Erlang.from(creation), Erlang.from(ids)]
|
48
|
+
return new(term, node, creation, ids)
|
51
49
|
end
|
52
|
-
self
|
53
50
|
end
|
54
51
|
|
55
|
-
|
56
|
-
|
57
|
-
|
52
|
+
def initialize(term, node = nil, creation = nil, ids = nil)
|
53
|
+
raise ArgumentError, "term must be of type Erlang::Reference" if not term.kind_of?(Erlang::Reference) or not term.new_reference?
|
54
|
+
@term = term
|
58
55
|
@node = node
|
59
56
|
@creation = creation
|
60
57
|
@ids = ids
|
61
58
|
end
|
59
|
+
|
60
|
+
def erlang_dump(buffer = ::String.new.force_encoding(BINARY_ENCODING))
|
61
|
+
buffer << NEW_REFERENCE_EXT
|
62
|
+
ids = @ids || @term.ids
|
63
|
+
length = ids.size
|
64
|
+
buffer << [length].pack(UINT16BE)
|
65
|
+
Erlang::ETF.write_term(@node || @term.node, buffer)
|
66
|
+
buffer << [
|
67
|
+
@creation || @term.creation,
|
68
|
+
*ids
|
69
|
+
].pack("#{UINT8}#{UINT32BE}#{length}")
|
70
|
+
return buffer
|
71
|
+
end
|
72
|
+
|
73
|
+
def inspect
|
74
|
+
if @node.nil? and @creation.nil? and @ids.nil?
|
75
|
+
return super
|
76
|
+
else
|
77
|
+
return "#{self.class}[#{@term.inspect}, #{@node.inspect}, #{@creation.inspect}, #{@ids.inspect}]"
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
def pretty_print(pp)
|
82
|
+
state = [@term]
|
83
|
+
state.push(@node, @creation, @ids) if not @node.nil? or not @creation.nil? or not @ids.nil?
|
84
|
+
return pp.group(1, "#{self.class}[", "]") do
|
85
|
+
pp.breakable ''
|
86
|
+
pp.seplist(state) { |obj| obj.pretty_print(pp) }
|
87
|
+
end
|
88
|
+
end
|
62
89
|
end
|
63
90
|
end
|
64
|
-
end
|
91
|
+
end
|