msgpack 0.6.0pre1-x64-mingw32
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 +7 -0
- data/.gitignore +20 -0
- data/.travis.yml +26 -0
- data/ChangeLog +117 -0
- data/Dockerfile +30 -0
- data/Gemfile +4 -0
- data/LICENSE +177 -0
- data/README.rdoc +129 -0
- data/Rakefile +114 -0
- data/bench/pack.rb +23 -0
- data/bench/pack_log.rb +33 -0
- data/bench/pack_log_long.rb +65 -0
- data/bench/run.sh +14 -0
- data/bench/run_long.sh +35 -0
- data/bench/unpack.rb +21 -0
- data/bench/unpack_log.rb +34 -0
- data/bench/unpack_log_long.rb +67 -0
- data/cross-build.sh +9 -0
- data/doclib/msgpack/buffer.rb +193 -0
- data/doclib/msgpack/core_ext.rb +101 -0
- data/doclib/msgpack/error.rb +14 -0
- data/doclib/msgpack/packer.rb +134 -0
- data/doclib/msgpack/unpacker.rb +146 -0
- data/doclib/msgpack.rb +77 -0
- data/ext/java/org/msgpack/jruby/Buffer.java +221 -0
- data/ext/java/org/msgpack/jruby/Decoder.java +201 -0
- data/ext/java/org/msgpack/jruby/Encoder.java +308 -0
- data/ext/java/org/msgpack/jruby/ExtensionValue.java +136 -0
- data/ext/java/org/msgpack/jruby/MessagePackLibrary.java +107 -0
- data/ext/java/org/msgpack/jruby/Packer.java +78 -0
- data/ext/java/org/msgpack/jruby/Types.java +37 -0
- data/ext/java/org/msgpack/jruby/Unpacker.java +170 -0
- data/ext/msgpack/buffer.c +695 -0
- data/ext/msgpack/buffer.h +447 -0
- data/ext/msgpack/buffer_class.c +507 -0
- data/ext/msgpack/buffer_class.h +32 -0
- data/ext/msgpack/compat.h +113 -0
- data/ext/msgpack/core_ext.c +129 -0
- data/ext/msgpack/core_ext.h +26 -0
- data/ext/msgpack/extconf.rb +28 -0
- data/ext/msgpack/packer.c +168 -0
- data/ext/msgpack/packer.h +441 -0
- data/ext/msgpack/packer_class.c +302 -0
- data/ext/msgpack/packer_class.h +30 -0
- data/ext/msgpack/rbinit.c +33 -0
- data/ext/msgpack/rmem.c +94 -0
- data/ext/msgpack/rmem.h +109 -0
- data/ext/msgpack/sysdep.h +115 -0
- data/ext/msgpack/sysdep_endian.h +50 -0
- data/ext/msgpack/sysdep_types.h +46 -0
- data/ext/msgpack/unpacker.c +771 -0
- data/ext/msgpack/unpacker.h +122 -0
- data/ext/msgpack/unpacker_class.c +405 -0
- data/ext/msgpack/unpacker_class.h +32 -0
- data/lib/msgpack/msgpack.so +0 -0
- data/lib/msgpack/version.rb +3 -0
- data/lib/msgpack.rb +13 -0
- data/msgpack.gemspec +31 -0
- data/msgpack.org.md +46 -0
- data/spec/cases.json +1 -0
- data/spec/cases.msg +0 -0
- data/spec/cases_compact.msg +0 -0
- data/spec/cases_spec.rb +39 -0
- data/spec/cruby/buffer_io_spec.rb +256 -0
- data/spec/cruby/buffer_packer.rb +29 -0
- data/spec/cruby/buffer_spec.rb +572 -0
- data/spec/cruby/buffer_unpacker.rb +19 -0
- data/spec/cruby/packer_spec.rb +120 -0
- data/spec/cruby/unpacker_spec.rb +305 -0
- data/spec/format_spec.rb +282 -0
- data/spec/jruby/benchmarks/shootout_bm.rb +73 -0
- data/spec/jruby/benchmarks/symbolize_keys_bm.rb +25 -0
- data/spec/jruby/msgpack/unpacker_spec.rb +290 -0
- data/spec/jruby/msgpack_spec.rb +142 -0
- data/spec/pack_spec.rb +67 -0
- data/spec/random_compat.rb +24 -0
- data/spec/spec_helper.rb +27 -0
- data/spec/unpack_spec.rb +60 -0
- metadata +209 -0
@@ -0,0 +1,302 @@
|
|
1
|
+
/*
|
2
|
+
* MessagePack for Ruby
|
3
|
+
*
|
4
|
+
* Copyright (C) 2008-2013 Sadayuki Furuhashi
|
5
|
+
*
|
6
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
7
|
+
* you may not use this file except in compliance with the License.
|
8
|
+
* You may obtain a copy of the License at
|
9
|
+
*
|
10
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
11
|
+
*
|
12
|
+
* Unless required by applicable law or agreed to in writing, software
|
13
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
14
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
15
|
+
* See the License for the specific language governing permissions and
|
16
|
+
* limitations under the License.
|
17
|
+
*/
|
18
|
+
|
19
|
+
#include "compat.h"
|
20
|
+
#include "ruby.h"
|
21
|
+
#include "packer.h"
|
22
|
+
#include "packer_class.h"
|
23
|
+
#include "buffer_class.h"
|
24
|
+
|
25
|
+
VALUE cMessagePack_Packer;
|
26
|
+
|
27
|
+
static ID s_to_msgpack;
|
28
|
+
static ID s_write;
|
29
|
+
|
30
|
+
//static VALUE s_packer_value;
|
31
|
+
//static msgpack_packer_t* s_packer;
|
32
|
+
|
33
|
+
#define PACKER(from, name) \
|
34
|
+
msgpack_packer_t* name; \
|
35
|
+
Data_Get_Struct(from, msgpack_packer_t, name); \
|
36
|
+
if(name == NULL) { \
|
37
|
+
rb_raise(rb_eArgError, "NULL found for " # name " when shouldn't be."); \
|
38
|
+
}
|
39
|
+
|
40
|
+
static void Packer_free(msgpack_packer_t* pk)
|
41
|
+
{
|
42
|
+
if(pk == NULL) {
|
43
|
+
return;
|
44
|
+
}
|
45
|
+
msgpack_packer_destroy(pk);
|
46
|
+
free(pk);
|
47
|
+
}
|
48
|
+
|
49
|
+
static VALUE Packer_alloc(VALUE klass)
|
50
|
+
{
|
51
|
+
msgpack_packer_t* pk = ALLOC_N(msgpack_packer_t, 1);
|
52
|
+
msgpack_packer_init(pk);
|
53
|
+
|
54
|
+
VALUE self = Data_Wrap_Struct(klass, msgpack_packer_mark, Packer_free, pk);
|
55
|
+
|
56
|
+
msgpack_packer_set_to_msgpack_method(pk, s_to_msgpack, self);
|
57
|
+
pk->buffer_ref = MessagePack_Buffer_wrap(PACKER_BUFFER_(pk), self);
|
58
|
+
|
59
|
+
return self;
|
60
|
+
}
|
61
|
+
|
62
|
+
static VALUE Packer_initialize(int argc, VALUE* argv, VALUE self)
|
63
|
+
{
|
64
|
+
VALUE io = Qnil;
|
65
|
+
VALUE options = Qnil;
|
66
|
+
|
67
|
+
if(argc == 0 || (argc == 1 && argv[0] == Qnil)) {
|
68
|
+
/* Qnil */
|
69
|
+
|
70
|
+
} else if(argc == 1) {
|
71
|
+
VALUE v = argv[0];
|
72
|
+
if(rb_type(v) == T_HASH) {
|
73
|
+
options = v;
|
74
|
+
} else {
|
75
|
+
io = v;
|
76
|
+
}
|
77
|
+
|
78
|
+
} else if(argc == 2) {
|
79
|
+
io = argv[0];
|
80
|
+
options = argv[1];
|
81
|
+
if(rb_type(options) != T_HASH) {
|
82
|
+
rb_raise(rb_eArgError, "expected Hash but found %s.", rb_obj_classname(options));
|
83
|
+
}
|
84
|
+
|
85
|
+
} else {
|
86
|
+
rb_raise(rb_eArgError, "wrong number of arguments (%d for 0..2)", argc);
|
87
|
+
}
|
88
|
+
|
89
|
+
PACKER(self, pk);
|
90
|
+
MessagePack_Buffer_initialize(PACKER_BUFFER_(pk), io, options);
|
91
|
+
|
92
|
+
// TODO MessagePack_Unpacker_initialize and options
|
93
|
+
|
94
|
+
return self;
|
95
|
+
}
|
96
|
+
|
97
|
+
static VALUE Packer_buffer(VALUE self)
|
98
|
+
{
|
99
|
+
PACKER(self, pk);
|
100
|
+
return pk->buffer_ref;
|
101
|
+
}
|
102
|
+
|
103
|
+
static VALUE Packer_write(VALUE self, VALUE v)
|
104
|
+
{
|
105
|
+
PACKER(self, pk);
|
106
|
+
msgpack_packer_write_value(pk, v);
|
107
|
+
return self;
|
108
|
+
}
|
109
|
+
|
110
|
+
static VALUE Packer_write_nil(VALUE self)
|
111
|
+
{
|
112
|
+
PACKER(self, pk);
|
113
|
+
msgpack_packer_write_nil(pk);
|
114
|
+
return self;
|
115
|
+
}
|
116
|
+
|
117
|
+
static VALUE Packer_write_array_header(VALUE self, VALUE n)
|
118
|
+
{
|
119
|
+
PACKER(self, pk);
|
120
|
+
msgpack_packer_write_array_header(pk, NUM2UINT(n));
|
121
|
+
return self;
|
122
|
+
}
|
123
|
+
|
124
|
+
static VALUE Packer_write_map_header(VALUE self, VALUE n)
|
125
|
+
{
|
126
|
+
PACKER(self, pk);
|
127
|
+
msgpack_packer_write_map_header(pk, NUM2UINT(n));
|
128
|
+
return self;
|
129
|
+
}
|
130
|
+
|
131
|
+
static VALUE Packer_flush(VALUE self)
|
132
|
+
{
|
133
|
+
PACKER(self, pk);
|
134
|
+
msgpack_buffer_flush(PACKER_BUFFER_(pk));
|
135
|
+
return self;
|
136
|
+
}
|
137
|
+
|
138
|
+
static VALUE Packer_clear(VALUE self)
|
139
|
+
{
|
140
|
+
PACKER(self, pk);
|
141
|
+
msgpack_buffer_clear(PACKER_BUFFER_(pk));
|
142
|
+
return Qnil;
|
143
|
+
}
|
144
|
+
|
145
|
+
static VALUE Packer_size(VALUE self)
|
146
|
+
{
|
147
|
+
PACKER(self, pk);
|
148
|
+
size_t size = msgpack_buffer_all_readable_size(PACKER_BUFFER_(pk));
|
149
|
+
return SIZET2NUM(size);
|
150
|
+
}
|
151
|
+
|
152
|
+
static VALUE Packer_empty_p(VALUE self)
|
153
|
+
{
|
154
|
+
PACKER(self, pk);
|
155
|
+
if(msgpack_buffer_top_readable_size(PACKER_BUFFER_(pk)) == 0) {
|
156
|
+
return Qtrue;
|
157
|
+
} else {
|
158
|
+
return Qfalse;
|
159
|
+
}
|
160
|
+
}
|
161
|
+
|
162
|
+
static VALUE Packer_to_str(VALUE self)
|
163
|
+
{
|
164
|
+
PACKER(self, pk);
|
165
|
+
return msgpack_buffer_all_as_string(PACKER_BUFFER_(pk));
|
166
|
+
}
|
167
|
+
|
168
|
+
static VALUE Packer_to_a(VALUE self)
|
169
|
+
{
|
170
|
+
PACKER(self, pk);
|
171
|
+
return msgpack_buffer_all_as_string_array(PACKER_BUFFER_(pk));
|
172
|
+
}
|
173
|
+
|
174
|
+
static VALUE Packer_write_to(VALUE self, VALUE io)
|
175
|
+
{
|
176
|
+
PACKER(self, pk);
|
177
|
+
size_t sz = msgpack_buffer_flush_to_io(PACKER_BUFFER_(pk), io, s_write, true);
|
178
|
+
return ULONG2NUM(sz);
|
179
|
+
}
|
180
|
+
|
181
|
+
//static VALUE Packer_append(VALUE self, VALUE string_or_buffer)
|
182
|
+
//{
|
183
|
+
// PACKER(self, pk);
|
184
|
+
//
|
185
|
+
// // TODO if string_or_buffer is a Buffer
|
186
|
+
// VALUE string = string_or_buffer;
|
187
|
+
//
|
188
|
+
// msgpack_buffer_append_string(PACKER_BUFFER_(pk), string);
|
189
|
+
//
|
190
|
+
// return self;
|
191
|
+
//}
|
192
|
+
|
193
|
+
VALUE MessagePack_pack(int argc, VALUE* argv)
|
194
|
+
{
|
195
|
+
VALUE v;
|
196
|
+
VALUE io = Qnil;
|
197
|
+
VALUE options = Qnil;
|
198
|
+
|
199
|
+
if(argc == 1) {
|
200
|
+
v = argv[0];
|
201
|
+
|
202
|
+
} else if(argc == 2) {
|
203
|
+
v = argv[0];
|
204
|
+
if(rb_type(argv[1]) == T_HASH) {
|
205
|
+
options = argv[1];
|
206
|
+
} else {
|
207
|
+
io = argv[1];
|
208
|
+
}
|
209
|
+
|
210
|
+
} else if(argc == 3) {
|
211
|
+
v = argv[0];
|
212
|
+
io = argv[1];
|
213
|
+
options = argv[2];
|
214
|
+
if(rb_type(options) != T_HASH) {
|
215
|
+
rb_raise(rb_eArgError, "expected Hash but found %s.", rb_obj_classname(options));
|
216
|
+
}
|
217
|
+
|
218
|
+
} else {
|
219
|
+
rb_raise(rb_eArgError, "wrong number of arguments (%d for 1..3)", argc);
|
220
|
+
}
|
221
|
+
|
222
|
+
VALUE self = Packer_alloc(cMessagePack_Packer);
|
223
|
+
PACKER(self, pk);
|
224
|
+
//msgpack_packer_reset(s_packer);
|
225
|
+
//msgpack_buffer_reset_io(PACKER_BUFFER_(s_packer));
|
226
|
+
|
227
|
+
MessagePack_Buffer_initialize(PACKER_BUFFER_(pk), io, options);
|
228
|
+
// TODO MessagePack_Unpacker_initialize and options
|
229
|
+
|
230
|
+
msgpack_packer_write_value(pk, v);
|
231
|
+
|
232
|
+
VALUE retval;
|
233
|
+
if(io != Qnil) {
|
234
|
+
msgpack_buffer_flush(PACKER_BUFFER_(pk));
|
235
|
+
retval = Qnil;
|
236
|
+
} else {
|
237
|
+
retval = msgpack_buffer_all_as_string(PACKER_BUFFER_(pk));
|
238
|
+
}
|
239
|
+
|
240
|
+
msgpack_buffer_clear(PACKER_BUFFER_(pk)); /* to free rmem before GC */
|
241
|
+
|
242
|
+
#ifdef RB_GC_GUARD
|
243
|
+
/* This prevents compilers from optimizing out the `self` variable
|
244
|
+
* from stack. Otherwise GC free()s it. */
|
245
|
+
RB_GC_GUARD(self);
|
246
|
+
#endif
|
247
|
+
|
248
|
+
return retval;
|
249
|
+
}
|
250
|
+
|
251
|
+
static VALUE MessagePack_dump_module_method(int argc, VALUE* argv, VALUE mod)
|
252
|
+
{
|
253
|
+
UNUSED(mod);
|
254
|
+
return MessagePack_pack(argc, argv);
|
255
|
+
}
|
256
|
+
|
257
|
+
static VALUE MessagePack_pack_module_method(int argc, VALUE* argv, VALUE mod)
|
258
|
+
{
|
259
|
+
UNUSED(mod);
|
260
|
+
return MessagePack_pack(argc, argv);
|
261
|
+
}
|
262
|
+
|
263
|
+
void MessagePack_Packer_module_init(VALUE mMessagePack)
|
264
|
+
{
|
265
|
+
s_to_msgpack = rb_intern("to_msgpack");
|
266
|
+
s_write = rb_intern("write");
|
267
|
+
|
268
|
+
msgpack_packer_static_init();
|
269
|
+
|
270
|
+
cMessagePack_Packer = rb_define_class_under(mMessagePack, "Packer", rb_cObject);
|
271
|
+
|
272
|
+
rb_define_alloc_func(cMessagePack_Packer, Packer_alloc);
|
273
|
+
|
274
|
+
rb_define_method(cMessagePack_Packer, "initialize", Packer_initialize, -1);
|
275
|
+
rb_define_method(cMessagePack_Packer, "buffer", Packer_buffer, 0);
|
276
|
+
rb_define_method(cMessagePack_Packer, "write", Packer_write, 1);
|
277
|
+
rb_define_alias(cMessagePack_Packer, "pack", "write");
|
278
|
+
rb_define_method(cMessagePack_Packer, "write_nil", Packer_write_nil, 0);
|
279
|
+
rb_define_method(cMessagePack_Packer, "write_array_header", Packer_write_array_header, 1);
|
280
|
+
rb_define_method(cMessagePack_Packer, "write_map_header", Packer_write_map_header, 1);
|
281
|
+
rb_define_method(cMessagePack_Packer, "flush", Packer_flush, 0);
|
282
|
+
|
283
|
+
/* delegation methods */
|
284
|
+
rb_define_method(cMessagePack_Packer, "clear", Packer_clear, 0);
|
285
|
+
rb_define_method(cMessagePack_Packer, "size", Packer_size, 0);
|
286
|
+
rb_define_method(cMessagePack_Packer, "empty?", Packer_empty_p, 0);
|
287
|
+
rb_define_method(cMessagePack_Packer, "write_to", Packer_write_to, 1);
|
288
|
+
rb_define_method(cMessagePack_Packer, "to_str", Packer_to_str, 0);
|
289
|
+
rb_define_alias(cMessagePack_Packer, "to_s", "to_str");
|
290
|
+
rb_define_method(cMessagePack_Packer, "to_a", Packer_to_a, 0);
|
291
|
+
//rb_define_method(cMessagePack_Packer, "append", Packer_append, 1);
|
292
|
+
//rb_define_alias(cMessagePack_Packer, "<<", "append");
|
293
|
+
|
294
|
+
//s_packer_value = Packer_alloc(cMessagePack_Packer);
|
295
|
+
//rb_gc_register_address(&s_packer_value);
|
296
|
+
//Data_Get_Struct(s_packer_value, msgpack_packer_t, s_packer);
|
297
|
+
|
298
|
+
/* MessagePack.pack(x) */
|
299
|
+
rb_define_module_function(mMessagePack, "pack", MessagePack_pack_module_method, -1);
|
300
|
+
rb_define_module_function(mMessagePack, "dump", MessagePack_dump_module_method, -1);
|
301
|
+
}
|
302
|
+
|
@@ -0,0 +1,30 @@
|
|
1
|
+
/*
|
2
|
+
* MessagePack for Ruby
|
3
|
+
*
|
4
|
+
* Copyright (C) 2008-2013 Sadayuki Furuhashi
|
5
|
+
*
|
6
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
7
|
+
* you may not use this file except in compliance with the License.
|
8
|
+
* You may obtain a copy of the License at
|
9
|
+
*
|
10
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
11
|
+
*
|
12
|
+
* Unless required by applicable law or agreed to in writing, software
|
13
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
14
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
15
|
+
* See the License for the specific language governing permissions and
|
16
|
+
* limitations under the License.
|
17
|
+
*/
|
18
|
+
#ifndef MSGPACK_RUBY_PACKER_CLASS_H__
|
19
|
+
#define MSGPACK_RUBY_PACKER_CLASS_H__
|
20
|
+
|
21
|
+
#include "packer.h"
|
22
|
+
|
23
|
+
extern VALUE cMessagePack_Packer;
|
24
|
+
|
25
|
+
void MessagePack_Packer_module_init(VALUE mMessagePack);
|
26
|
+
|
27
|
+
VALUE MessagePack_pack(int argc, VALUE* argv);
|
28
|
+
|
29
|
+
#endif
|
30
|
+
|
@@ -0,0 +1,33 @@
|
|
1
|
+
/*
|
2
|
+
* MessagePack for Ruby
|
3
|
+
*
|
4
|
+
* Copyright (C) 2008-2013 Sadayuki Furuhashi
|
5
|
+
*
|
6
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
7
|
+
* you may not use this file except in compliance with the License.
|
8
|
+
* You may obtain a copy of the License at
|
9
|
+
*
|
10
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
11
|
+
*
|
12
|
+
* Unless required by applicable law or agreed to in writing, software
|
13
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
14
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
15
|
+
* See the License for the specific language governing permissions and
|
16
|
+
* limitations under the License.
|
17
|
+
*/
|
18
|
+
|
19
|
+
#include "buffer_class.h"
|
20
|
+
#include "packer_class.h"
|
21
|
+
#include "unpacker_class.h"
|
22
|
+
#include "core_ext.h"
|
23
|
+
|
24
|
+
void Init_msgpack(void)
|
25
|
+
{
|
26
|
+
VALUE mMessagePack = rb_define_module("MessagePack");
|
27
|
+
|
28
|
+
MessagePack_Buffer_module_init(mMessagePack);
|
29
|
+
MessagePack_Packer_module_init(mMessagePack);
|
30
|
+
MessagePack_Unpacker_module_init(mMessagePack);
|
31
|
+
MessagePack_core_ext_module_init();
|
32
|
+
}
|
33
|
+
|
data/ext/msgpack/rmem.c
ADDED
@@ -0,0 +1,94 @@
|
|
1
|
+
/*
|
2
|
+
* MessagePack for Ruby
|
3
|
+
*
|
4
|
+
* Copyright (C) 2008-2013 Sadayuki Furuhashi
|
5
|
+
*
|
6
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
7
|
+
* you may not use this file except in compliance with the License.
|
8
|
+
* You may obtain a copy of the License at
|
9
|
+
*
|
10
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
11
|
+
*
|
12
|
+
* Unless required by applicable law or agreed to in writing, software
|
13
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
14
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
15
|
+
* See the License for the specific language governing permissions and
|
16
|
+
* limitations under the License.
|
17
|
+
*/
|
18
|
+
|
19
|
+
#include "rmem.h"
|
20
|
+
|
21
|
+
void msgpack_rmem_init(msgpack_rmem_t* pm)
|
22
|
+
{
|
23
|
+
memset(pm, 0, sizeof(msgpack_rmem_t));
|
24
|
+
pm->head.pages = malloc(MSGPACK_RMEM_PAGE_SIZE * 32);
|
25
|
+
pm->head.mask = 0xffffffff; /* all bit is 1 = available */
|
26
|
+
}
|
27
|
+
|
28
|
+
void msgpack_rmem_destroy(msgpack_rmem_t* pm)
|
29
|
+
{
|
30
|
+
msgpack_rmem_chunk_t* c = pm->array_first;
|
31
|
+
msgpack_rmem_chunk_t* cend = pm->array_last;
|
32
|
+
for(; c != cend; c++) {
|
33
|
+
free(c->pages);
|
34
|
+
}
|
35
|
+
free(pm->head.pages);
|
36
|
+
free(pm->array_first);
|
37
|
+
}
|
38
|
+
|
39
|
+
void* _msgpack_rmem_alloc2(msgpack_rmem_t* pm)
|
40
|
+
{
|
41
|
+
msgpack_rmem_chunk_t* c = pm->array_first;
|
42
|
+
msgpack_rmem_chunk_t* last = pm->array_last;
|
43
|
+
for(; c != last; c++) {
|
44
|
+
if(_msgpack_rmem_chunk_available(c)) {
|
45
|
+
void* mem = _msgpack_rmem_chunk_alloc(c);
|
46
|
+
|
47
|
+
/* move to head */
|
48
|
+
msgpack_rmem_chunk_t tmp = pm->head;
|
49
|
+
pm->head = *c;
|
50
|
+
*c = tmp;
|
51
|
+
return mem;
|
52
|
+
}
|
53
|
+
}
|
54
|
+
|
55
|
+
if(c == pm->array_end) {
|
56
|
+
size_t capacity = c - pm->array_first;
|
57
|
+
size_t length = last - pm->array_first;
|
58
|
+
capacity = (capacity == 0) ? 8 : capacity * 2;
|
59
|
+
msgpack_rmem_chunk_t* array = realloc(pm->array_first, capacity * sizeof(msgpack_rmem_chunk_t));
|
60
|
+
pm->array_first = array;
|
61
|
+
pm->array_last = array + length;
|
62
|
+
pm->array_end = array + capacity;
|
63
|
+
}
|
64
|
+
|
65
|
+
/* allocate new chunk */
|
66
|
+
c = pm->array_last++;
|
67
|
+
|
68
|
+
/* move to head */
|
69
|
+
msgpack_rmem_chunk_t tmp = pm->head;
|
70
|
+
pm->head = *c;
|
71
|
+
*c = tmp;
|
72
|
+
|
73
|
+
pm->head.mask = 0xffffffff & (~1); /* "& (~1)" means first chunk is already allocated */
|
74
|
+
pm->head.pages = malloc(MSGPACK_RMEM_PAGE_SIZE * 32);
|
75
|
+
|
76
|
+
return pm->head.pages;
|
77
|
+
}
|
78
|
+
|
79
|
+
void _msgpack_rmem_chunk_free(msgpack_rmem_t* pm, msgpack_rmem_chunk_t* c)
|
80
|
+
{
|
81
|
+
if(pm->array_first->mask == 0xffffffff) {
|
82
|
+
/* free and move to last */
|
83
|
+
pm->array_last--;
|
84
|
+
free(c->pages);
|
85
|
+
*c = *pm->array_last;
|
86
|
+
return;
|
87
|
+
}
|
88
|
+
|
89
|
+
/* move to first */
|
90
|
+
msgpack_rmem_chunk_t tmp = *pm->array_first;
|
91
|
+
*pm->array_first = *c;
|
92
|
+
*c = tmp;
|
93
|
+
}
|
94
|
+
|
data/ext/msgpack/rmem.h
ADDED
@@ -0,0 +1,109 @@
|
|
1
|
+
/*
|
2
|
+
* MessagePack for Ruby
|
3
|
+
*
|
4
|
+
* Copyright (C) 2008-2013 Sadayuki Furuhashi
|
5
|
+
*
|
6
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
7
|
+
* you may not use this file except in compliance with the License.
|
8
|
+
* You may obtain a copy of the License at
|
9
|
+
*
|
10
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
11
|
+
*
|
12
|
+
* Unless required by applicable law or agreed to in writing, software
|
13
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
14
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
15
|
+
* See the License for the specific language governing permissions and
|
16
|
+
* limitations under the License.
|
17
|
+
*/
|
18
|
+
#ifndef MSGPACK_RUBY_RMEM_H__
|
19
|
+
#define MSGPACK_RUBY_RMEM_H__
|
20
|
+
|
21
|
+
#include "compat.h"
|
22
|
+
#include "sysdep.h"
|
23
|
+
|
24
|
+
#ifndef MSGPACK_RMEM_PAGE_SIZE
|
25
|
+
#define MSGPACK_RMEM_PAGE_SIZE (4*1024)
|
26
|
+
#endif
|
27
|
+
|
28
|
+
struct msgpack_rmem_t;
|
29
|
+
typedef struct msgpack_rmem_t msgpack_rmem_t;
|
30
|
+
|
31
|
+
struct msgpack_rmem_chunk_t;
|
32
|
+
typedef struct msgpack_rmem_chunk_t msgpack_rmem_chunk_t;
|
33
|
+
|
34
|
+
/*
|
35
|
+
* a chunk contains 32 pages.
|
36
|
+
* size of each buffer is MSGPACK_RMEM_PAGE_SIZE bytes.
|
37
|
+
*/
|
38
|
+
struct msgpack_rmem_chunk_t {
|
39
|
+
unsigned int mask;
|
40
|
+
char* pages;
|
41
|
+
};
|
42
|
+
|
43
|
+
struct msgpack_rmem_t {
|
44
|
+
msgpack_rmem_chunk_t head;
|
45
|
+
msgpack_rmem_chunk_t* array_first;
|
46
|
+
msgpack_rmem_chunk_t* array_last;
|
47
|
+
msgpack_rmem_chunk_t* array_end;
|
48
|
+
};
|
49
|
+
|
50
|
+
/* assert MSGPACK_RMEM_PAGE_SIZE % sysconf(_SC_PAGE_SIZE) == 0 */
|
51
|
+
void msgpack_rmem_init(msgpack_rmem_t* pm);
|
52
|
+
|
53
|
+
void msgpack_rmem_destroy(msgpack_rmem_t* pm);
|
54
|
+
|
55
|
+
void* _msgpack_rmem_alloc2(msgpack_rmem_t* pm);
|
56
|
+
|
57
|
+
#define _msgpack_rmem_chunk_available(c) ((c)->mask != 0)
|
58
|
+
|
59
|
+
static inline void* _msgpack_rmem_chunk_alloc(msgpack_rmem_chunk_t* c)
|
60
|
+
{
|
61
|
+
_msgpack_bsp32(pos, c->mask);
|
62
|
+
(c)->mask &= ~(1 << pos);
|
63
|
+
return ((char*)(c)->pages) + (pos * (MSGPACK_RMEM_PAGE_SIZE));
|
64
|
+
}
|
65
|
+
|
66
|
+
static inline bool _msgpack_rmem_chunk_try_free(msgpack_rmem_chunk_t* c, void* mem)
|
67
|
+
{
|
68
|
+
ptrdiff_t pdiff = ((char*)(mem)) - ((char*)(c)->pages);
|
69
|
+
if(0 <= pdiff && pdiff < MSGPACK_RMEM_PAGE_SIZE * 32) {
|
70
|
+
size_t pos = pdiff / MSGPACK_RMEM_PAGE_SIZE;
|
71
|
+
(c)->mask |= (1 << pos);
|
72
|
+
return true;
|
73
|
+
}
|
74
|
+
return false;
|
75
|
+
}
|
76
|
+
|
77
|
+
static inline void* msgpack_rmem_alloc(msgpack_rmem_t* pm)
|
78
|
+
{
|
79
|
+
if(_msgpack_rmem_chunk_available(&pm->head)) {
|
80
|
+
return _msgpack_rmem_chunk_alloc(&pm->head);
|
81
|
+
}
|
82
|
+
return _msgpack_rmem_alloc2(pm);
|
83
|
+
}
|
84
|
+
|
85
|
+
void _msgpack_rmem_chunk_free(msgpack_rmem_t* pm, msgpack_rmem_chunk_t* c);
|
86
|
+
|
87
|
+
static inline bool msgpack_rmem_free(msgpack_rmem_t* pm, void* mem)
|
88
|
+
{
|
89
|
+
if(_msgpack_rmem_chunk_try_free(&pm->head, mem)) {
|
90
|
+
return true;
|
91
|
+
}
|
92
|
+
|
93
|
+
/* search from last */
|
94
|
+
msgpack_rmem_chunk_t* c = pm->array_last - 1;
|
95
|
+
msgpack_rmem_chunk_t* before_first = pm->array_first - 1;
|
96
|
+
for(; c != before_first; c--) {
|
97
|
+
if(_msgpack_rmem_chunk_try_free(c, mem)) {
|
98
|
+
if(c != pm->array_first && c->mask == 0xffffffff) {
|
99
|
+
_msgpack_rmem_chunk_free(pm, c);
|
100
|
+
}
|
101
|
+
return true;
|
102
|
+
}
|
103
|
+
}
|
104
|
+
return false;
|
105
|
+
}
|
106
|
+
|
107
|
+
|
108
|
+
#endif
|
109
|
+
|
@@ -0,0 +1,115 @@
|
|
1
|
+
/*
|
2
|
+
* MessagePack for Ruby
|
3
|
+
*
|
4
|
+
* Copyright (C) 2008-2013 Sadayuki Furuhashi
|
5
|
+
*
|
6
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
7
|
+
* you may not use this file except in compliance with the License.
|
8
|
+
* You may obtain a copy of the License at
|
9
|
+
*
|
10
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
11
|
+
*
|
12
|
+
* Unless required by applicable law or agreed to in writing, software
|
13
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
14
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
15
|
+
* See the License for the specific language governing permissions and
|
16
|
+
* limitations under the License.
|
17
|
+
*/
|
18
|
+
#ifndef MSGPACK_RUBY_SYSDEP_H__
|
19
|
+
#define MSGPACK_RUBY_SYSDEP_H__
|
20
|
+
|
21
|
+
#include "sysdep_types.h"
|
22
|
+
#include "sysdep_endian.h"
|
23
|
+
|
24
|
+
|
25
|
+
#define UNUSED(var) ((void)var)
|
26
|
+
|
27
|
+
|
28
|
+
#ifdef __LITTLE_ENDIAN__
|
29
|
+
|
30
|
+
/* _msgpack_be16 */
|
31
|
+
#ifdef _WIN32
|
32
|
+
# if defined(ntohs)
|
33
|
+
# define _msgpack_be16(x) ntohs(x)
|
34
|
+
# elif defined(_byteswap_ushort) || (defined(_MSC_VER) && _MSC_VER >= 1400)
|
35
|
+
# define _msgpack_be16(x) ((uint16_t)_byteswap_ushort((unsigned short)x))
|
36
|
+
# else
|
37
|
+
# define _msgpack_be16(x) ( \
|
38
|
+
((((uint16_t)x) << 8) ) | \
|
39
|
+
((((uint16_t)x) >> 8) ) )
|
40
|
+
# endif
|
41
|
+
#else
|
42
|
+
# define _msgpack_be16(x) ntohs(x)
|
43
|
+
#endif
|
44
|
+
|
45
|
+
/* _msgpack_be32 */
|
46
|
+
#ifdef _WIN32
|
47
|
+
# if defined(ntohl)
|
48
|
+
# define _msgpack_be32(x) ntohl(x)
|
49
|
+
# elif defined(_byteswap_ulong) || (defined(_MSC_VER) && _MSC_VER >= 1400)
|
50
|
+
# define _msgpack_be32(x) ((uint32_t)_byteswap_ulong((unsigned long)x))
|
51
|
+
# else
|
52
|
+
# define _msgpack_be32(x) \
|
53
|
+
( ((((uint32_t)x) << 24) ) | \
|
54
|
+
((((uint32_t)x) << 8) & 0x00ff0000U ) | \
|
55
|
+
((((uint32_t)x) >> 8) & 0x0000ff00U ) | \
|
56
|
+
((((uint32_t)x) >> 24) ) )
|
57
|
+
# endif
|
58
|
+
#else
|
59
|
+
# define _msgpack_be32(x) ntohl(x)
|
60
|
+
#endif
|
61
|
+
|
62
|
+
/* _msgpack_be64 */
|
63
|
+
#if defined(_byteswap_uint64) || (defined(_MSC_VER) && _MSC_VER >= 1400)
|
64
|
+
# define _msgpack_be64(x) (_byteswap_uint64(x))
|
65
|
+
#elif defined(bswap_64)
|
66
|
+
# define _msgpack_be64(x) bswap_64(x)
|
67
|
+
#elif defined(__DARWIN_OSSwapInt64)
|
68
|
+
# define _msgpack_be64(x) __DARWIN_OSSwapInt64(x)
|
69
|
+
#else
|
70
|
+
#define _msgpack_be64(x) \
|
71
|
+
( ((((uint64_t)x) << 56) ) | \
|
72
|
+
((((uint64_t)x) << 40) & 0x00ff000000000000ULL ) | \
|
73
|
+
((((uint64_t)x) << 24) & 0x0000ff0000000000ULL ) | \
|
74
|
+
((((uint64_t)x) << 8) & 0x000000ff00000000ULL ) | \
|
75
|
+
((((uint64_t)x) >> 8) & 0x00000000ff000000ULL ) | \
|
76
|
+
((((uint64_t)x) >> 24) & 0x0000000000ff0000ULL ) | \
|
77
|
+
((((uint64_t)x) >> 40) & 0x000000000000ff00ULL ) | \
|
78
|
+
((((uint64_t)x) >> 56) ) )
|
79
|
+
#endif
|
80
|
+
|
81
|
+
#else /* big endian */
|
82
|
+
#define _msgpack_be16(x) (x)
|
83
|
+
#define _msgpack_be32(x) (x)
|
84
|
+
#define _msgpack_be64(x) (x)
|
85
|
+
|
86
|
+
#endif
|
87
|
+
|
88
|
+
|
89
|
+
/* _msgpack_be_float */
|
90
|
+
#define _msgpack_be_float(x) _msgpack_be32(x)
|
91
|
+
|
92
|
+
/* _msgpack_be_double */
|
93
|
+
#if defined(__arm__) && !(__ARM_EABI__)
|
94
|
+
/* ARM OABI */
|
95
|
+
#define _msgpack_be_double(x) \
|
96
|
+
( (((x) & 0xFFFFFFFFUL) << 32UL) | ((x) >> 32UL) )
|
97
|
+
#else
|
98
|
+
/* the other ABI */
|
99
|
+
#define _msgpack_be_double(x) _msgpack_be64(x)
|
100
|
+
#endif
|
101
|
+
|
102
|
+
/* _msgpack_bsp32 */
|
103
|
+
#if defined(_MSC_VER)
|
104
|
+
#define _msgpack_bsp32(name, val) \
|
105
|
+
long name; \
|
106
|
+
_BitScanForward(&name, val)
|
107
|
+
#else
|
108
|
+
#define _msgpack_bsp32(name, val) \
|
109
|
+
int name = __builtin_ctz(val)
|
110
|
+
/* TODO default impl for _msgpack_bsp32 */
|
111
|
+
#endif
|
112
|
+
|
113
|
+
|
114
|
+
#endif
|
115
|
+
|