msgpack 1.4.2 → 1.7.2
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/ChangeLog +85 -0
- data/README.md +52 -1
- data/ext/java/org/msgpack/jruby/Buffer.java +26 -19
- data/ext/java/org/msgpack/jruby/Decoder.java +29 -21
- data/ext/java/org/msgpack/jruby/Encoder.java +68 -30
- data/ext/java/org/msgpack/jruby/ExtensionRegistry.java +43 -64
- data/ext/java/org/msgpack/jruby/ExtensionValue.java +6 -9
- data/ext/java/org/msgpack/jruby/Factory.java +43 -42
- data/ext/java/org/msgpack/jruby/Packer.java +37 -40
- data/ext/java/org/msgpack/jruby/Unpacker.java +80 -73
- data/ext/msgpack/buffer.c +54 -74
- data/ext/msgpack/buffer.h +21 -18
- data/ext/msgpack/buffer_class.c +161 -52
- data/ext/msgpack/buffer_class.h +1 -0
- data/ext/msgpack/compat.h +0 -99
- data/ext/msgpack/extconf.rb +25 -46
- data/ext/msgpack/factory_class.c +143 -87
- data/ext/msgpack/packer.c +66 -43
- data/ext/msgpack/packer.h +25 -20
- data/ext/msgpack/packer_class.c +102 -130
- data/ext/msgpack/packer_class.h +11 -0
- data/ext/msgpack/packer_ext_registry.c +35 -40
- data/ext/msgpack/packer_ext_registry.h +41 -38
- data/ext/msgpack/rbinit.c +1 -1
- data/ext/msgpack/rmem.c +3 -4
- data/ext/msgpack/sysdep.h +5 -2
- data/ext/msgpack/unpacker.c +126 -108
- data/ext/msgpack/unpacker.h +16 -13
- data/ext/msgpack/unpacker_class.c +86 -126
- data/ext/msgpack/unpacker_class.h +11 -0
- data/ext/msgpack/unpacker_ext_registry.c +40 -28
- data/ext/msgpack/unpacker_ext_registry.h +21 -18
- data/lib/msgpack/bigint.rb +69 -0
- data/lib/msgpack/buffer.rb +9 -0
- data/lib/msgpack/factory.rb +140 -10
- data/lib/msgpack/packer.rb +10 -1
- data/lib/msgpack/symbol.rb +21 -4
- data/lib/msgpack/time.rb +1 -1
- data/lib/msgpack/unpacker.rb +14 -1
- data/lib/msgpack/version.rb +1 -1
- data/lib/msgpack.rb +6 -7
- data/msgpack.gemspec +8 -5
- metadata +37 -82
- data/.gitignore +0 -23
- data/.rubocop.yml +0 -36
- data/.travis.yml +0 -39
- data/Gemfile +0 -9
- data/Rakefile +0 -71
- data/appveyor.yml +0 -18
- data/bench/pack.rb +0 -23
- data/bench/pack_log.rb +0 -33
- data/bench/pack_log_long.rb +0 -65
- data/bench/pack_symbols.rb +0 -28
- data/bench/run.sh +0 -14
- data/bench/run_long.sh +0 -35
- data/bench/run_symbols.sh +0 -26
- data/bench/unpack.rb +0 -21
- data/bench/unpack_log.rb +0 -34
- data/bench/unpack_log_long.rb +0 -67
- data/doclib/msgpack/buffer.rb +0 -193
- data/doclib/msgpack/core_ext.rb +0 -101
- data/doclib/msgpack/error.rb +0 -19
- data/doclib/msgpack/extension_value.rb +0 -9
- data/doclib/msgpack/factory.rb +0 -101
- data/doclib/msgpack/packer.rb +0 -208
- data/doclib/msgpack/time.rb +0 -22
- data/doclib/msgpack/timestamp.rb +0 -44
- data/doclib/msgpack/unpacker.rb +0 -183
- data/doclib/msgpack.rb +0 -87
- data/msgpack.org.md +0 -46
- data/spec/cases.json +0 -1
- data/spec/cases.msg +0 -0
- data/spec/cases_compact.msg +0 -0
- data/spec/cases_spec.rb +0 -39
- data/spec/cruby/buffer_io_spec.rb +0 -255
- data/spec/cruby/buffer_packer.rb +0 -29
- data/spec/cruby/buffer_spec.rb +0 -575
- data/spec/cruby/buffer_unpacker.rb +0 -19
- data/spec/cruby/unpacker_spec.rb +0 -70
- data/spec/ext_value_spec.rb +0 -99
- data/spec/exttypes.rb +0 -51
- data/spec/factory_spec.rb +0 -367
- data/spec/format_spec.rb +0 -301
- data/spec/jruby/benchmarks/shootout_bm.rb +0 -73
- data/spec/jruby/benchmarks/symbolize_keys_bm.rb +0 -25
- data/spec/jruby/unpacker_spec.rb +0 -186
- data/spec/msgpack_spec.rb +0 -214
- data/spec/pack_spec.rb +0 -61
- data/spec/packer_spec.rb +0 -557
- data/spec/random_compat.rb +0 -24
- data/spec/spec_helper.rb +0 -55
- data/spec/timestamp_spec.rb +0 -121
- data/spec/unpack_spec.rb +0 -57
- data/spec/unpacker_spec.rb +0 -819
@@ -21,17 +21,17 @@ import org.jruby.runtime.ThreadContext;
|
|
21
21
|
import org.jruby.anno.JRubyClass;
|
22
22
|
import org.jruby.anno.JRubyMethod;
|
23
23
|
import org.jruby.util.ByteList;
|
24
|
-
import org.jruby.ext.stringio.StringIO;
|
25
24
|
|
26
25
|
import static org.jruby.runtime.Visibility.PRIVATE;
|
27
26
|
|
28
27
|
@JRubyClass(name="MessagePack::Unpacker")
|
29
28
|
public class Unpacker extends RubyObject {
|
30
|
-
private final
|
29
|
+
private static final long serialVersionUID = 8451264671199362492L;
|
30
|
+
private transient final ExtensionRegistry registry;
|
31
31
|
|
32
|
-
private IRubyObject stream;
|
33
|
-
private IRubyObject data;
|
34
|
-
private Decoder decoder;
|
32
|
+
private transient IRubyObject stream;
|
33
|
+
private transient IRubyObject data;
|
34
|
+
private transient Decoder decoder;
|
35
35
|
private final RubyClass underflowErrorClass;
|
36
36
|
private boolean symbolizeKeys;
|
37
37
|
private boolean freeze;
|
@@ -55,51 +55,70 @@ public class Unpacker extends RubyObject {
|
|
55
55
|
|
56
56
|
@JRubyMethod(name = "initialize", optional = 2, visibility = PRIVATE)
|
57
57
|
public IRubyObject initialize(ThreadContext ctx, IRubyObject[] args) {
|
58
|
+
Ruby runtime = ctx.runtime;
|
59
|
+
|
58
60
|
symbolizeKeys = false;
|
59
61
|
allowUnknownExt = false;
|
60
62
|
freeze = false;
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
63
|
+
|
64
|
+
IRubyObject io = null;
|
65
|
+
RubyHash options = null;
|
66
|
+
|
67
|
+
if (args.length >= 1) {
|
68
|
+
io = args[0];
|
69
|
+
}
|
70
|
+
|
71
|
+
if (args.length >= 2 && args[1] != runtime.getNil()) {
|
72
|
+
options = (RubyHash)args[1];
|
73
|
+
}
|
74
|
+
|
75
|
+
if (options == null && io != null && io instanceof RubyHash) {
|
76
|
+
options = (RubyHash)io;
|
77
|
+
io = null;
|
78
|
+
}
|
79
|
+
|
80
|
+
if (options != null) {
|
81
|
+
IRubyObject sk = options.fastARef(runtime.newSymbol("symbolize_keys"));
|
82
|
+
if (sk != null) {
|
83
|
+
symbolizeKeys = sk.isTrue();
|
84
|
+
}
|
85
|
+
IRubyObject f = options.fastARef(runtime.newSymbol("freeze"));
|
86
|
+
if (f != null) {
|
87
|
+
freeze = f.isTrue();
|
76
88
|
}
|
77
|
-
|
78
|
-
|
89
|
+
IRubyObject au = options.fastARef(runtime.newSymbol("allow_unknown_ext"));
|
90
|
+
if (au != null) {
|
91
|
+
allowUnknownExt = au.isTrue();
|
79
92
|
}
|
93
|
+
|
94
|
+
}
|
95
|
+
|
96
|
+
if (io != null && io != runtime.getNil()) {
|
97
|
+
setStream(ctx, io);
|
80
98
|
}
|
99
|
+
|
81
100
|
return this;
|
82
101
|
}
|
83
102
|
|
84
103
|
public static Unpacker newUnpacker(ThreadContext ctx, ExtensionRegistry extRegistry, IRubyObject[] args) {
|
85
|
-
Unpacker unpacker = new Unpacker(ctx.
|
104
|
+
Unpacker unpacker = new Unpacker(ctx.runtime, ctx.runtime.getModule("MessagePack").getClass("Unpacker"), extRegistry);
|
86
105
|
unpacker.initialize(ctx, args);
|
87
106
|
return unpacker;
|
88
107
|
}
|
89
108
|
|
90
109
|
@JRubyMethod(name = "symbolize_keys?")
|
91
110
|
public IRubyObject isSymbolizeKeys(ThreadContext ctx) {
|
92
|
-
return symbolizeKeys ? ctx.
|
111
|
+
return symbolizeKeys ? ctx.runtime.getTrue() : ctx.runtime.getFalse();
|
93
112
|
}
|
94
113
|
|
95
114
|
@JRubyMethod(name = "freeze?")
|
96
115
|
public IRubyObject isFreeze(ThreadContext ctx) {
|
97
|
-
return freeze ? ctx.
|
116
|
+
return freeze ? ctx.runtime.getTrue() : ctx.runtime.getFalse();
|
98
117
|
}
|
99
118
|
|
100
119
|
@JRubyMethod(name = "allow_unknown_ext?")
|
101
120
|
public IRubyObject isAllowUnknownExt(ThreadContext ctx) {
|
102
|
-
return allowUnknownExt ? ctx.
|
121
|
+
return allowUnknownExt ? ctx.runtime.getTrue() : ctx.runtime.getFalse();
|
103
122
|
}
|
104
123
|
|
105
124
|
@JRubyMethod(name = "registered_types_internal", visibility = PRIVATE)
|
@@ -107,37 +126,23 @@ public class Unpacker extends RubyObject {
|
|
107
126
|
return registry.toInternalUnpackerRegistry(ctx);
|
108
127
|
}
|
109
128
|
|
110
|
-
@JRubyMethod(name = "
|
111
|
-
public IRubyObject
|
112
|
-
|
113
|
-
|
114
|
-
|
115
|
-
RubyModule extModule;
|
116
|
-
IRubyObject arg;
|
117
|
-
IRubyObject proc;
|
118
|
-
if (args.length == 1) {
|
119
|
-
if (! block.isGiven()) {
|
120
|
-
throw runtime.newLocalJumpErrorNoBlock();
|
121
|
-
}
|
122
|
-
proc = RubyProc.newProc(runtime, block, block.type);
|
123
|
-
if (proc == null)
|
124
|
-
System.err.println("proc from Block is null");
|
125
|
-
arg = proc;
|
126
|
-
extModule = null;
|
127
|
-
} else if (args.length == 3) {
|
128
|
-
extModule = (RubyModule) args[1];
|
129
|
-
arg = args[2];
|
130
|
-
proc = extModule.method(arg);
|
131
|
-
} else {
|
132
|
-
throw runtime.newArgumentError(String.format("wrong number of arguments (%d for 1 or 3)", 2 + args.length));
|
133
|
-
}
|
129
|
+
@JRubyMethod(name = "register_type_internal", required = 3, visibility = PRIVATE)
|
130
|
+
public IRubyObject registerTypeInternal(ThreadContext ctx, IRubyObject type, IRubyObject mod, IRubyObject proc) {
|
131
|
+
testFrozen("MessagePack::Unpacker");
|
132
|
+
|
133
|
+
Ruby runtime = ctx.runtime;
|
134
134
|
|
135
135
|
long typeId = ((RubyFixnum) type).getLongValue();
|
136
136
|
if (typeId < -128 || typeId > 127) {
|
137
137
|
throw runtime.newRangeError(String.format("integer %d too big to convert to `signed char'", typeId));
|
138
138
|
}
|
139
139
|
|
140
|
-
|
140
|
+
RubyModule extModule = null;
|
141
|
+
if (mod != runtime.getNil()) {
|
142
|
+
extModule = (RubyModule)mod;
|
143
|
+
}
|
144
|
+
|
145
|
+
registry.put(extModule, (int) typeId, false, null, proc);
|
141
146
|
return runtime.getNil();
|
142
147
|
}
|
143
148
|
|
@@ -155,7 +160,7 @@ public class Unpacker extends RubyObject {
|
|
155
160
|
if (limit == -1) {
|
156
161
|
limit = byteList.length() - offset;
|
157
162
|
}
|
158
|
-
Decoder decoder = new Decoder(ctx.
|
163
|
+
Decoder decoder = new Decoder(ctx.runtime, this, byteList.unsafeBytes(), byteList.begin() + offset, limit, symbolizeKeys, freeze, allowUnknownExt);
|
159
164
|
try {
|
160
165
|
data = null;
|
161
166
|
data = decoder.next();
|
@@ -164,13 +169,13 @@ public class Unpacker extends RubyObject {
|
|
164
169
|
throw re;
|
165
170
|
}
|
166
171
|
}
|
167
|
-
return ctx.
|
172
|
+
return ctx.runtime.newFixnum(decoder.offset());
|
168
173
|
}
|
169
174
|
|
170
175
|
@JRubyMethod(name = "data")
|
171
176
|
public IRubyObject getData(ThreadContext ctx) {
|
172
177
|
if (data == null) {
|
173
|
-
return ctx.
|
178
|
+
return ctx.runtime.getNil();
|
174
179
|
} else {
|
175
180
|
return data;
|
176
181
|
}
|
@@ -178,14 +183,14 @@ public class Unpacker extends RubyObject {
|
|
178
183
|
|
179
184
|
@JRubyMethod(name = "finished?")
|
180
185
|
public IRubyObject finished_p(ThreadContext ctx) {
|
181
|
-
return data == null ? ctx.
|
186
|
+
return data == null ? ctx.runtime.getFalse() : ctx.runtime.getTrue();
|
182
187
|
}
|
183
188
|
|
184
189
|
@JRubyMethod(required = 1, name = "feed", alias = { "feed_reference" })
|
185
190
|
public IRubyObject feed(ThreadContext ctx, IRubyObject data) {
|
186
191
|
ByteList byteList = data.asString().getByteList();
|
187
192
|
if (decoder == null) {
|
188
|
-
decoder = new Decoder(ctx.
|
193
|
+
decoder = new Decoder(ctx.runtime, this, byteList.unsafeBytes(), byteList.begin(), byteList.length(), symbolizeKeys, freeze, allowUnknownExt);
|
189
194
|
} else {
|
190
195
|
decoder.feed(byteList.unsafeBytes(), byteList.begin(), byteList.length());
|
191
196
|
}
|
@@ -202,7 +207,7 @@ public class Unpacker extends RubyObject {
|
|
202
207
|
feed(ctx, data);
|
203
208
|
if (block.isGiven()) {
|
204
209
|
each(ctx, block);
|
205
|
-
return ctx.
|
210
|
+
return ctx.runtime.getNil();
|
206
211
|
} else {
|
207
212
|
return callMethod(ctx, "to_enum");
|
208
213
|
}
|
@@ -230,7 +235,7 @@ public class Unpacker extends RubyObject {
|
|
230
235
|
|
231
236
|
@JRubyMethod
|
232
237
|
public IRubyObject fill(ThreadContext ctx) {
|
233
|
-
return ctx.
|
238
|
+
return ctx.runtime.getNil();
|
234
239
|
}
|
235
240
|
|
236
241
|
@JRubyMethod
|
@@ -238,13 +243,13 @@ public class Unpacker extends RubyObject {
|
|
238
243
|
if (decoder != null) {
|
239
244
|
decoder.reset();
|
240
245
|
}
|
241
|
-
return ctx.
|
246
|
+
return ctx.runtime.getNil();
|
242
247
|
}
|
243
248
|
|
244
249
|
@JRubyMethod(name = "read", alias = { "unpack" })
|
245
250
|
public IRubyObject read(ThreadContext ctx) {
|
246
251
|
if (decoder == null) {
|
247
|
-
throw ctx.
|
252
|
+
throw ctx.runtime.newEOFError();
|
248
253
|
}
|
249
254
|
try {
|
250
255
|
return decoder.next();
|
@@ -252,19 +257,19 @@ public class Unpacker extends RubyObject {
|
|
252
257
|
if (re.getException().getType() != underflowErrorClass) {
|
253
258
|
throw re;
|
254
259
|
} else {
|
255
|
-
throw ctx.
|
260
|
+
throw ctx.runtime.newEOFError();
|
256
261
|
}
|
257
262
|
}
|
258
263
|
}
|
259
264
|
|
260
265
|
@JRubyMethod(name = "skip")
|
261
266
|
public IRubyObject skip(ThreadContext ctx) {
|
262
|
-
throw ctx.
|
267
|
+
throw ctx.runtime.newNotImplementedError("Not supported yet in JRuby implementation");
|
263
268
|
}
|
264
269
|
|
265
270
|
@JRubyMethod(name = "skip_nil")
|
266
271
|
public IRubyObject skipNil(ThreadContext ctx) {
|
267
|
-
throw ctx.
|
272
|
+
throw ctx.runtime.newNotImplementedError("Not supported yet in JRuby implementation");
|
268
273
|
}
|
269
274
|
|
270
275
|
@JRubyMethod
|
@@ -276,11 +281,11 @@ public class Unpacker extends RubyObject {
|
|
276
281
|
if (re.getException().getType() != underflowErrorClass) {
|
277
282
|
throw re;
|
278
283
|
} else {
|
279
|
-
throw ctx.
|
284
|
+
throw ctx.runtime.newEOFError();
|
280
285
|
}
|
281
286
|
}
|
282
287
|
}
|
283
|
-
return ctx.
|
288
|
+
return ctx.runtime.getNil();
|
284
289
|
}
|
285
290
|
|
286
291
|
@JRubyMethod
|
@@ -292,17 +297,17 @@ public class Unpacker extends RubyObject {
|
|
292
297
|
if (re.getException().getType() != underflowErrorClass) {
|
293
298
|
throw re;
|
294
299
|
} else {
|
295
|
-
throw ctx.
|
300
|
+
throw ctx.runtime.newEOFError();
|
296
301
|
}
|
297
302
|
}
|
298
303
|
}
|
299
|
-
return ctx.
|
304
|
+
return ctx.runtime.getNil();
|
300
305
|
}
|
301
306
|
|
302
307
|
@JRubyMethod(name = "stream")
|
303
308
|
public IRubyObject getStream(ThreadContext ctx) {
|
304
309
|
if (stream == null) {
|
305
|
-
return ctx.
|
310
|
+
return ctx.runtime.getNil();
|
306
311
|
} else {
|
307
312
|
return stream;
|
308
313
|
}
|
@@ -311,19 +316,21 @@ public class Unpacker extends RubyObject {
|
|
311
316
|
@JRubyMethod(name = "stream=", required = 1)
|
312
317
|
public IRubyObject setStream(ThreadContext ctx, IRubyObject stream) {
|
313
318
|
RubyString str;
|
314
|
-
if (stream instanceof
|
315
|
-
str = stream.callMethod(ctx, "string").asString();
|
316
|
-
} else if (stream instanceof RubyIO) {
|
319
|
+
if (stream instanceof RubyIO) {
|
317
320
|
str = stream.callMethod(ctx, "read").asString();
|
318
321
|
} else if (stream.respondsTo("read")) {
|
319
322
|
str = stream.callMethod(ctx, "read").asString();
|
320
323
|
} else {
|
321
|
-
throw ctx.
|
324
|
+
throw ctx.runtime.newTypeError(stream, "IO");
|
322
325
|
}
|
323
326
|
ByteList byteList = str.getByteList();
|
324
327
|
this.stream = stream;
|
325
328
|
this.decoder = null;
|
326
|
-
this.decoder = new Decoder(ctx.
|
329
|
+
this.decoder = new Decoder(ctx.runtime, this, byteList.unsafeBytes(), byteList.begin(), byteList.length(), symbolizeKeys, freeze, allowUnknownExt);
|
327
330
|
return getStream(ctx);
|
328
331
|
}
|
332
|
+
|
333
|
+
public ExtensionRegistry.ExtensionEntry lookupExtensionByTypeId(int typeId) {
|
334
|
+
return registry.lookupExtensionByTypeId(typeId);
|
335
|
+
}
|
329
336
|
}
|
data/ext/msgpack/buffer.c
CHANGED
@@ -19,21 +19,15 @@
|
|
19
19
|
#include "buffer.h"
|
20
20
|
#include "rmem.h"
|
21
21
|
|
22
|
-
#ifndef HAVE_RB_STR_REPLACE
|
23
|
-
static ID s_replace;
|
24
|
-
#endif
|
25
|
-
|
26
22
|
int msgpack_rb_encindex_utf8;
|
27
23
|
int msgpack_rb_encindex_usascii;
|
28
24
|
int msgpack_rb_encindex_ascii8bit;
|
29
25
|
|
30
26
|
ID s_uminus;
|
31
27
|
|
32
|
-
#ifndef DISABLE_RMEM
|
33
28
|
static msgpack_rmem_t s_rmem;
|
34
|
-
#endif
|
35
29
|
|
36
|
-
void msgpack_buffer_static_init()
|
30
|
+
void msgpack_buffer_static_init(void)
|
37
31
|
{
|
38
32
|
s_uminus = rb_intern("-@");
|
39
33
|
|
@@ -41,20 +35,12 @@ void msgpack_buffer_static_init()
|
|
41
35
|
msgpack_rb_encindex_usascii = rb_usascii_encindex();
|
42
36
|
msgpack_rb_encindex_ascii8bit = rb_ascii8bit_encindex();
|
43
37
|
|
44
|
-
#ifndef DISABLE_RMEM
|
45
38
|
msgpack_rmem_init(&s_rmem);
|
46
|
-
#endif
|
47
|
-
|
48
|
-
#ifndef HAVE_RB_STR_REPLACE
|
49
|
-
s_replace = rb_intern("replace");
|
50
|
-
#endif
|
51
39
|
}
|
52
40
|
|
53
|
-
void msgpack_buffer_static_destroy()
|
41
|
+
void msgpack_buffer_static_destroy(void)
|
54
42
|
{
|
55
|
-
#ifndef DISABLE_RMEM
|
56
43
|
msgpack_rmem_destroy(&s_rmem);
|
57
|
-
#endif
|
58
44
|
}
|
59
45
|
|
60
46
|
void msgpack_buffer_init(msgpack_buffer_t* b)
|
@@ -72,16 +58,16 @@ void msgpack_buffer_init(msgpack_buffer_t* b)
|
|
72
58
|
static void _msgpack_buffer_chunk_destroy(msgpack_buffer_chunk_t* c)
|
73
59
|
{
|
74
60
|
if(c->mem != NULL) {
|
75
|
-
|
76
|
-
|
61
|
+
if(c->rmem) {
|
62
|
+
if(!msgpack_rmem_free(&s_rmem, c->mem)) {
|
63
|
+
rb_bug("Failed to free an rmem pointer, memory leak?");
|
64
|
+
}
|
65
|
+
} else {
|
77
66
|
xfree(c->mem);
|
78
67
|
}
|
79
68
|
/* no needs to update rmem_owner because chunks will not be
|
80
69
|
* free()ed (left in free_list) and thus *rmem_owner is
|
81
70
|
* always valid. */
|
82
|
-
#else
|
83
|
-
xfree(c->mem);
|
84
|
-
#endif
|
85
71
|
}
|
86
72
|
c->first = NULL;
|
87
73
|
c->last = NULL;
|
@@ -108,8 +94,25 @@ void msgpack_buffer_destroy(msgpack_buffer_t* b)
|
|
108
94
|
}
|
109
95
|
}
|
110
96
|
|
111
|
-
|
97
|
+
size_t msgpack_buffer_memsize(const msgpack_buffer_t* b)
|
98
|
+
{
|
99
|
+
size_t memsize = 0;
|
100
|
+
msgpack_buffer_chunk_t* c = b->head;
|
101
|
+
|
102
|
+
while(c) {
|
103
|
+
memsize += sizeof(msgpack_buffer_chunk_t);
|
104
|
+
if(c->mapped_string != NO_MAPPED_STRING) {
|
105
|
+
memsize += (c->last - c->first);
|
106
|
+
}
|
107
|
+
c = c->next;
|
108
|
+
}
|
109
|
+
|
110
|
+
return memsize;
|
111
|
+
}
|
112
|
+
|
113
|
+
void msgpack_buffer_mark(void *ptr)
|
112
114
|
{
|
115
|
+
msgpack_buffer_t* b = ptr;
|
113
116
|
/* head is always available */
|
114
117
|
msgpack_buffer_chunk_t* c = b->head;
|
115
118
|
while(c != &b->tail) {
|
@@ -120,8 +123,6 @@ void msgpack_buffer_mark(msgpack_buffer_t* b)
|
|
120
123
|
|
121
124
|
rb_gc_mark(b->io);
|
122
125
|
rb_gc_mark(b->io_buffer);
|
123
|
-
|
124
|
-
rb_gc_mark(b->owner);
|
125
126
|
}
|
126
127
|
|
127
128
|
bool _msgpack_buffer_shift_chunk(msgpack_buffer_t* b)
|
@@ -158,24 +159,17 @@ size_t msgpack_buffer_read_to_string_nonblock(msgpack_buffer_t* b, VALUE string,
|
|
158
159
|
{
|
159
160
|
size_t avail = msgpack_buffer_top_readable_size(b);
|
160
161
|
|
161
|
-
#ifndef DISABLE_BUFFER_READ_REFERENCE_OPTIMIZE
|
162
162
|
/* optimize */
|
163
163
|
if(length <= avail && RSTRING_LEN(string) == 0 &&
|
164
164
|
b->head->mapped_string != NO_MAPPED_STRING &&
|
165
165
|
length >= b->read_reference_threshold) {
|
166
166
|
VALUE s = _msgpack_buffer_refer_head_mapped_string(b, length);
|
167
|
-
#ifndef HAVE_RB_STR_REPLACE
|
168
|
-
/* TODO MRI 1.8 */
|
169
|
-
rb_funcall(string, s_replace, 1, s);
|
170
|
-
#else
|
171
167
|
rb_str_replace(string, s);
|
172
|
-
#endif
|
173
168
|
/* here doesn't have to call ENCODING_SET because
|
174
169
|
* encoding of s is always ASCII-8BIT */
|
175
170
|
_msgpack_buffer_consumed(b, length);
|
176
171
|
return length;
|
177
172
|
}
|
178
|
-
#endif
|
179
173
|
|
180
174
|
size_t const length_orig = length;
|
181
175
|
|
@@ -257,12 +251,14 @@ bool _msgpack_buffer_read_all2(msgpack_buffer_t* b, char* buffer, size_t length)
|
|
257
251
|
|
258
252
|
static inline msgpack_buffer_chunk_t* _msgpack_buffer_alloc_new_chunk(msgpack_buffer_t* b)
|
259
253
|
{
|
260
|
-
msgpack_buffer_chunk_t*
|
261
|
-
if(
|
262
|
-
|
254
|
+
msgpack_buffer_chunk_t* chunk = b->free_list;
|
255
|
+
if (chunk) {
|
256
|
+
b->free_list = b->free_list->next;
|
257
|
+
} else {
|
258
|
+
chunk = xmalloc(sizeof(msgpack_buffer_chunk_t));
|
263
259
|
}
|
264
|
-
|
265
|
-
return
|
260
|
+
memset(chunk, 0, sizeof(msgpack_buffer_chunk_t));
|
261
|
+
return chunk;
|
266
262
|
}
|
267
263
|
|
268
264
|
static inline void _msgpack_buffer_add_new_chunk(msgpack_buffer_t* b)
|
@@ -288,15 +284,11 @@ static inline void _msgpack_buffer_add_new_chunk(msgpack_buffer_t* b)
|
|
288
284
|
|
289
285
|
msgpack_buffer_chunk_t* nc = _msgpack_buffer_alloc_new_chunk(b);
|
290
286
|
|
291
|
-
#ifndef DISABLE_RMEM
|
292
|
-
#ifndef DISABLE_RMEM_REUSE_INTERNAL_FRAGMENT
|
293
287
|
if(b->rmem_last == b->tail_buffer_end) {
|
294
288
|
/* reuse unused rmem space */
|
295
289
|
size_t unused = b->tail_buffer_end - b->tail.last;
|
296
290
|
b->rmem_last -= unused;
|
297
291
|
}
|
298
|
-
#endif
|
299
|
-
#endif
|
300
292
|
|
301
293
|
/* rebuild tail */
|
302
294
|
*nc = b->tail;
|
@@ -307,8 +299,13 @@ static inline void _msgpack_buffer_add_new_chunk(msgpack_buffer_t* b)
|
|
307
299
|
|
308
300
|
static inline void _msgpack_buffer_append_reference(msgpack_buffer_t* b, VALUE string)
|
309
301
|
{
|
310
|
-
VALUE mapped_string
|
311
|
-
|
302
|
+
VALUE mapped_string;
|
303
|
+
if(ENCODING_GET(string) == msgpack_rb_encindex_ascii8bit && RTEST(rb_obj_frozen_p(string))) {
|
304
|
+
mapped_string = string;
|
305
|
+
} else {
|
306
|
+
mapped_string = rb_str_dup(string);
|
307
|
+
ENCODING_SET(mapped_string, msgpack_rb_encindex_ascii8bit);
|
308
|
+
}
|
312
309
|
|
313
310
|
_msgpack_buffer_add_new_chunk(b);
|
314
311
|
|
@@ -331,24 +328,15 @@ static inline void _msgpack_buffer_append_reference(msgpack_buffer_t* b, VALUE s
|
|
331
328
|
|
332
329
|
void _msgpack_buffer_append_long_string(msgpack_buffer_t* b, VALUE string)
|
333
330
|
{
|
334
|
-
size_t length = RSTRING_LEN(string);
|
335
|
-
|
336
331
|
if(b->io != Qnil) {
|
337
332
|
msgpack_buffer_flush(b);
|
338
333
|
if (ENCODING_GET(string) == msgpack_rb_encindex_ascii8bit) {
|
339
334
|
rb_funcall(b->io, b->io_write_all_method, 1, string);
|
340
|
-
} else if(!STR_DUP_LIKELY_DOES_COPY(string)) {
|
341
|
-
VALUE s = rb_str_dup(string);
|
342
|
-
ENCODING_SET(s, msgpack_rb_encindex_ascii8bit);
|
343
|
-
rb_funcall(b->io, b->io_write_all_method, 1, s);
|
344
335
|
} else {
|
345
|
-
msgpack_buffer_append(b, RSTRING_PTR(string),
|
336
|
+
msgpack_buffer_append(b, RSTRING_PTR(string), RSTRING_LEN(string));
|
346
337
|
}
|
347
|
-
} else if(!STR_DUP_LIKELY_DOES_COPY(string)) {
|
348
|
-
_msgpack_buffer_append_reference(b, string);
|
349
|
-
|
350
338
|
} else {
|
351
|
-
|
339
|
+
_msgpack_buffer_append_reference(b, string);
|
352
340
|
}
|
353
341
|
}
|
354
342
|
|
@@ -356,11 +344,10 @@ static inline void* _msgpack_buffer_chunk_malloc(
|
|
356
344
|
msgpack_buffer_t* b, msgpack_buffer_chunk_t* c,
|
357
345
|
size_t required_size, size_t* allocated_size)
|
358
346
|
{
|
359
|
-
#ifndef DISABLE_RMEM
|
360
347
|
if(required_size <= MSGPACK_RMEM_PAGE_SIZE) {
|
361
|
-
|
348
|
+
c->rmem = true;
|
349
|
+
|
362
350
|
if((size_t)(b->rmem_end - b->rmem_last) < required_size) {
|
363
|
-
#endif
|
364
351
|
/* alloc new rmem page */
|
365
352
|
*allocated_size = MSGPACK_RMEM_PAGE_SIZE;
|
366
353
|
char* buffer = msgpack_rmem_alloc(&s_rmem);
|
@@ -371,8 +358,6 @@ static inline void* _msgpack_buffer_chunk_malloc(
|
|
371
358
|
b->rmem_last = b->rmem_end = buffer + MSGPACK_RMEM_PAGE_SIZE;
|
372
359
|
|
373
360
|
return buffer;
|
374
|
-
|
375
|
-
#ifndef DISABLE_RMEM_REUSE_INTERNAL_FRAGMENT
|
376
361
|
} else {
|
377
362
|
/* reuse unused rmem */
|
378
363
|
*allocated_size = (size_t)(b->rmem_end - b->rmem_last);
|
@@ -386,18 +371,13 @@ static inline void* _msgpack_buffer_chunk_malloc(
|
|
386
371
|
|
387
372
|
return buffer;
|
388
373
|
}
|
389
|
-
#endif
|
390
374
|
}
|
391
|
-
#else
|
392
|
-
if(required_size < 72) {
|
393
|
-
required_size = 72;
|
394
|
-
}
|
395
|
-
#endif
|
396
375
|
|
397
376
|
// TODO alignment?
|
398
377
|
*allocated_size = required_size;
|
399
378
|
void* mem = xmalloc(required_size);
|
400
379
|
c->mem = mem;
|
380
|
+
c->rmem = false;
|
401
381
|
return mem;
|
402
382
|
}
|
403
383
|
|
@@ -447,11 +427,7 @@ void _msgpack_buffer_expand(msgpack_buffer_t* b, const char* data, size_t length
|
|
447
427
|
size_t capacity = b->tail.last - b->tail.first;
|
448
428
|
|
449
429
|
/* can't realloc mapped chunk or rmem page */
|
450
|
-
if(b->tail.mapped_string != NO_MAPPED_STRING
|
451
|
-
#ifndef DISABLE_RMEM
|
452
|
-
|| capacity <= MSGPACK_RMEM_PAGE_SIZE
|
453
|
-
#endif
|
454
|
-
) {
|
430
|
+
if(b->tail.mapped_string != NO_MAPPED_STRING || capacity <= MSGPACK_RMEM_PAGE_SIZE) {
|
455
431
|
/* allocate new chunk */
|
456
432
|
_msgpack_buffer_add_new_chunk(b);
|
457
433
|
|
@@ -624,13 +600,13 @@ size_t msgpack_buffer_flush_to_io(msgpack_buffer_t* b, VALUE io, ID write_method
|
|
624
600
|
size_t _msgpack_buffer_feed_from_io(msgpack_buffer_t* b)
|
625
601
|
{
|
626
602
|
if(b->io_buffer == Qnil) {
|
627
|
-
b->io_buffer = rb_funcall(b->io, b->io_partial_read_method, 1,
|
603
|
+
b->io_buffer = rb_funcall(b->io, b->io_partial_read_method, 1, SIZET2NUM(b->io_buffer_size));
|
628
604
|
if(b->io_buffer == Qnil) {
|
629
605
|
rb_raise(rb_eEOFError, "IO reached end of file");
|
630
606
|
}
|
631
607
|
StringValue(b->io_buffer);
|
632
608
|
} else {
|
633
|
-
VALUE ret = rb_funcall(b->io, b->io_partial_read_method, 2,
|
609
|
+
VALUE ret = rb_funcall(b->io, b->io_partial_read_method, 2, SIZET2NUM(b->io_buffer_size), b->io_buffer);
|
634
610
|
if(ret == Qnil) {
|
635
611
|
rb_raise(rb_eEOFError, "IO reached end of file");
|
636
612
|
}
|
@@ -649,9 +625,11 @@ size_t _msgpack_buffer_feed_from_io(msgpack_buffer_t* b)
|
|
649
625
|
|
650
626
|
size_t _msgpack_buffer_read_from_io_to_string(msgpack_buffer_t* b, VALUE string, size_t length)
|
651
627
|
{
|
628
|
+
#define MIN(x, y) (((x) < (y)) ? (x) : (y))
|
629
|
+
|
652
630
|
if(RSTRING_LEN(string) == 0) {
|
653
631
|
/* direct read */
|
654
|
-
VALUE ret = rb_funcall(b->io, b->io_partial_read_method, 2,
|
632
|
+
VALUE ret = rb_funcall(b->io, b->io_partial_read_method, 2, SIZET2NUM(MIN(b->io_buffer_size, length)), string);
|
655
633
|
if(ret == Qnil) {
|
656
634
|
return 0;
|
657
635
|
}
|
@@ -663,7 +641,7 @@ size_t _msgpack_buffer_read_from_io_to_string(msgpack_buffer_t* b, VALUE string,
|
|
663
641
|
b->io_buffer = rb_str_buf_new(0);
|
664
642
|
}
|
665
643
|
|
666
|
-
VALUE ret = rb_funcall(b->io, b->io_partial_read_method, 2,
|
644
|
+
VALUE ret = rb_funcall(b->io, b->io_partial_read_method, 2, SIZET2NUM(MIN(b->io_buffer_size, length)), b->io_buffer);
|
667
645
|
if(ret == Qnil) {
|
668
646
|
return 0;
|
669
647
|
}
|
@@ -671,6 +649,8 @@ size_t _msgpack_buffer_read_from_io_to_string(msgpack_buffer_t* b, VALUE string,
|
|
671
649
|
|
672
650
|
rb_str_buf_cat(string, (const void*)RSTRING_PTR(b->io_buffer), rl);
|
673
651
|
return rl;
|
652
|
+
|
653
|
+
#undef MIN
|
674
654
|
}
|
675
655
|
|
676
656
|
size_t _msgpack_buffer_skip_from_io(msgpack_buffer_t* b, size_t length)
|
@@ -679,7 +659,7 @@ size_t _msgpack_buffer_skip_from_io(msgpack_buffer_t* b, size_t length)
|
|
679
659
|
b->io_buffer = rb_str_buf_new(0);
|
680
660
|
}
|
681
661
|
|
682
|
-
VALUE ret = rb_funcall(b->io, b->io_partial_read_method, 2,
|
662
|
+
VALUE ret = rb_funcall(b->io, b->io_partial_read_method, 2, SIZET2NUM(length), b->io_buffer);
|
683
663
|
if(ret == Qnil) {
|
684
664
|
return 0;
|
685
665
|
}
|