rbs 3.9.4 → 4.1.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.clang-format +75 -0
- data/.clangd +2 -0
- data/.dockerignore +37 -0
- data/.github/dependabot.yml +16 -14
- data/.github/workflows/bundle-update.yml +63 -0
- data/.github/workflows/c-check.yml +66 -0
- data/.github/workflows/comments.yml +5 -3
- data/.github/workflows/dependabot.yml +2 -2
- data/.github/workflows/jruby.yml +79 -0
- data/.github/workflows/release-gems.yml +164 -0
- data/.github/workflows/ruby.yml +84 -30
- data/.github/workflows/rust.yml +186 -0
- data/.github/workflows/truffleruby.yml +54 -0
- data/.github/workflows/typecheck.yml +5 -2
- data/.github/workflows/wasm.yml +55 -0
- data/.github/workflows/windows.yml +9 -3
- data/.gitignore +16 -0
- data/.rubocop.yml +2 -2
- data/CHANGELOG.md +430 -0
- data/Dockerfile.jruby +53 -0
- data/README.md +41 -4
- data/Rakefile +777 -60
- data/Steepfile +11 -0
- data/config.yml +660 -62
- data/core/array.rbs +541 -398
- data/core/basic_object.rbs +9 -8
- data/core/binding.rbs +0 -2
- data/core/builtin.rbs +9 -8
- data/core/class.rbs +11 -8
- data/core/comparable.rbs +55 -34
- data/core/complex.rbs +104 -78
- data/core/dir.rbs +61 -49
- data/core/encoding.rbs +12 -15
- data/core/enumerable.rbs +297 -196
- data/core/enumerator/arithmetic_sequence.rbs +70 -0
- data/core/enumerator/product.rbs +5 -5
- data/core/enumerator.rbs +91 -28
- data/core/errno.rbs +11 -2
- data/core/errors.rbs +58 -29
- data/core/exception.rbs +13 -13
- data/core/fiber.rbs +74 -54
- data/core/file.rbs +260 -1151
- data/core/file_constants.rbs +463 -0
- data/core/file_stat.rbs +534 -0
- data/core/file_test.rbs +3 -3
- data/core/float.rbs +257 -116
- data/core/gc.rbs +425 -281
- data/core/hash.rbs +1151 -829
- data/core/integer.rbs +156 -195
- data/core/io/buffer.rbs +53 -42
- data/core/io/wait.rbs +13 -35
- data/core/io.rbs +220 -154
- data/core/kernel.rbs +239 -163
- data/core/marshal.rbs +4 -4
- data/core/match_data.rbs +16 -14
- data/core/math.rbs +107 -66
- data/core/method.rbs +69 -33
- data/core/module.rbs +302 -150
- data/core/nil_class.rbs +7 -6
- data/core/numeric.rbs +77 -63
- data/core/object.rbs +9 -11
- data/core/object_space/weak_key_map.rbs +7 -7
- data/core/object_space.rbs +30 -23
- data/core/pathname.rbs +1312 -0
- data/core/proc.rbs +95 -58
- data/core/process.rbs +222 -202
- data/core/ractor.rbs +364 -518
- data/core/random.rbs +21 -3
- data/core/range.rbs +181 -79
- data/core/rational.rbs +60 -89
- data/core/rbs/ops.rbs +154 -0
- data/core/rbs/unnamed/argf.rbs +63 -56
- data/core/rbs/unnamed/env_class.rbs +19 -14
- data/core/rbs/unnamed/main_class.rbs +123 -0
- data/core/rbs/unnamed/random.rbs +11 -118
- data/core/regexp.rbs +258 -214
- data/core/ruby.rbs +53 -0
- data/core/ruby_vm.rbs +78 -34
- data/core/rubygems/config_file.rbs +5 -5
- data/core/rubygems/errors.rbs +6 -70
- data/core/rubygems/requirement.rbs +5 -15
- data/core/rubygems/rubygems.rbs +18 -81
- data/core/rubygems/specification.rbs +8 -0
- data/core/rubygems/version.rbs +2 -163
- data/core/set.rbs +493 -363
- data/core/signal.rbs +26 -16
- data/core/string.rbs +3234 -1285
- data/core/struct.rbs +43 -42
- data/core/symbol.rbs +41 -34
- data/core/thread.rbs +139 -83
- data/core/time.rbs +81 -50
- data/core/trace_point.rbs +41 -35
- data/core/true_class.rbs +2 -2
- data/core/unbound_method.rbs +24 -16
- data/core/warning.rbs +7 -7
- data/docs/CONTRIBUTING.md +2 -1
- data/docs/aliases.md +79 -0
- data/docs/collection.md +3 -3
- data/docs/config.md +171 -0
- data/docs/encoding.md +56 -0
- data/docs/gem.md +0 -1
- data/docs/inline.md +634 -0
- data/docs/rbs_by_example.md +20 -20
- data/docs/release.md +151 -0
- data/docs/rust.md +96 -0
- data/docs/sigs.md +3 -3
- data/docs/syntax.md +48 -18
- data/docs/type_fingerprint.md +21 -0
- data/docs/wasm_serialization.md +80 -0
- data/exe/rbs +1 -1
- data/ext/rbs_extension/ast_translation.c +1855 -0
- data/ext/rbs_extension/ast_translation.h +41 -0
- data/ext/rbs_extension/class_constants.c +187 -0
- data/{include/rbs/constants.h → ext/rbs_extension/class_constants.h} +23 -1
- data/ext/rbs_extension/compat.h +10 -0
- data/ext/rbs_extension/extconf.rb +26 -1
- data/ext/rbs_extension/legacy_location.c +299 -0
- data/ext/rbs_extension/legacy_location.h +82 -0
- data/ext/rbs_extension/main.c +603 -23
- data/ext/rbs_extension/rbs_extension.h +6 -21
- data/ext/rbs_extension/rbs_string_bridging.c +9 -0
- data/ext/rbs_extension/rbs_string_bridging.h +24 -0
- data/include/rbs/ast.h +1047 -0
- data/include/rbs/defines.h +99 -0
- data/include/rbs/lexer.h +207 -0
- data/include/rbs/location.h +40 -0
- data/include/rbs/parser.h +153 -0
- data/include/rbs/serialize.h +39 -0
- data/include/rbs/string.h +47 -0
- data/include/rbs/util/rbs_allocator.h +59 -0
- data/include/rbs/util/rbs_assert.h +20 -0
- data/include/rbs/util/rbs_buffer.h +83 -0
- data/include/rbs/util/rbs_constant_pool.h +6 -70
- data/include/rbs/util/rbs_encoding.h +282 -0
- data/include/rbs/util/rbs_unescape.h +24 -0
- data/include/rbs.h +9 -2
- data/lib/rbs/annotate/formatter.rb +3 -13
- data/lib/rbs/annotate/rdoc_annotator.rb +30 -32
- data/lib/rbs/annotate/rdoc_source.rb +1 -1
- data/lib/rbs/ast/annotation.rb +1 -1
- data/lib/rbs/ast/comment.rb +1 -1
- data/lib/rbs/ast/declarations.rb +10 -10
- data/lib/rbs/ast/members.rb +14 -14
- data/lib/rbs/ast/ruby/annotations.rb +451 -0
- data/lib/rbs/ast/ruby/comment_block.rb +247 -0
- data/lib/rbs/ast/ruby/declarations.rb +291 -0
- data/lib/rbs/ast/ruby/helpers/constant_helper.rb +28 -0
- data/lib/rbs/ast/ruby/helpers/location_helper.rb +15 -0
- data/lib/rbs/ast/ruby/members.rb +762 -0
- data/lib/rbs/ast/type_param.rb +24 -4
- data/lib/rbs/buffer.rb +142 -20
- data/lib/rbs/cli/diff.rb +16 -15
- data/lib/rbs/cli/validate.rb +63 -126
- data/lib/rbs/cli.rb +59 -29
- data/lib/rbs/collection/config/lockfile_generator.rb +28 -3
- data/lib/rbs/collection/sources/git.rb +7 -0
- data/lib/rbs/definition.rb +6 -1
- data/lib/rbs/definition_builder/ancestor_builder.rb +121 -65
- data/lib/rbs/definition_builder/method_builder.rb +74 -33
- data/lib/rbs/definition_builder.rb +177 -20
- data/lib/rbs/diff.rb +7 -1
- data/lib/rbs/environment/class_entry.rb +69 -0
- data/lib/rbs/environment/module_entry.rb +66 -0
- data/lib/rbs/environment.rb +410 -215
- data/lib/rbs/environment_loader.rb +2 -8
- data/lib/rbs/errors.rb +31 -21
- data/lib/rbs/inline_parser/comment_association.rb +117 -0
- data/lib/rbs/inline_parser.rb +568 -0
- data/lib/rbs/location_aux.rb +36 -4
- data/lib/rbs/locator.rb +5 -1
- data/lib/rbs/method_type.rb +5 -3
- data/lib/rbs/namespace.rb +47 -18
- data/lib/rbs/parser_aux.rb +37 -7
- data/lib/rbs/prototype/helpers.rb +57 -0
- data/lib/rbs/prototype/rb.rb +3 -28
- data/lib/rbs/prototype/rbi.rb +196 -45
- data/lib/rbs/prototype/runtime.rb +12 -2
- data/lib/rbs/resolver/constant_resolver.rb +2 -2
- data/lib/rbs/resolver/type_name_resolver.rb +120 -44
- data/lib/rbs/rewriter.rb +70 -0
- data/lib/rbs/source.rb +99 -0
- data/lib/rbs/subtractor.rb +7 -4
- data/lib/rbs/test/type_check.rb +25 -3
- data/lib/rbs/type_name.rb +34 -21
- data/lib/rbs/types.rb +91 -79
- data/lib/rbs/unit_test/convertibles.rb +1 -0
- data/lib/rbs/unit_test/type_assertions.rb +44 -8
- data/lib/rbs/validator.rb +2 -2
- data/lib/rbs/version.rb +1 -1
- data/lib/rbs/wasm/deserializer.rb +213 -0
- data/lib/rbs/wasm/location.rb +61 -0
- data/lib/rbs/wasm/parser.rb +137 -0
- data/lib/rbs/wasm/runtime.rb +196 -0
- data/lib/rbs/wasm/serialization_schema.rb +110 -0
- data/lib/rbs.rb +25 -2
- data/lib/rbs_jars.rb +39 -0
- data/lib/rdoc/discover.rb +1 -1
- data/lib/rdoc_plugin/parser.rb +8 -3
- data/rbs.gemspec +37 -5
- data/schema/typeParam.json +17 -1
- data/sig/ancestor_builder.rbs +1 -1
- data/sig/annotate/formatter.rbs +2 -2
- data/sig/annotate/rdoc_annotater.rbs +13 -10
- data/sig/ast/ruby/annotations.rbs +470 -0
- data/sig/ast/ruby/comment_block.rbs +127 -0
- data/sig/ast/ruby/declarations.rbs +158 -0
- data/sig/ast/ruby/helpers/constant_helper.rbs +11 -0
- data/sig/ast/ruby/helpers/location_helper.rbs +15 -0
- data/sig/ast/ruby/members.rbs +198 -0
- data/sig/buffer.rbs +81 -5
- data/sig/cli/diff.rbs +5 -11
- data/sig/cli/validate.rbs +12 -8
- data/sig/cli.rbs +18 -18
- data/sig/collection/config/lockfile_generator.rbs +2 -0
- data/sig/definition.rbs +6 -0
- data/sig/definition_builder.rbs +3 -1
- data/sig/environment/class_entry.rbs +50 -0
- data/sig/environment/module_entry.rbs +50 -0
- data/sig/environment.rbs +94 -87
- data/sig/errors.rbs +26 -20
- data/sig/inline_parser/comment_association.rbs +71 -0
- data/sig/inline_parser.rbs +126 -0
- data/sig/location.rbs +32 -7
- data/sig/locator.rbs +0 -2
- data/sig/manifest.yaml +0 -2
- data/sig/method_builder.rbs +9 -4
- data/sig/namespace.rbs +20 -5
- data/sig/parser.rbs +77 -13
- data/sig/prototype/helpers.rbs +2 -0
- data/sig/prototype/rbi.rbs +33 -4
- data/sig/resolver/type_name_resolver.rbs +36 -10
- data/sig/rewriter.rbs +45 -0
- data/sig/source.rbs +48 -0
- data/sig/type_param.rbs +13 -8
- data/sig/typename.rbs +15 -5
- data/sig/types.rbs +10 -8
- data/sig/unit_test/spy.rbs +0 -8
- data/sig/unit_test/type_assertions.rbs +15 -0
- data/sig/wasm/deserializer.rbs +66 -0
- data/sig/wasm/serialization_schema.rbs +13 -0
- data/src/ast.c +1628 -0
- data/src/lexer.c +3221 -0
- data/src/lexer.re +155 -0
- data/src/lexstate.c +221 -0
- data/src/location.c +31 -0
- data/src/parser.c +4258 -0
- data/src/serialize.c +958 -0
- data/src/string.c +41 -0
- data/src/util/rbs_allocator.c +171 -0
- data/src/util/rbs_assert.c +19 -0
- data/src/util/rbs_buffer.c +54 -0
- data/src/util/rbs_constant_pool.c +18 -92
- data/src/util/rbs_encoding.c +21308 -0
- data/src/util/rbs_unescape.c +167 -0
- data/stdlib/abbrev/0/array.rbs +1 -1
- data/stdlib/bigdecimal/0/big_decimal.rbs +116 -98
- data/stdlib/bigdecimal-math/0/big_math.rbs +169 -8
- data/stdlib/cgi/0/core.rbs +9 -393
- data/stdlib/cgi/0/manifest.yaml +1 -0
- data/stdlib/cgi-escape/0/escape.rbs +171 -0
- data/stdlib/coverage/0/coverage.rbs +7 -4
- data/stdlib/csv/0/csv.rbs +5 -5
- data/stdlib/date/0/date.rbs +92 -79
- data/stdlib/date/0/date_time.rbs +25 -24
- data/stdlib/delegate/0/delegator.rbs +11 -7
- data/stdlib/did_you_mean/0/did_you_mean.rbs +17 -16
- data/stdlib/digest/0/digest.rbs +117 -1
- data/stdlib/erb/0/erb.rbs +748 -347
- data/stdlib/etc/0/etc.rbs +73 -54
- data/stdlib/fileutils/0/fileutils.rbs +179 -160
- data/stdlib/forwardable/0/forwardable.rbs +13 -10
- data/stdlib/io-console/0/io-console.rbs +2 -2
- data/stdlib/ipaddr/0/ipaddr.rbs +0 -5
- data/stdlib/json/0/json.rbs +232 -185
- data/stdlib/monitor/0/monitor.rbs +5 -5
- data/stdlib/net-http/0/net-http.rbs +162 -134
- data/stdlib/objspace/0/objspace.rbs +17 -34
- data/stdlib/open-uri/0/open-uri.rbs +48 -8
- data/stdlib/open3/0/open3.rbs +469 -10
- data/stdlib/openssl/0/openssl.rbs +521 -397
- data/stdlib/optparse/0/optparse.rbs +26 -17
- data/stdlib/pathname/0/pathname.rbs +11 -1381
- data/stdlib/pp/0/pp.rbs +9 -8
- data/stdlib/prettyprint/0/prettyprint.rbs +7 -7
- data/stdlib/pstore/0/pstore.rbs +35 -30
- data/stdlib/psych/0/psych.rbs +65 -12
- data/stdlib/psych/0/store.rbs +2 -4
- data/stdlib/pty/0/pty.rbs +9 -6
- data/stdlib/random-formatter/0/random-formatter.rbs +277 -0
- data/stdlib/rdoc/0/code_object.rbs +4 -3
- data/stdlib/rdoc/0/comment.rbs +2 -0
- data/stdlib/rdoc/0/options.rbs +76 -0
- data/stdlib/rdoc/0/parser.rbs +1 -1
- data/stdlib/rdoc/0/rdoc.rbs +7 -5
- data/stdlib/rdoc/0/store.rbs +2 -2
- data/stdlib/resolv/0/resolv.rbs +26 -69
- data/stdlib/ripper/0/ripper.rbs +25 -19
- data/stdlib/securerandom/0/manifest.yaml +2 -0
- data/stdlib/securerandom/0/securerandom.rbs +7 -20
- data/stdlib/shellwords/0/shellwords.rbs +3 -3
- data/stdlib/singleton/0/singleton.rbs +3 -0
- data/stdlib/socket/0/addrinfo.rbs +9 -9
- data/stdlib/socket/0/basic_socket.rbs +3 -3
- data/stdlib/socket/0/ip_socket.rbs +10 -8
- data/stdlib/socket/0/socket.rbs +23 -10
- data/stdlib/socket/0/tcp_server.rbs +1 -1
- data/stdlib/socket/0/tcp_socket.rbs +11 -3
- data/stdlib/socket/0/udp_socket.rbs +1 -1
- data/stdlib/socket/0/unix_server.rbs +1 -1
- data/stdlib/stringio/0/stringio.rbs +1209 -95
- data/stdlib/strscan/0/string_scanner.rbs +101 -80
- data/stdlib/tempfile/0/manifest.yaml +3 -0
- data/stdlib/tempfile/0/tempfile.rbs +25 -21
- data/stdlib/time/0/time.rbs +8 -6
- data/stdlib/timeout/0/timeout.rbs +58 -7
- data/stdlib/tsort/0/cyclic.rbs +4 -1
- data/stdlib/tsort/0/interfaces.rbs +8 -8
- data/stdlib/tsort/0/tsort.rbs +16 -15
- data/stdlib/uri/0/common.rbs +42 -20
- data/stdlib/uri/0/file.rbs +3 -3
- data/stdlib/uri/0/generic.rbs +21 -18
- data/stdlib/uri/0/http.rbs +2 -2
- data/stdlib/uri/0/ldap.rbs +2 -2
- data/stdlib/uri/0/mailto.rbs +3 -3
- data/stdlib/uri/0/rfc2396_parser.rbs +12 -12
- data/stdlib/zlib/0/deflate.rbs +4 -3
- data/stdlib/zlib/0/gzip_reader.rbs +8 -8
- data/stdlib/zlib/0/gzip_writer.rbs +14 -12
- data/stdlib/zlib/0/inflate.rbs +1 -1
- data/stdlib/zlib/0/need_dict.rbs +1 -1
- data/wasm/README.md +60 -0
- data/wasm/rbs_wasm.c +423 -0
- metadata +131 -19
- data/ext/rbs_extension/lexer.c +0 -2728
- data/ext/rbs_extension/lexer.h +0 -179
- data/ext/rbs_extension/lexer.re +0 -147
- data/ext/rbs_extension/lexstate.c +0 -175
- data/ext/rbs_extension/location.c +0 -325
- data/ext/rbs_extension/location.h +0 -85
- data/ext/rbs_extension/parser.c +0 -2982
- data/ext/rbs_extension/parser.h +0 -18
- data/ext/rbs_extension/parserstate.c +0 -411
- data/ext/rbs_extension/parserstate.h +0 -163
- data/ext/rbs_extension/unescape.c +0 -32
- data/include/rbs/ruby_objs.h +0 -72
- data/src/constants.c +0 -153
- data/src/ruby_objs.c +0 -799
data/lib/rbs/types.rb
CHANGED
|
@@ -61,7 +61,7 @@ module RBS
|
|
|
61
61
|
include EmptyEachType
|
|
62
62
|
include NoTypeName
|
|
63
63
|
|
|
64
|
-
def to_json(state =
|
|
64
|
+
def to_json(state = nil)
|
|
65
65
|
klass = to_s.to_sym
|
|
66
66
|
{ class: klass, location: location }.to_json(state)
|
|
67
67
|
end
|
|
@@ -157,7 +157,7 @@ module RBS
|
|
|
157
157
|
end
|
|
158
158
|
end
|
|
159
159
|
|
|
160
|
-
def to_json(state =
|
|
160
|
+
def to_json(state = nil)
|
|
161
161
|
{ class: :variable, name: name, location: location }.to_json(state)
|
|
162
162
|
end
|
|
163
163
|
|
|
@@ -199,58 +199,6 @@ module RBS
|
|
|
199
199
|
end
|
|
200
200
|
end
|
|
201
201
|
|
|
202
|
-
class ClassSingleton
|
|
203
|
-
attr_reader :name
|
|
204
|
-
attr_reader :location
|
|
205
|
-
|
|
206
|
-
def initialize(name:, location:)
|
|
207
|
-
@name = name
|
|
208
|
-
@location = location
|
|
209
|
-
end
|
|
210
|
-
|
|
211
|
-
def ==(other)
|
|
212
|
-
other.is_a?(ClassSingleton) && other.name == name
|
|
213
|
-
end
|
|
214
|
-
|
|
215
|
-
alias eql? ==
|
|
216
|
-
|
|
217
|
-
def hash
|
|
218
|
-
self.class.hash ^ name.hash
|
|
219
|
-
end
|
|
220
|
-
|
|
221
|
-
include NoFreeVariables
|
|
222
|
-
include NoSubst
|
|
223
|
-
|
|
224
|
-
def to_json(state = _ = nil)
|
|
225
|
-
{ class: :class_singleton, name: name, location: location }.to_json(state)
|
|
226
|
-
end
|
|
227
|
-
|
|
228
|
-
def to_s(level = 0)
|
|
229
|
-
"singleton(#{name})"
|
|
230
|
-
end
|
|
231
|
-
|
|
232
|
-
include EmptyEachType
|
|
233
|
-
|
|
234
|
-
def map_type_name(&)
|
|
235
|
-
ClassSingleton.new(
|
|
236
|
-
name: yield(name, location, self),
|
|
237
|
-
location: location
|
|
238
|
-
)
|
|
239
|
-
end
|
|
240
|
-
|
|
241
|
-
def has_self_type?
|
|
242
|
-
false
|
|
243
|
-
end
|
|
244
|
-
|
|
245
|
-
def has_classish_type?
|
|
246
|
-
false
|
|
247
|
-
end
|
|
248
|
-
|
|
249
|
-
def with_nonreturn_void?
|
|
250
|
-
false
|
|
251
|
-
end
|
|
252
|
-
end
|
|
253
|
-
|
|
254
202
|
module Application
|
|
255
203
|
attr_reader :name
|
|
256
204
|
attr_reader :args
|
|
@@ -303,12 +251,74 @@ module RBS
|
|
|
303
251
|
# `void` in immediate generics parameter is allowed
|
|
304
252
|
false
|
|
305
253
|
else
|
|
306
|
-
type.with_nonreturn_void?
|
|
254
|
+
type.with_nonreturn_void? # steep:ignore DeprecatedReference
|
|
307
255
|
end
|
|
308
256
|
end
|
|
309
257
|
end
|
|
310
258
|
end
|
|
311
259
|
|
|
260
|
+
class ClassSingleton
|
|
261
|
+
attr_reader :location
|
|
262
|
+
|
|
263
|
+
include Application
|
|
264
|
+
|
|
265
|
+
def initialize(name:, location:, args: [])
|
|
266
|
+
@name = name
|
|
267
|
+
@location = location
|
|
268
|
+
@args = args
|
|
269
|
+
end
|
|
270
|
+
|
|
271
|
+
def ==(other)
|
|
272
|
+
other.is_a?(ClassSingleton) && other.name == name && other.args == args
|
|
273
|
+
end
|
|
274
|
+
|
|
275
|
+
alias eql? ==
|
|
276
|
+
|
|
277
|
+
def hash
|
|
278
|
+
self.class.hash ^ name.hash ^ args.hash
|
|
279
|
+
end
|
|
280
|
+
|
|
281
|
+
def sub(s)
|
|
282
|
+
return self if s.empty?
|
|
283
|
+
|
|
284
|
+
self.class.new(name: name,
|
|
285
|
+
args: args.map {|ty| ty.sub(s) },
|
|
286
|
+
location: location)
|
|
287
|
+
end
|
|
288
|
+
|
|
289
|
+
def to_json(state = _ = nil)
|
|
290
|
+
{ class: :class_singleton, name: name, args: args, location: location }.to_json(state)
|
|
291
|
+
end
|
|
292
|
+
|
|
293
|
+
def to_s(level = 0)
|
|
294
|
+
if args.empty?
|
|
295
|
+
"singleton(#{name})"
|
|
296
|
+
else
|
|
297
|
+
"singleton(#{name})[#{args.join(", ")}]"
|
|
298
|
+
end
|
|
299
|
+
end
|
|
300
|
+
|
|
301
|
+
def map_type_name(&block)
|
|
302
|
+
ClassSingleton.new(
|
|
303
|
+
name: yield(name, location, self),
|
|
304
|
+
args: args.map {|type| type.map_type_name(&block) },
|
|
305
|
+
location: location
|
|
306
|
+
)
|
|
307
|
+
end
|
|
308
|
+
|
|
309
|
+
def map_type(&block)
|
|
310
|
+
if block
|
|
311
|
+
ClassSingleton.new(
|
|
312
|
+
name: name,
|
|
313
|
+
args: args.map {|type| yield type },
|
|
314
|
+
location: location
|
|
315
|
+
)
|
|
316
|
+
else
|
|
317
|
+
enum_for :map_type
|
|
318
|
+
end
|
|
319
|
+
end
|
|
320
|
+
end
|
|
321
|
+
|
|
312
322
|
class Interface
|
|
313
323
|
attr_reader :location
|
|
314
324
|
|
|
@@ -320,7 +330,7 @@ module RBS
|
|
|
320
330
|
@location = location
|
|
321
331
|
end
|
|
322
332
|
|
|
323
|
-
def to_json(state =
|
|
333
|
+
def to_json(state = nil)
|
|
324
334
|
{ class: :interface, name: name, args: args, location: location }.to_json(state)
|
|
325
335
|
end
|
|
326
336
|
|
|
@@ -364,7 +374,7 @@ module RBS
|
|
|
364
374
|
@location = location
|
|
365
375
|
end
|
|
366
376
|
|
|
367
|
-
def to_json(state =
|
|
377
|
+
def to_json(state = nil)
|
|
368
378
|
{ class: :class_instance, name: name, args: args, location: location }.to_json(state)
|
|
369
379
|
end
|
|
370
380
|
|
|
@@ -408,7 +418,7 @@ module RBS
|
|
|
408
418
|
@location = location
|
|
409
419
|
end
|
|
410
420
|
|
|
411
|
-
def to_json(state =
|
|
421
|
+
def to_json(state = nil)
|
|
412
422
|
{ class: :alias, name: name, args: args, location: location }.to_json(state)
|
|
413
423
|
end
|
|
414
424
|
|
|
@@ -466,7 +476,7 @@ module RBS
|
|
|
466
476
|
end
|
|
467
477
|
end
|
|
468
478
|
|
|
469
|
-
def to_json(state =
|
|
479
|
+
def to_json(state = nil)
|
|
470
480
|
{ class: :tuple, types: types, location: location }.to_json(state)
|
|
471
481
|
end
|
|
472
482
|
|
|
@@ -520,7 +530,7 @@ module RBS
|
|
|
520
530
|
end
|
|
521
531
|
|
|
522
532
|
def with_nonreturn_void?
|
|
523
|
-
each_type.any? {|type| type.with_nonreturn_void? }
|
|
533
|
+
each_type.any? {|type| type.with_nonreturn_void? } # steep:ignore DeprecatedReference
|
|
524
534
|
end
|
|
525
535
|
end
|
|
526
536
|
|
|
@@ -573,7 +583,7 @@ module RBS
|
|
|
573
583
|
end
|
|
574
584
|
end
|
|
575
585
|
|
|
576
|
-
def to_json(state =
|
|
586
|
+
def to_json(state = nil)
|
|
577
587
|
{ class: :record, fields: fields, optional_fields: optional_fields, location: location }.to_json(state)
|
|
578
588
|
end
|
|
579
589
|
|
|
@@ -638,7 +648,7 @@ module RBS
|
|
|
638
648
|
end
|
|
639
649
|
|
|
640
650
|
def with_nonreturn_void?
|
|
641
|
-
each_type.any? {|type| type.with_nonreturn_void? }
|
|
651
|
+
each_type.any? {|type| type.with_nonreturn_void? } # steep:ignore DeprecatedReference
|
|
642
652
|
end
|
|
643
653
|
end
|
|
644
654
|
|
|
@@ -665,7 +675,7 @@ module RBS
|
|
|
665
675
|
type.free_variables(set)
|
|
666
676
|
end
|
|
667
677
|
|
|
668
|
-
def to_json(state =
|
|
678
|
+
def to_json(state = nil)
|
|
669
679
|
{ class: :optional, type: type, location: location }.to_json(state)
|
|
670
680
|
end
|
|
671
681
|
|
|
@@ -724,7 +734,7 @@ module RBS
|
|
|
724
734
|
end
|
|
725
735
|
|
|
726
736
|
def with_nonreturn_void?
|
|
727
|
-
each_type.any? {|type| type.with_nonreturn_void? }
|
|
737
|
+
each_type.any? {|type| type.with_nonreturn_void? } # steep:ignore DeprecatedReference
|
|
728
738
|
end
|
|
729
739
|
end
|
|
730
740
|
|
|
@@ -755,7 +765,7 @@ module RBS
|
|
|
755
765
|
end
|
|
756
766
|
end
|
|
757
767
|
|
|
758
|
-
def to_json(state =
|
|
768
|
+
def to_json(state = nil)
|
|
759
769
|
{ class: :union, types: types, location: location }.to_json(state)
|
|
760
770
|
end
|
|
761
771
|
|
|
@@ -815,7 +825,7 @@ module RBS
|
|
|
815
825
|
end
|
|
816
826
|
|
|
817
827
|
def with_nonreturn_void?
|
|
818
|
-
each_type.any? {|type| type.with_nonreturn_void? }
|
|
828
|
+
each_type.any? {|type| type.with_nonreturn_void? } # steep:ignore DeprecatedReference
|
|
819
829
|
end
|
|
820
830
|
end
|
|
821
831
|
|
|
@@ -846,7 +856,7 @@ module RBS
|
|
|
846
856
|
end
|
|
847
857
|
end
|
|
848
858
|
|
|
849
|
-
def to_json(state =
|
|
859
|
+
def to_json(state = nil)
|
|
850
860
|
{ class: :intersection, types: types, location: location }.to_json(state)
|
|
851
861
|
end
|
|
852
862
|
|
|
@@ -898,7 +908,7 @@ module RBS
|
|
|
898
908
|
end
|
|
899
909
|
|
|
900
910
|
def with_nonreturn_void?
|
|
901
|
-
each_type.any? {|type| type.with_nonreturn_void? }
|
|
911
|
+
each_type.any? {|type| type.with_nonreturn_void? } # steep:ignore DeprecatedReference
|
|
902
912
|
end
|
|
903
913
|
end
|
|
904
914
|
|
|
@@ -932,7 +942,7 @@ module RBS
|
|
|
932
942
|
end
|
|
933
943
|
end
|
|
934
944
|
|
|
935
|
-
def to_json(state =
|
|
945
|
+
def to_json(state = nil)
|
|
936
946
|
{ type: type, name: name }.to_json(state)
|
|
937
947
|
end
|
|
938
948
|
|
|
@@ -1091,7 +1101,7 @@ module RBS
|
|
|
1091
1101
|
end
|
|
1092
1102
|
end
|
|
1093
1103
|
|
|
1094
|
-
def to_json(state =
|
|
1104
|
+
def to_json(state = nil)
|
|
1095
1105
|
{
|
|
1096
1106
|
required_positionals: required_positionals,
|
|
1097
1107
|
optional_positionals: optional_positionals,
|
|
@@ -1226,13 +1236,13 @@ module RBS
|
|
|
1226
1236
|
end
|
|
1227
1237
|
|
|
1228
1238
|
def with_nonreturn_void?
|
|
1229
|
-
if each_param.any? {|param| param.type.with_nonreturn_void? }
|
|
1239
|
+
if each_param.any? {|param| param.type.with_nonreturn_void? } # steep:ignore DeprecatedReference
|
|
1230
1240
|
true
|
|
1231
1241
|
else
|
|
1232
1242
|
if return_type.is_a?(Bases::Void)
|
|
1233
1243
|
false
|
|
1234
1244
|
else
|
|
1235
|
-
return_type.with_nonreturn_void?
|
|
1245
|
+
return_type.with_nonreturn_void? # steep:ignore DeprecatedReference
|
|
1236
1246
|
end
|
|
1237
1247
|
end
|
|
1238
1248
|
end
|
|
@@ -1279,7 +1289,7 @@ module RBS
|
|
|
1279
1289
|
end
|
|
1280
1290
|
end
|
|
1281
1291
|
|
|
1282
|
-
def to_json(state =
|
|
1292
|
+
def to_json(state = nil)
|
|
1283
1293
|
{
|
|
1284
1294
|
return_type: return_type
|
|
1285
1295
|
}.to_json(state)
|
|
@@ -1339,8 +1349,10 @@ module RBS
|
|
|
1339
1349
|
attr_reader :type
|
|
1340
1350
|
attr_reader :required
|
|
1341
1351
|
attr_reader :self_type
|
|
1352
|
+
attr_reader :location
|
|
1342
1353
|
|
|
1343
|
-
def initialize(type:, required:, self_type: nil)
|
|
1354
|
+
def initialize(location: nil, type:, required:, self_type: nil)
|
|
1355
|
+
@location = location
|
|
1344
1356
|
@type = type
|
|
1345
1357
|
@required = required ? true : false
|
|
1346
1358
|
@self_type = self_type
|
|
@@ -1353,7 +1365,7 @@ module RBS
|
|
|
1353
1365
|
other.self_type == self_type
|
|
1354
1366
|
end
|
|
1355
1367
|
|
|
1356
|
-
def to_json(state =
|
|
1368
|
+
def to_json(state = nil)
|
|
1357
1369
|
{
|
|
1358
1370
|
type: type,
|
|
1359
1371
|
required: required,
|
|
@@ -1422,7 +1434,7 @@ module RBS
|
|
|
1422
1434
|
set
|
|
1423
1435
|
end
|
|
1424
1436
|
|
|
1425
|
-
def to_json(state =
|
|
1437
|
+
def to_json(state = nil)
|
|
1426
1438
|
{
|
|
1427
1439
|
class: :proc,
|
|
1428
1440
|
type: type,
|
|
@@ -1503,11 +1515,11 @@ module RBS
|
|
|
1503
1515
|
end
|
|
1504
1516
|
|
|
1505
1517
|
def with_nonreturn_void?
|
|
1506
|
-
if type.with_nonreturn_void? || self_type&.with_nonreturn_void?
|
|
1518
|
+
if type.with_nonreturn_void? || self_type&.with_nonreturn_void? # steep:ignore DeprecatedReference
|
|
1507
1519
|
true
|
|
1508
1520
|
else
|
|
1509
1521
|
if block = block()
|
|
1510
|
-
block.type.with_nonreturn_void? || block.self_type&.with_nonreturn_void? || false
|
|
1522
|
+
block.type.with_nonreturn_void? || block.self_type&.with_nonreturn_void? || false # steep:ignore DeprecatedReference
|
|
1511
1523
|
else
|
|
1512
1524
|
false
|
|
1513
1525
|
end
|
|
@@ -1539,7 +1551,7 @@ module RBS
|
|
|
1539
1551
|
include EmptyEachType
|
|
1540
1552
|
include NoTypeName
|
|
1541
1553
|
|
|
1542
|
-
def to_json(state =
|
|
1554
|
+
def to_json(state = nil)
|
|
1543
1555
|
{ class: :literal, literal: literal.inspect, location: location }.to_json(state)
|
|
1544
1556
|
end
|
|
1545
1557
|
|
|
@@ -192,6 +192,31 @@ module RBS
|
|
|
192
192
|
end
|
|
193
193
|
end
|
|
194
194
|
|
|
195
|
+
ruby2_keywords def assert_send_type_error(method_type, error_type, receiver, method, *args, &block)
|
|
196
|
+
send_setup(method_type, receiver, method, args, block) do |method_type, trace, result, exception|
|
|
197
|
+
typecheck = RBS::Test::TypeCheck.new(
|
|
198
|
+
self_class: receiver.class,
|
|
199
|
+
builder: builder,
|
|
200
|
+
sample_size: 100,
|
|
201
|
+
unchecked_classes: [],
|
|
202
|
+
instance_class: instance_class,
|
|
203
|
+
class_class: class_class
|
|
204
|
+
)
|
|
205
|
+
errors = typecheck.method_call(method, method_type, trace, errors: [])
|
|
206
|
+
|
|
207
|
+
assert_empty errors.map {|x| RBS::Test::Errors.to_string(x) }, "Call trace does not match with given method type: #{trace.inspect}"
|
|
208
|
+
|
|
209
|
+
method_defs = method_defs(method)
|
|
210
|
+
all_errors = method_defs.map {|t| typecheck.method_call(method, t.type, trace, errors: [], annotations: t.each_annotation.to_a) }
|
|
211
|
+
assert all_errors.any? {|es| es.empty? }, "Call trace does not match one of method definitions:\n #{trace.inspect}\n #{method_defs.map(&:type).join(" | ")}"
|
|
212
|
+
|
|
213
|
+
# Use `instnace_of?` instead of `is_a?` as we want to check for _the exact exception class_.
|
|
214
|
+
assert exception.instance_of? error_type
|
|
215
|
+
|
|
216
|
+
result
|
|
217
|
+
end
|
|
218
|
+
end
|
|
219
|
+
|
|
195
220
|
ruby2_keywords def refute_send_type(method_type, receiver, method, *args, &block)
|
|
196
221
|
send_setup(method_type, receiver, method, args, block) do |method_type, trace, result, exception|
|
|
197
222
|
method_type = method_type.update(
|
|
@@ -231,15 +256,17 @@ module RBS
|
|
|
231
256
|
type, definition = target
|
|
232
257
|
|
|
233
258
|
case type
|
|
234
|
-
when Types::ClassInstance
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
259
|
+
when Types::ClassInstance, Types::ClassSingleton
|
|
260
|
+
if type.is_a?(Types::ClassSingleton) && type.args.empty?
|
|
261
|
+
definition.methods[method].defs
|
|
262
|
+
else
|
|
263
|
+
subst = RBS::Substitution.build(definition.type_params, type.args)
|
|
264
|
+
definition.methods[method].defs.map do |type_def|
|
|
265
|
+
type_def.update(
|
|
266
|
+
type: type_def.type.sub(subst)
|
|
267
|
+
)
|
|
268
|
+
end
|
|
240
269
|
end
|
|
241
|
-
when Types::ClassSingleton
|
|
242
|
-
definition.methods[method].defs
|
|
243
270
|
else
|
|
244
271
|
raise
|
|
245
272
|
end
|
|
@@ -296,6 +323,15 @@ module RBS
|
|
|
296
323
|
assert typecheck.value(constant, definition_type), "`#{constant_name}` (#{constant.inspect}) must be compatible with RBS type definition `#{definition_type}`"
|
|
297
324
|
end
|
|
298
325
|
|
|
326
|
+
def assert_visibility(visibility, method)
|
|
327
|
+
_, definition = target
|
|
328
|
+
method_entry = definition.methods[method]
|
|
329
|
+
|
|
330
|
+
assert method_entry, "Method `#{method}` not found in RBS definition"
|
|
331
|
+
assert visibility == method_entry.accessibility,
|
|
332
|
+
"Expected `#{method}` to be #{visibility}, but was #{method_entry.accessibility}"
|
|
333
|
+
end
|
|
334
|
+
|
|
299
335
|
def assert_type(type, value)
|
|
300
336
|
typecheck = RBS::Test::TypeCheck.new(
|
|
301
337
|
self_class: value.class,
|
data/lib/rbs/validator.rb
CHANGED
|
@@ -127,8 +127,8 @@ module RBS
|
|
|
127
127
|
# @type var each_child: ^(Symbol) { (Symbol) -> void } -> void
|
|
128
128
|
each_child = -> (name, &block) do
|
|
129
129
|
if param = params.find {|p| p.name == name }
|
|
130
|
-
|
|
131
|
-
|
|
130
|
+
[param.upper_bound_type, param.lower_bound_type].compact.each do |bound|
|
|
131
|
+
bound.free_variables.each do |tv|
|
|
132
132
|
block[tv]
|
|
133
133
|
end
|
|
134
134
|
end
|
data/lib/rbs/version.rb
CHANGED
|
@@ -0,0 +1,213 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require_relative "serialization_schema"
|
|
4
|
+
|
|
5
|
+
module RBS
|
|
6
|
+
module WASM
|
|
7
|
+
# Rebuilds RBS::AST objects from the binary buffer produced by
|
|
8
|
+
# `rbs_serialize_node` (src/serialize.c), driven by the generated
|
|
9
|
+
# SerializationSchema. This is the pure-Ruby counterpart of the C extension's
|
|
10
|
+
# ast_translation.c, used when the parser runs inside WebAssembly (JRuby).
|
|
11
|
+
#
|
|
12
|
+
# All locations are reconstructed through the public RBS::Location API, so the
|
|
13
|
+
# same code works whether RBS::Location is backed by the C extension (CRuby)
|
|
14
|
+
# or by a pure-Ruby implementation (JRuby).
|
|
15
|
+
class Deserializer
|
|
16
|
+
# Deserialize a buffer produced for a whole signature, returning
|
|
17
|
+
# `[directives, declarations]` to match RBS::Parser._parse_signature.
|
|
18
|
+
def self.deserialize(bytes, buffer)
|
|
19
|
+
new(bytes, buffer).read_node
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
# Deserialize a bare node list (rbs_serialize_node_list), e.g. the result
|
|
23
|
+
# of RBS::Parser._parse_type_params.
|
|
24
|
+
def self.deserialize_node_list(bytes, buffer)
|
|
25
|
+
new(bytes, buffer).read_node_list
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
# Deserialize the token stream produced by rbs_wasm_lex into the
|
|
29
|
+
# [type, location] pairs RBS::Parser._lex returns.
|
|
30
|
+
def self.deserialize_tokens(bytes, buffer)
|
|
31
|
+
new(bytes, buffer).read_tokens
|
|
32
|
+
end
|
|
33
|
+
|
|
34
|
+
def initialize(bytes, buffer)
|
|
35
|
+
@bytes = bytes
|
|
36
|
+
@buffer = buffer
|
|
37
|
+
# Symbols and rbs_string fields (comments, annotations) inherit the
|
|
38
|
+
# source encoding, matching ast_translation.c. String/Integer literal
|
|
39
|
+
# nodes are always UTF-8 (see read_node).
|
|
40
|
+
@encoding = buffer.content.encoding
|
|
41
|
+
@pos = 0
|
|
42
|
+
@class_cache = {} #: Hash[String, untyped]
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
def read_node
|
|
46
|
+
tag = read_u8
|
|
47
|
+
return nil if tag == 0
|
|
48
|
+
return read_string(@encoding).to_sym if tag == SerializationSchema::SYMBOL_TAG
|
|
49
|
+
|
|
50
|
+
entry = SerializationSchema::SCHEMA[tag] or raise "Unknown node tag: #{tag}"
|
|
51
|
+
|
|
52
|
+
case entry[0]
|
|
53
|
+
when :node then read_struct(entry)
|
|
54
|
+
when :bool then read_u8 != 0
|
|
55
|
+
when :integer then read_string(Encoding::UTF_8).to_i
|
|
56
|
+
when :string_value then read_string(Encoding::UTF_8)
|
|
57
|
+
when :record_field then [read_node, read_u8 != 0]
|
|
58
|
+
when :signature then [read_node_list, read_node_list]
|
|
59
|
+
when :namespace then RBS::Namespace[read_node_list, read_u8 != 0]
|
|
60
|
+
when :type_name then RBS::TypeName[read_node, read_node]
|
|
61
|
+
else raise "Unknown schema entry kind: #{entry[0].inspect}"
|
|
62
|
+
end
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
def read_node_list
|
|
66
|
+
Array.new(read_count) { read_node }
|
|
67
|
+
end
|
|
68
|
+
|
|
69
|
+
# The lex stream has no leading count: read records until the buffer is
|
|
70
|
+
# exhausted. Each is a token type name followed by its character range.
|
|
71
|
+
def read_tokens
|
|
72
|
+
tokens = [] #: Array[[ Symbol, Location ]]
|
|
73
|
+
until @pos >= @bytes.bytesize
|
|
74
|
+
type = read_string(Encoding::UTF_8).to_sym
|
|
75
|
+
start_char = read_i32
|
|
76
|
+
end_char = read_i32
|
|
77
|
+
tokens << [type, RBS::Location.new(@buffer, start_char, end_char)]
|
|
78
|
+
end
|
|
79
|
+
tokens
|
|
80
|
+
end
|
|
81
|
+
|
|
82
|
+
private
|
|
83
|
+
|
|
84
|
+
def read_struct(entry)
|
|
85
|
+
_, class_name, expose_location, loc_children, fields, resolve_type_params = entry
|
|
86
|
+
|
|
87
|
+
location = read_location(loc_children) if expose_location
|
|
88
|
+
|
|
89
|
+
kwargs = {} #: Hash[Symbol, untyped]
|
|
90
|
+
(fields || []).each do |name, reader|
|
|
91
|
+
kwargs[name] = read_field(reader)
|
|
92
|
+
end
|
|
93
|
+
|
|
94
|
+
RBS::AST::TypeParam.resolve_variables(kwargs[:type_params]) if resolve_type_params
|
|
95
|
+
|
|
96
|
+
klass = class_for(class_name)
|
|
97
|
+
if expose_location
|
|
98
|
+
klass.new(location: location, **kwargs)
|
|
99
|
+
else
|
|
100
|
+
klass.new(**kwargs)
|
|
101
|
+
end
|
|
102
|
+
end
|
|
103
|
+
|
|
104
|
+
def read_field(reader)
|
|
105
|
+
case reader
|
|
106
|
+
when :node then read_node
|
|
107
|
+
when :node_list then read_node_list
|
|
108
|
+
when :hash then read_hash
|
|
109
|
+
when :string then read_string(@encoding)
|
|
110
|
+
when :bool then read_u8 != 0
|
|
111
|
+
when :location_range then read_location_value
|
|
112
|
+
when :location_range_list then read_location_value_list
|
|
113
|
+
when :attr_ivar_name then read_attr_ivar_name
|
|
114
|
+
else # [:enum, [value_or_nil, ...]]
|
|
115
|
+
reader[1][read_u8]
|
|
116
|
+
end
|
|
117
|
+
end
|
|
118
|
+
|
|
119
|
+
def read_hash
|
|
120
|
+
hash = {} #: Hash[untyped, untyped]
|
|
121
|
+
read_count.times do
|
|
122
|
+
key = read_node
|
|
123
|
+
hash[key] = read_node
|
|
124
|
+
end
|
|
125
|
+
hash
|
|
126
|
+
end
|
|
127
|
+
|
|
128
|
+
# A count of nested items. Each item is at least one byte, so a count that
|
|
129
|
+
# exceeds the bytes remaining signals the cursor has drifted out of sync.
|
|
130
|
+
def read_count
|
|
131
|
+
count = read_u32
|
|
132
|
+
if count > @bytes.bytesize - @pos
|
|
133
|
+
raise "Corrupt buffer: count #{count} exceeds #{@bytes.bytesize - @pos} remaining bytes at offset #{@pos}"
|
|
134
|
+
end
|
|
135
|
+
count
|
|
136
|
+
end
|
|
137
|
+
|
|
138
|
+
# The base location of a node, followed by its named child ranges.
|
|
139
|
+
def read_location(loc_children)
|
|
140
|
+
base = read_range
|
|
141
|
+
children = (loc_children || []).map { |name, required| [name, required, read_range] }
|
|
142
|
+
|
|
143
|
+
return nil unless base
|
|
144
|
+
|
|
145
|
+
location = RBS::Location.new(@buffer, base[0], base[1])
|
|
146
|
+
children.each do |name, required, range|
|
|
147
|
+
if required
|
|
148
|
+
location.add_required_child(name, range[0]...range[1]) if range
|
|
149
|
+
else
|
|
150
|
+
location.add_optional_child(name, range ? (range[0]...range[1]) : nil)
|
|
151
|
+
end
|
|
152
|
+
end
|
|
153
|
+
location
|
|
154
|
+
end
|
|
155
|
+
|
|
156
|
+
# A standalone location range field: nil or an RBS::Location without children.
|
|
157
|
+
def read_location_value
|
|
158
|
+
range = read_range
|
|
159
|
+
range && RBS::Location.new(@buffer, range[0], range[1])
|
|
160
|
+
end
|
|
161
|
+
|
|
162
|
+
def read_location_value_list
|
|
163
|
+
Array.new(read_count) { read_location_value }
|
|
164
|
+
end
|
|
165
|
+
|
|
166
|
+
def read_attr_ivar_name
|
|
167
|
+
case read_u8
|
|
168
|
+
when 0 then nil # inferred instance variable
|
|
169
|
+
when 1 then false # no instance variable
|
|
170
|
+
else read_string(@encoding).to_sym
|
|
171
|
+
end
|
|
172
|
+
end
|
|
173
|
+
|
|
174
|
+
# Reads a presence byte and, when present, the start/end character positions.
|
|
175
|
+
def read_range
|
|
176
|
+
return nil if read_u8 == 0
|
|
177
|
+
|
|
178
|
+
start_char = read_i32
|
|
179
|
+
end_char = read_i32
|
|
180
|
+
[start_char, end_char]
|
|
181
|
+
end
|
|
182
|
+
|
|
183
|
+
def read_u8
|
|
184
|
+
byte = @bytes.getbyte(@pos) or raise "Unexpected end of buffer"
|
|
185
|
+
@pos += 1
|
|
186
|
+
byte
|
|
187
|
+
end
|
|
188
|
+
|
|
189
|
+
def read_u32
|
|
190
|
+
value = @bytes.unpack1("L<", offset: @pos) #: Integer
|
|
191
|
+
@pos += 4
|
|
192
|
+
value
|
|
193
|
+
end
|
|
194
|
+
|
|
195
|
+
def read_i32
|
|
196
|
+
value = @bytes.unpack1("l<", offset: @pos) #: Integer
|
|
197
|
+
@pos += 4
|
|
198
|
+
value
|
|
199
|
+
end
|
|
200
|
+
|
|
201
|
+
def read_string(encoding)
|
|
202
|
+
length = read_u32
|
|
203
|
+
string = @bytes.byteslice(@pos, length) or raise "Unexpected end of buffer"
|
|
204
|
+
@pos += length
|
|
205
|
+
string.force_encoding(encoding)
|
|
206
|
+
end
|
|
207
|
+
|
|
208
|
+
def class_for(name)
|
|
209
|
+
@class_cache[name] ||= Object.const_get(name)
|
|
210
|
+
end
|
|
211
|
+
end
|
|
212
|
+
end
|
|
213
|
+
end
|