jruby-prism-parser 0.23.0.pre.SNAPSHOT-java → 0.24.0-java

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.
data/lib/prism/ffi.rb CHANGED
@@ -119,15 +119,12 @@ module Prism
119
119
 
120
120
  # Initialize a new buffer and yield it to the block. The buffer will be
121
121
  # automatically freed when the block returns.
122
- def self.with(&block)
123
- pointer = FFI::MemoryPointer.new(SIZEOF)
124
-
125
- begin
122
+ def self.with
123
+ FFI::MemoryPointer.new(SIZEOF) do |pointer|
126
124
  raise unless LibRubyParser.pm_buffer_init(pointer)
127
- yield new(pointer)
125
+ return yield new(pointer)
128
126
  ensure
129
127
  LibRubyParser.pm_buffer_free(pointer)
130
- pointer.free
131
128
  end
132
129
  end
133
130
  end
@@ -137,39 +134,47 @@ module Prism
137
134
  class PrismString # :nodoc:
138
135
  SIZEOF = LibRubyParser.pm_string_sizeof
139
136
 
140
- attr_reader :pointer
137
+ attr_reader :pointer, :length
141
138
 
142
- def initialize(pointer)
139
+ def initialize(pointer, length, from_string)
143
140
  @pointer = pointer
144
- end
145
-
146
- def source
147
- LibRubyParser.pm_string_source(pointer)
148
- end
149
-
150
- def length
151
- LibRubyParser.pm_string_length(pointer)
141
+ @length = length
142
+ @from_string = from_string
152
143
  end
153
144
 
154
145
  def read
155
- source.read_string(length)
146
+ raise "should use the original String instead" if @from_string
147
+ @pointer.read_string(@length)
156
148
  end
157
149
 
158
150
  # Yields a pm_string_t pointer to the given block.
159
- def self.with(filepath, &block)
160
- pointer = FFI::MemoryPointer.new(SIZEOF)
161
-
162
- begin
163
- raise TypeError unless filepath.is_a?(String)
151
+ def self.with_string(string)
152
+ raise TypeError unless string.is_a?(String)
153
+
154
+ length = string.bytesize
155
+ # + 1 to never get an address of 0, which pm_parser_init() asserts
156
+ FFI::MemoryPointer.new(:char, length + 1, false) do |pointer|
157
+ pointer.write_string(string)
158
+ # since we have the extra byte we might as well \0-terminate
159
+ pointer.put_char(length, 0)
160
+ return yield new(pointer, length, true)
161
+ end
162
+ end
164
163
 
165
- if LibRubyParser.pm_string_mapped_init(pointer, filepath)
166
- yield new(pointer)
164
+ # Yields a pm_string_t pointer to the given block.
165
+ def self.with_file(filepath)
166
+ raise TypeError unless filepath.is_a?(String)
167
+
168
+ FFI::MemoryPointer.new(SIZEOF) do |pm_string|
169
+ if LibRubyParser.pm_string_mapped_init(pm_string, filepath)
170
+ pointer = LibRubyParser.pm_string_source(pm_string)
171
+ length = LibRubyParser.pm_string_length(pm_string)
172
+ return yield new(pointer, length, false)
167
173
  else
168
174
  raise SystemCallError.new(filepath, FFI.errno)
169
175
  end
170
176
  ensure
171
- LibRubyParser.pm_string_free(pointer)
172
- pointer.free
177
+ LibRubyParser.pm_string_free(pm_string)
173
178
  end
174
179
  end
175
180
  end
@@ -185,52 +190,100 @@ module Prism
185
190
  class << self
186
191
  # Mirror the Prism.dump API by using the serialization API.
187
192
  def dump(code, **options)
188
- LibRubyParser::PrismBuffer.with do |buffer|
189
- LibRubyParser.pm_serialize_parse(buffer.pointer, code, code.bytesize, dump_options(options))
190
- buffer.read
191
- end
193
+ LibRubyParser::PrismString.with_string(code) { |string| dump_common(string, options) }
192
194
  end
193
195
 
194
196
  # Mirror the Prism.dump_file API by using the serialization API.
195
197
  def dump_file(filepath, **options)
196
- LibRubyParser::PrismString.with(filepath) do |string|
197
- dump(string.read, **options, filepath: filepath)
198
- end
198
+ options[:filepath] = filepath
199
+ LibRubyParser::PrismString.with_file(filepath) { |string| dump_common(string, options) }
199
200
  end
200
201
 
201
202
  # Mirror the Prism.lex API by using the serialization API.
202
203
  def lex(code, **options)
203
- LibRubyParser::PrismBuffer.with do |buffer|
204
- LibRubyParser.pm_serialize_lex(buffer.pointer, code, code.bytesize, dump_options(options))
205
- Serialize.load_tokens(Source.new(code), buffer.read)
206
- end
204
+ LibRubyParser::PrismString.with_string(code) { |string| lex_common(string, code, options) }
207
205
  end
208
206
 
209
207
  # Mirror the Prism.lex_file API by using the serialization API.
210
208
  def lex_file(filepath, **options)
211
- LibRubyParser::PrismString.with(filepath) do |string|
212
- lex(string.read, **options, filepath: filepath)
213
- end
209
+ options[:filepath] = filepath
210
+ LibRubyParser::PrismString.with_file(filepath) { |string| lex_common(string, string.read, options) }
214
211
  end
215
212
 
216
213
  # Mirror the Prism.parse API by using the serialization API.
217
214
  def parse(code, **options)
218
- Prism.load(code, dump(code, **options))
215
+ LibRubyParser::PrismString.with_string(code) { |string| parse_common(string, code, options) }
219
216
  end
220
217
 
221
218
  # Mirror the Prism.parse_file API by using the serialization API. This uses
222
219
  # native strings instead of Ruby strings because it allows us to use mmap when
223
220
  # it is available.
224
221
  def parse_file(filepath, **options)
225
- LibRubyParser::PrismString.with(filepath) do |string|
226
- parse(string.read, **options, filepath: filepath)
227
- end
222
+ options[:filepath] = filepath
223
+ LibRubyParser::PrismString.with_file(filepath) { |string| parse_common(string, string.read, options) }
228
224
  end
229
225
 
230
226
  # Mirror the Prism.parse_comments API by using the serialization API.
231
227
  def parse_comments(code, **options)
228
+ LibRubyParser::PrismString.with_string(code) { |string| parse_comments_common(string, code, options) }
229
+ end
230
+
231
+ # Mirror the Prism.parse_file_comments API by using the serialization
232
+ # API. This uses native strings instead of Ruby strings because it allows us
233
+ # to use mmap when it is available.
234
+ def parse_file_comments(filepath, **options)
235
+ options[:filepath] = filepath
236
+ LibRubyParser::PrismString.with_file(filepath) { |string| parse_comments_common(string, string.read, options) }
237
+ end
238
+
239
+ # Mirror the Prism.parse_lex API by using the serialization API.
240
+ def parse_lex(code, **options)
241
+ LibRubyParser::PrismString.with_string(code) { |string| parse_lex_common(string, code, options) }
242
+ end
243
+
244
+ # Mirror the Prism.parse_lex_file API by using the serialization API.
245
+ def parse_lex_file(filepath, **options)
246
+ options[:filepath] = filepath
247
+ LibRubyParser::PrismString.with_file(filepath) { |string| parse_lex_common(string, string.read, options) }
248
+ end
249
+
250
+ # Mirror the Prism.parse_success? API by using the serialization API.
251
+ def parse_success?(code, **options)
252
+ LibRubyParser::PrismString.with_string(code) { |string| parse_file_success_common(string, options) }
253
+ end
254
+
255
+ # Mirror the Prism.parse_file_success? API by using the serialization API.
256
+ def parse_file_success?(filepath, **options)
257
+ options[:filepath] = filepath
258
+ LibRubyParser::PrismString.with_file(filepath) { |string| parse_file_success_common(string, options) }
259
+ end
260
+
261
+ private
262
+
263
+ def dump_common(string, options) # :nodoc:
264
+ LibRubyParser::PrismBuffer.with do |buffer|
265
+ LibRubyParser.pm_serialize_parse(buffer.pointer, string.pointer, string.length, dump_options(options))
266
+ buffer.read
267
+ end
268
+ end
269
+
270
+ def lex_common(string, code, options) # :nodoc:
271
+ serialized = LibRubyParser::PrismBuffer.with do |buffer|
272
+ LibRubyParser.pm_serialize_lex(buffer.pointer, string.pointer, string.length, dump_options(options))
273
+ buffer.read
274
+ end
275
+
276
+ Serialize.load_tokens(Source.new(code), serialized)
277
+ end
278
+
279
+ def parse_common(string, code, options) # :nodoc:
280
+ serialized = dump_common(string, options)
281
+ Prism.load(code, serialized)
282
+ end
283
+
284
+ def parse_comments_common(string, code, options) # :nodoc:
232
285
  LibRubyParser::PrismBuffer.with do |buffer|
233
- LibRubyParser.pm_serialize_parse_comments(buffer.pointer, code, code.bytesize, dump_options(options))
286
+ LibRubyParser.pm_serialize_parse_comments(buffer.pointer, string.pointer, string.length, dump_options(options))
234
287
 
235
288
  source = Source.new(code)
236
289
  loader = Serialize::Loader.new(source, buffer.read)
@@ -242,19 +295,9 @@ module Prism
242
295
  end
243
296
  end
244
297
 
245
- # Mirror the Prism.parse_file_comments API by using the serialization
246
- # API. This uses native strings instead of Ruby strings because it allows us
247
- # to use mmap when it is available.
248
- def parse_file_comments(filepath, **options)
249
- LibRubyParser::PrismString.with(filepath) do |string|
250
- parse_comments(string.read, **options, filepath: filepath)
251
- end
252
- end
253
-
254
- # Mirror the Prism.parse_lex API by using the serialization API.
255
- def parse_lex(code, **options)
298
+ def parse_lex_common(string, code, options) # :nodoc:
256
299
  LibRubyParser::PrismBuffer.with do |buffer|
257
- LibRubyParser.pm_serialize_parse_lex(buffer.pointer, code, code.bytesize, dump_options(options))
300
+ LibRubyParser.pm_serialize_parse_lex(buffer.pointer, string.pointer, string.length, dump_options(options))
258
301
 
259
302
  source = Source.new(code)
260
303
  loader = Serialize::Loader.new(source, buffer.read)
@@ -267,27 +310,10 @@ module Prism
267
310
  end
268
311
  end
269
312
 
270
- # Mirror the Prism.parse_lex_file API by using the serialization API.
271
- def parse_lex_file(filepath, **options)
272
- LibRubyParser::PrismString.with(filepath) do |string|
273
- parse_lex(string.read, **options, filepath: filepath)
274
- end
275
- end
276
-
277
- # Mirror the Prism.parse_success? API by using the serialization API.
278
- def parse_success?(code, **options)
279
- LibRubyParser.pm_parse_success_p(code, code.bytesize, dump_options(options))
280
- end
281
-
282
- # Mirror the Prism.parse_file_success? API by using the serialization API.
283
- def parse_file_success?(filepath, **options)
284
- LibRubyParser::PrismString.with(filepath) do |string|
285
- parse_success?(string.read, **options, filepath: filepath)
286
- end
313
+ def parse_file_success_common(string, options) # :nodoc:
314
+ LibRubyParser.pm_parse_success_p(string.pointer, string.length, dump_options(options))
287
315
  end
288
316
 
289
- private
290
-
291
317
  # Convert the given options into a serialized options string.
292
318
  def dump_options(options)
293
319
  template = +""