tdb 0.5.0 → 0.6.1

Sign up to get free protection for your applications and to get access to all the features.
@@ -3,12 +3,15 @@
3
3
  #include <ruby.h>
4
4
  #include <tdb.h>
5
5
 
6
+ unsigned int rbtdb_siphash24(TDB_DATA *key);
6
7
  unsigned int rbtdb_murmur1(TDB_DATA *key);
7
8
  unsigned int rbtdb_murmur1_aligned(TDB_DATA *key);
8
9
  unsigned int rbtdb_murmur2(TDB_DATA *key);
9
10
  unsigned int rbtdb_murmur2a(TDB_DATA *key);
10
11
  unsigned int rbtdb_murmur2_neutral(TDB_DATA *key);
11
12
  unsigned int rbtdb_murmur2_aligned(TDB_DATA *key);
13
+ unsigned int rbtdb_murmur3a(TDB_DATA *key);
14
+ unsigned int rbtdb_murmur3f(TDB_DATA *key);
12
15
  unsigned int rbtdb_fnv1a(TDB_DATA *key);
13
16
  unsigned int rbtdb_djb2(TDB_DATA *key);
14
17
  unsigned int rbtdb_djb3(TDB_DATA *key);
@@ -19,4 +22,5 @@ unsigned int rbtdb_jenkins_lookup3(TDB_DATA *key);
19
22
  #endif
20
23
  #define rbtdb_default 0
21
24
 
25
+ void rbtdb_init_tdb_hash_functions(void);
22
26
  #endif /* RBTDB_H */
@@ -0,0 +1,328 @@
1
+ #include "rbtdb.h"
2
+ /*
3
+ SipHash reference C implementation
4
+ Trivially adapted by Eric Wong for ruby-tdb
5
+
6
+ Written in 2012 by
7
+ Jean-Philippe Aumasson <jeanphilippe.aumasson@gmail.com>
8
+ Daniel J. Bernstein <djb@cr.yp.to>
9
+
10
+ To the extent possible under law, the author(s) have dedicated all copyright
11
+ and related and neighboring rights to this software to the public domain
12
+ worldwide. This software is distributed without any warranty.
13
+
14
+ You should have received a copy of the CC0 Public Domain Dedication along with
15
+ this software. If not, see <http://creativecommons.org/publicdomain/zero/1.0/>.
16
+ */
17
+ #include <stdint.h>
18
+ #include <stdio.h>
19
+ #include <string.h>
20
+ typedef uint64_t u64;
21
+ typedef uint32_t u32;
22
+ typedef uint8_t u8;
23
+
24
+ #define ROTL(x,b) (u64)( ((x) << (b)) | ( (x) >> (64 - (b))) )
25
+
26
+ #define U32TO8_LE(p, v) \
27
+ (p)[0] = (u8)((v) ); (p)[1] = (u8)((v) >> 8); \
28
+ (p)[2] = (u8)((v) >> 16); (p)[3] = (u8)((v) >> 24);
29
+
30
+ #define U64TO8_LE(p, v) \
31
+ U32TO8_LE((p), (u32)((v) )); \
32
+ U32TO8_LE((p) + 4, (u32)((v) >> 32));
33
+
34
+ #define U8TO64_LE(p) \
35
+ (((u64)((p)[0]) ) | \
36
+ ((u64)((p)[1]) << 8) | \
37
+ ((u64)((p)[2]) << 16) | \
38
+ ((u64)((p)[3]) << 24) | \
39
+ ((u64)((p)[4]) << 32) | \
40
+ ((u64)((p)[5]) << 40) | \
41
+ ((u64)((p)[6]) << 48) | \
42
+ ((u64)((p)[7]) << 56))
43
+
44
+ #define SIPROUND \
45
+ do { \
46
+ v0 += v1; v1=ROTL(v1,13); v1 ^= v0; v0=ROTL(v0,32); \
47
+ v2 += v3; v3=ROTL(v3,16); v3 ^= v2; \
48
+ v0 += v3; v3=ROTL(v3,21); v3 ^= v0; \
49
+ v2 += v1; v1=ROTL(v1,17); v1 ^= v2; v2=ROTL(v2,32); \
50
+ } while(0)
51
+
52
+ /* SipHash-2-4 */
53
+ static int
54
+ crypto_auth(unsigned char *out, const unsigned char *in,
55
+ size_t inlen, const unsigned char *k)
56
+ {
57
+ /* "somepseudorandomlygeneratedbytes" */
58
+ u64 v0 = 0x736f6d6570736575ULL;
59
+ u64 v1 = 0x646f72616e646f6dULL;
60
+ u64 v2 = 0x6c7967656e657261ULL;
61
+ u64 v3 = 0x7465646279746573ULL;
62
+ u64 b;
63
+ u64 k0 = U8TO64_LE(k);
64
+ u64 k1 = U8TO64_LE(k + 8);
65
+ u64 m;
66
+ const u8 *end = in + inlen - (inlen % sizeof(u64));
67
+ const int left = inlen & 7;
68
+ b = ((u64) inlen) << 56;
69
+ v3 ^= k1;
70
+ v2 ^= k0;
71
+ v1 ^= k1;
72
+ v0 ^= k0;
73
+
74
+ for (; in != end; in += 8) {
75
+ m = U8TO64_LE(in);
76
+ #ifdef DEBUG
77
+ printf("(%3d) v0 %08x %08x\n", (int)inlen, (u32) (v0 >> 32),
78
+ (u32) v0);
79
+ printf("(%3d) v1 %08x %08x\n", (int)inlen, (u32) (v1 >> 32),
80
+ (u32) v1);
81
+ printf("(%3d) v2 %08x %08x\n", (int)inlen, (u32) (v2 >> 32),
82
+ (u32) v2);
83
+ printf("(%3d) v3 %08x %08x\n", (int)inlen, (u32) (v3 >> 32),
84
+ (u32) v3);
85
+ printf("(%3d) compress %08x %08x\n", (int)inlen,
86
+ (u32) (m >> 32), (u32) m);
87
+ #endif
88
+ v3 ^= m;
89
+ SIPROUND;
90
+ SIPROUND;
91
+ v0 ^= m;
92
+ }
93
+
94
+ switch (left) {
95
+ case 7:
96
+ b |= ((u64) in[6]) << 48;
97
+
98
+ case 6:
99
+ b |= ((u64) in[5]) << 40;
100
+
101
+ case 5:
102
+ b |= ((u64) in[4]) << 32;
103
+
104
+ case 4:
105
+ b |= ((u64) in[3]) << 24;
106
+
107
+ case 3:
108
+ b |= ((u64) in[2]) << 16;
109
+
110
+ case 2:
111
+ b |= ((u64) in[1]) << 8;
112
+
113
+ case 1:
114
+ b |= ((u64) in[0]);
115
+ break;
116
+
117
+ case 0:
118
+ break;
119
+ }
120
+
121
+ #ifdef DEBUG
122
+ printf("(%3d) v0 %08x %08x\n", (int)inlen, (u32) (v0 >> 32), (u32) v0);
123
+ printf("(%3d) v1 %08x %08x\n", (int)inlen, (u32) (v1 >> 32), (u32) v1);
124
+ printf("(%3d) v2 %08x %08x\n", (int)inlen, (u32) (v2 >> 32), (u32) v2);
125
+ printf("(%3d) v3 %08x %08x\n", (int)inlen, (u32) (v3 >> 32), (u32) v3);
126
+ printf("(%3d) padding %08x %08x\n", (int)inlen, (u32) (b >> 32),
127
+ (u32) b);
128
+ #endif
129
+ v3 ^= b;
130
+ SIPROUND;
131
+ SIPROUND;
132
+ v0 ^= b;
133
+ #ifdef DEBUG
134
+ printf("(%3d) v0 %08x %08x\n", (int)inlen, (u32) (v0 >> 32), (u32) v0);
135
+ printf("(%3d) v1 %08x %08x\n", (int)inlen, (u32) (v1 >> 32), (u32) v1);
136
+ printf("(%3d) v2 %08x %08x\n", (int)inlen, (u32) (v2 >> 32), (u32) v2);
137
+ printf("(%3d) v3 %08x %08x\n", (int)inlen, (u32) (v3 >> 32), (u32) v3);
138
+ #endif
139
+ v2 ^= 0xff;
140
+ SIPROUND;
141
+ SIPROUND;
142
+ SIPROUND;
143
+ SIPROUND;
144
+ b = v0 ^ v1 ^ v2 ^ v3;
145
+ U64TO8_LE(out, b);
146
+ return 0;
147
+ }
148
+
149
+ /*
150
+ SipHash-2-4 output with
151
+ k = 00 01 02 ...
152
+ and
153
+ in = (empty string)
154
+ in = 00 (1 byte)
155
+ in = 00 01 (2 bytes)
156
+ in = 00 01 02 (3 bytes)
157
+ ...
158
+ in = 00 01 02 ... 3e (63 bytes)
159
+ */
160
+ u8 vectors[64][8] = {
161
+ {0x31, 0x0e, 0x0e, 0xdd, 0x47, 0xdb, 0x6f, 0x72,}
162
+ ,
163
+ {0xfd, 0x67, 0xdc, 0x93, 0xc5, 0x39, 0xf8, 0x74,}
164
+ ,
165
+ {0x5a, 0x4f, 0xa9, 0xd9, 0x09, 0x80, 0x6c, 0x0d,}
166
+ ,
167
+ {0x2d, 0x7e, 0xfb, 0xd7, 0x96, 0x66, 0x67, 0x85,}
168
+ ,
169
+ {0xb7, 0x87, 0x71, 0x27, 0xe0, 0x94, 0x27, 0xcf,}
170
+ ,
171
+ {0x8d, 0xa6, 0x99, 0xcd, 0x64, 0x55, 0x76, 0x18,}
172
+ ,
173
+ {0xce, 0xe3, 0xfe, 0x58, 0x6e, 0x46, 0xc9, 0xcb,}
174
+ ,
175
+ {0x37, 0xd1, 0x01, 0x8b, 0xf5, 0x00, 0x02, 0xab,}
176
+ ,
177
+ {0x62, 0x24, 0x93, 0x9a, 0x79, 0xf5, 0xf5, 0x93,}
178
+ ,
179
+ {0xb0, 0xe4, 0xa9, 0x0b, 0xdf, 0x82, 0x00, 0x9e,}
180
+ ,
181
+ {0xf3, 0xb9, 0xdd, 0x94, 0xc5, 0xbb, 0x5d, 0x7a,}
182
+ ,
183
+ {0xa7, 0xad, 0x6b, 0x22, 0x46, 0x2f, 0xb3, 0xf4,}
184
+ ,
185
+ {0xfb, 0xe5, 0x0e, 0x86, 0xbc, 0x8f, 0x1e, 0x75,}
186
+ ,
187
+ {0x90, 0x3d, 0x84, 0xc0, 0x27, 0x56, 0xea, 0x14,}
188
+ ,
189
+ {0xee, 0xf2, 0x7a, 0x8e, 0x90, 0xca, 0x23, 0xf7,}
190
+ ,
191
+ {0xe5, 0x45, 0xbe, 0x49, 0x61, 0xca, 0x29, 0xa1,}
192
+ ,
193
+ {0xdb, 0x9b, 0xc2, 0x57, 0x7f, 0xcc, 0x2a, 0x3f,}
194
+ ,
195
+ {0x94, 0x47, 0xbe, 0x2c, 0xf5, 0xe9, 0x9a, 0x69,}
196
+ ,
197
+ {0x9c, 0xd3, 0x8d, 0x96, 0xf0, 0xb3, 0xc1, 0x4b,}
198
+ ,
199
+ {0xbd, 0x61, 0x79, 0xa7, 0x1d, 0xc9, 0x6d, 0xbb,}
200
+ ,
201
+ {0x98, 0xee, 0xa2, 0x1a, 0xf2, 0x5c, 0xd6, 0xbe,}
202
+ ,
203
+ {0xc7, 0x67, 0x3b, 0x2e, 0xb0, 0xcb, 0xf2, 0xd0,}
204
+ ,
205
+ {0x88, 0x3e, 0xa3, 0xe3, 0x95, 0x67, 0x53, 0x93,}
206
+ ,
207
+ {0xc8, 0xce, 0x5c, 0xcd, 0x8c, 0x03, 0x0c, 0xa8,}
208
+ ,
209
+ {0x94, 0xaf, 0x49, 0xf6, 0xc6, 0x50, 0xad, 0xb8,}
210
+ ,
211
+ {0xea, 0xb8, 0x85, 0x8a, 0xde, 0x92, 0xe1, 0xbc,}
212
+ ,
213
+ {0xf3, 0x15, 0xbb, 0x5b, 0xb8, 0x35, 0xd8, 0x17,}
214
+ ,
215
+ {0xad, 0xcf, 0x6b, 0x07, 0x63, 0x61, 0x2e, 0x2f,}
216
+ ,
217
+ {0xa5, 0xc9, 0x1d, 0xa7, 0xac, 0xaa, 0x4d, 0xde,}
218
+ ,
219
+ {0x71, 0x65, 0x95, 0x87, 0x66, 0x50, 0xa2, 0xa6,}
220
+ ,
221
+ {0x28, 0xef, 0x49, 0x5c, 0x53, 0xa3, 0x87, 0xad,}
222
+ ,
223
+ {0x42, 0xc3, 0x41, 0xd8, 0xfa, 0x92, 0xd8, 0x32,}
224
+ ,
225
+ {0xce, 0x7c, 0xf2, 0x72, 0x2f, 0x51, 0x27, 0x71,}
226
+ ,
227
+ {0xe3, 0x78, 0x59, 0xf9, 0x46, 0x23, 0xf3, 0xa7,}
228
+ ,
229
+ {0x38, 0x12, 0x05, 0xbb, 0x1a, 0xb0, 0xe0, 0x12,}
230
+ ,
231
+ {0xae, 0x97, 0xa1, 0x0f, 0xd4, 0x34, 0xe0, 0x15,}
232
+ ,
233
+ {0xb4, 0xa3, 0x15, 0x08, 0xbe, 0xff, 0x4d, 0x31,}
234
+ ,
235
+ {0x81, 0x39, 0x62, 0x29, 0xf0, 0x90, 0x79, 0x02,}
236
+ ,
237
+ {0x4d, 0x0c, 0xf4, 0x9e, 0xe5, 0xd4, 0xdc, 0xca,}
238
+ ,
239
+ {0x5c, 0x73, 0x33, 0x6a, 0x76, 0xd8, 0xbf, 0x9a,}
240
+ ,
241
+ {0xd0, 0xa7, 0x04, 0x53, 0x6b, 0xa9, 0x3e, 0x0e,}
242
+ ,
243
+ {0x92, 0x59, 0x58, 0xfc, 0xd6, 0x42, 0x0c, 0xad,}
244
+ ,
245
+ {0xa9, 0x15, 0xc2, 0x9b, 0xc8, 0x06, 0x73, 0x18,}
246
+ ,
247
+ {0x95, 0x2b, 0x79, 0xf3, 0xbc, 0x0a, 0xa6, 0xd4,}
248
+ ,
249
+ {0xf2, 0x1d, 0xf2, 0xe4, 0x1d, 0x45, 0x35, 0xf9,}
250
+ ,
251
+ {0x87, 0x57, 0x75, 0x19, 0x04, 0x8f, 0x53, 0xa9,}
252
+ ,
253
+ {0x10, 0xa5, 0x6c, 0xf5, 0xdf, 0xcd, 0x9a, 0xdb,}
254
+ ,
255
+ {0xeb, 0x75, 0x09, 0x5c, 0xcd, 0x98, 0x6c, 0xd0,}
256
+ ,
257
+ {0x51, 0xa9, 0xcb, 0x9e, 0xcb, 0xa3, 0x12, 0xe6,}
258
+ ,
259
+ {0x96, 0xaf, 0xad, 0xfc, 0x2c, 0xe6, 0x66, 0xc7,}
260
+ ,
261
+ {0x72, 0xfe, 0x52, 0x97, 0x5a, 0x43, 0x64, 0xee,}
262
+ ,
263
+ {0x5a, 0x16, 0x45, 0xb2, 0x76, 0xd5, 0x92, 0xa1,}
264
+ ,
265
+ {0xb2, 0x74, 0xcb, 0x8e, 0xbf, 0x87, 0x87, 0x0a,}
266
+ ,
267
+ {0x6f, 0x9b, 0xb4, 0x20, 0x3d, 0xe7, 0xb3, 0x81,}
268
+ ,
269
+ {0xea, 0xec, 0xb2, 0xa3, 0x0b, 0x22, 0xa8, 0x7f,}
270
+ ,
271
+ {0x99, 0x24, 0xa4, 0x3c, 0xc1, 0x31, 0x57, 0x24,}
272
+ ,
273
+ {0xbd, 0x83, 0x8d, 0x3a, 0xaf, 0xbf, 0x8d, 0xb7,}
274
+ ,
275
+ {0x0b, 0x1a, 0x2a, 0x32, 0x65, 0xd5, 0x1a, 0xea,}
276
+ ,
277
+ {0x13, 0x50, 0x79, 0xa3, 0x23, 0x1c, 0xe6, 0x60,}
278
+ ,
279
+ {0x93, 0x2b, 0x28, 0x46, 0xe4, 0xd7, 0x06, 0x66,}
280
+ ,
281
+ {0xe1, 0x91, 0x5f, 0x5c, 0xb1, 0xec, 0xa4, 0x6c,}
282
+ ,
283
+ {0xf3, 0x25, 0x96, 0x5c, 0xa1, 0x6d, 0x62, 0x9f,}
284
+ ,
285
+ {0x57, 0x5f, 0xf2, 0x8e, 0x60, 0x38, 0x1b, 0xe5,}
286
+ ,
287
+ {0x72, 0x45, 0x06, 0xeb, 0x4c, 0x32, 0x8a, 0x95,}
288
+ };
289
+
290
+ int rbtdb_siphash_test_vectors(void)
291
+ {
292
+ #define MAXLEN 64
293
+ u8 in[MAXLEN], out[8], k[16];
294
+ int i;
295
+ int ok = 1;
296
+
297
+ for (i = 0; i < 16; ++i)
298
+ k[i] = i;
299
+
300
+ for (i = 0; i < MAXLEN; ++i) {
301
+ in[i] = i;
302
+ crypto_auth(out, in, i, k);
303
+
304
+ if (memcmp(out, vectors[i], 8)) {
305
+ printf("test vector failed for %d bytes\n", i);
306
+ ok = 0;
307
+ }
308
+ }
309
+
310
+ return ok;
311
+ }
312
+
313
+ unsigned int rbtdb_siphash24(TDB_DATA *data)
314
+ {
315
+ /* n.b.: tdb is for persistent storage, so the key must be constant */
316
+ static uint8_t key[] = "trivial database";
317
+ /* static const uint8_t check[(sizeof(key) >= 16)]; */
318
+ union {
319
+ uint32_t x32[2];
320
+ uint64_t x64;
321
+ } out;
322
+ unsigned char *in = data->dptr;
323
+ size_t len = data->dsize;
324
+
325
+ crypto_auth((unsigned char *)&out, in, len, key);
326
+
327
+ return (unsigned int)(out.x32[0] ^ out.x32[1]);
328
+ }
@@ -3,17 +3,12 @@
3
3
  #include <sys/stat.h>
4
4
  #include <fcntl.h>
5
5
  #include <errno.h>
6
- #ifdef HAVE_RUBY_ST_H
7
- # include <ruby/st.h>
8
- #else
9
- # include <st.h>
10
- #endif
11
6
  #include <pthread.h>
12
7
 
13
8
  /* this protects the global list of tdb objects maintained by libtdb */
14
9
  static pthread_mutex_t big_lock = PTHREAD_MUTEX_INITIALIZER;
15
10
  static VALUE cTDB, cERR;
16
- static st_table *exc_hash;
11
+ static VALUE exc_hash;
17
12
  static VALUE hashes;
18
13
 
19
14
  /* must be a macro to prevent GC from killing converted 'val's */
@@ -26,13 +21,14 @@ static VALUE hashes;
26
21
  static void init_exc(enum TDB_ERROR ecode, const char *name)
27
22
  {
28
23
  VALUE exc = rb_define_class_under(cERR, name, cERR);
29
- st_insert(exc_hash, (st_data_t)ecode, (st_data_t)exc);
24
+ rb_hash_aset(exc_hash, INT2NUM(ecode), exc);
30
25
  }
31
26
 
32
27
  static void init_errors(void)
33
28
  {
34
29
  cERR = rb_define_class_under(cTDB, "ERR", rb_eStandardError);
35
- exc_hash = st_init_numtable();
30
+ exc_hash = rb_hash_new();
31
+ rb_global_variable(&exc_hash);
36
32
 
37
33
  init_exc(TDB_ERR_CORRUPT, "CORRUPT");
38
34
  init_exc(TDB_ERR_IO, "IO");
@@ -53,7 +49,7 @@ static void my_raise(struct tdb_context *tdb)
53
49
  {
54
50
  enum TDB_ERROR ecode = tdb_error(tdb);
55
51
  const char *str = tdb_errorstr(tdb);
56
- VALUE exc;
52
+ VALUE exc = Qnil;
57
53
 
58
54
  switch (ecode) {
59
55
  case TDB_SUCCESS:
@@ -71,9 +67,10 @@ static void my_raise(struct tdb_context *tdb)
71
67
  #ifdef HAVE_CONST_TDB_ERR_NESTING
72
68
  case TDB_ERR_NESTING:
73
69
  #endif /* HAVE_CONST_TDB_ERR_NESTING */
74
- if (!st_lookup(exc_hash, (st_data_t)ecode, (st_data_t *)&exc))
75
- rb_bug("no-existent exception: %s\n", str);
70
+ exc = rb_hash_aref(exc_hash, INT2NUM(ecode));
76
71
  }
72
+ if (NIL_P(exc))
73
+ rb_bug("no-existent exception: %s\n", str);
77
74
  rb_raise(exc, str);
78
75
  }
79
76
 
@@ -81,12 +78,15 @@ static void init_hashes(void)
81
78
  {
82
79
  #define HF(x) \
83
80
  rb_hash_aset(hashes,ID2SYM(rb_intern(#x)),ULONG2NUM((unsigned long)rbtdb_##x))
81
+ HF(siphash24);
84
82
  HF(murmur1);
85
83
  HF(murmur1_aligned);
86
84
  HF(murmur2);
87
85
  HF(murmur2a);
88
86
  HF(murmur2_neutral);
89
87
  HF(murmur2_aligned);
88
+ HF(murmur3a);
89
+ HF(murmur3f);
90
90
  HF(fnv1a);
91
91
  HF(djb2);
92
92
  HF(djb3);
@@ -94,26 +94,39 @@ rb_hash_aset(hashes,ID2SYM(rb_intern(#x)),ULONG2NUM((unsigned long)rbtdb_##x))
94
94
  HF(default);
95
95
  }
96
96
 
97
- #ifndef HAVE_RB_THREAD_BLOCKING_REGION
98
- /* (very) partial emulation of the 1.9 rb_thread_blocking_region under 1.8 */
97
+ /* partial emulation of the 1.9 rb_thread_blocking_region under 1.8 */
98
+ #if defined(HAVE_RB_THREAD_BLOCKING_REGION) && \
99
+ defined(HAVE_RB_THREAD_CALL_WITHOUT_GVL)
100
+ /*
101
+ * Ruby 1.9 - 2.1 (we use deprecated rb_thread_blocking_region in 2.0+
102
+ * because we can detect (but not use) rb_thread_blocking_region in 1.9.3
103
+ */
104
+ typedef VALUE (*my_blocking_fn_t)(void*);
105
+ # define WITHOUT_GVL(fn,a,ubf,b) \
106
+ rb_thread_blocking_region((my_blocking_fn_t)(fn),(a),(ubf),(b))
107
+ #elif defined(HAVE_RB_THREAD_CALL_WITHOUT_GVL) /* Ruby 2.2+ */
108
+ #include <ruby/thread.h>
109
+ # define WITHOUT_GVL(fn,a,ubf,b) \
110
+ rb_thread_call_without_gvl((fn),(a),(ubf),(b))
111
+ #else /* Ruby 1.8 */
99
112
  # include <rubysig.h>
100
- typedef VALUE rb_blocking_function_t(void *);
101
- static VALUE my_tbr(rb_blocking_function_t *fn, void *data)
113
+ # define RUBY_UBF_IO ((rb_unblock_function_t *)-1)
114
+ typedef void rb_unblock_function_t(void *);
115
+ typedef void * rb_blocking_function_t(void *);
116
+ static void * WITHOUT_GVL(rb_blocking_function_t *func, void *data1,
117
+ rb_unblock_function_t *ubf, void *data2)
102
118
  {
103
- VALUE rv;
119
+ void *rv;
104
120
 
105
121
  TRAP_BEG;
106
- rv = fn(data);
122
+ rv = func(data1);
107
123
  TRAP_END;
108
124
 
109
125
  return rv;
110
126
  }
111
- #else
112
- static VALUE my_tbr(rb_blocking_function_t *fn, void *data)
113
- {
114
- return rb_thread_blocking_region(fn, data, RUBY_UBF_IO, 0);
115
- }
116
- #endif /* HAVE_RUBY_THREAD_BLOCKING_REGION */
127
+ #endif /* ! HAVE_RB_THREAD_BLOCKING_REGION */
128
+
129
+ #define my_tbr(fn,data) WITHOUT_GVL((void *)(fn),(data),RUBY_UBF_IO,0)
117
130
 
118
131
  static void gcfree(void *ptr)
119
132
  {
@@ -154,7 +167,7 @@ struct open_args {
154
167
  tdb_hash_func hash_fn;
155
168
  };
156
169
 
157
- static VALUE nogvl_open(void *ptr)
170
+ static void * nogvl_open(void *ptr)
158
171
  {
159
172
  struct open_args *o = ptr;
160
173
  struct tdb_context *tdb;
@@ -164,7 +177,7 @@ static VALUE nogvl_open(void *ptr)
164
177
  o->open_flags, o->mode, o->log_ctx, o->hash_fn);
165
178
  pthread_mutex_unlock(&big_lock);
166
179
 
167
- return (VALUE)tdb;
180
+ return (void *)tdb;
168
181
  }
169
182
 
170
183
  static void set_args(VALUE self, struct open_args *o, VALUE opts)
@@ -260,7 +273,7 @@ static VALUE init(int argc, VALUE *argv, VALUE self)
260
273
  if (NIL_P(path))
261
274
  o.tdb_flags |= TDB_INTERNAL;
262
275
  else
263
- o.name = StringValuePtr(path);
276
+ o.name = StringValueCStr(path);
264
277
 
265
278
  tdb = (struct tdb_context *)my_tbr(nogvl_open, &o);
266
279
  if (!tdb) {
@@ -280,16 +293,16 @@ static VALUE init(int argc, VALUE *argv, VALUE self)
280
293
  }
281
294
 
282
295
  /* tdb_close can do a lot, including cancel transactions an munmap */
283
- static VALUE nogvl_close(void *ptr)
296
+ static void * nogvl_close(void *ptr)
284
297
  {
285
298
  struct tdb_context *tdb = ptr;
286
- VALUE rv;
299
+ long rv;
287
300
 
288
301
  pthread_mutex_lock(&big_lock);
289
- rv = (VALUE)tdb_close(tdb);
302
+ rv = tdb_close(tdb);
290
303
  pthread_mutex_unlock(&big_lock);
291
304
 
292
- return rv;
305
+ return (void *)rv;
293
306
  }
294
307
 
295
308
  static VALUE tdbclose(VALUE self)
@@ -298,7 +311,7 @@ static VALUE tdbclose(VALUE self)
298
311
 
299
312
  DATA_PTR(self) = NULL;
300
313
 
301
- if ((int)my_tbr(nogvl_close, tdb) == -1)
314
+ if ((long)my_tbr(nogvl_close, tdb) == -1)
302
315
  rb_sys_fail("tdb_close");
303
316
 
304
317
  return Qnil;
@@ -365,14 +378,14 @@ static int fetch_parse(TDB_DATA key, TDB_DATA val, void *data)
365
378
  return 0;
366
379
  }
367
380
 
368
- static VALUE nogvl_parse_record(void *ptr)
381
+ static void * nogvl_parse_record(void *ptr)
369
382
  {
370
383
  struct fetch_parse_args *f = ptr;
371
384
 
372
385
  if (tdb_parse_record(f->tdb, f->as.key, fetch_parse, ptr) == -1)
373
- return Qnil;
386
+ return (void *)Qnil;
374
387
 
375
- return f->value == f->as.value ? f->value : Qnil;
388
+ return (void *)(f->value == f->as.value ? f->value : Qnil);
376
389
  }
377
390
 
378
391
  static VALUE fetch(int argc, VALUE *argv, VALUE self)
@@ -391,7 +404,7 @@ static VALUE fetch(int argc, VALUE *argv, VALUE self)
391
404
  f.tdb = db(self, 1);
392
405
  TO_TDB_DATA(f.as.key, key);
393
406
 
394
- return my_tbr(nogvl_parse_record, &f);
407
+ return (VALUE)my_tbr(nogvl_parse_record, &f);
395
408
  }
396
409
 
397
410
  struct store_args {
@@ -401,11 +414,12 @@ struct store_args {
401
414
  int flag;
402
415
  };
403
416
 
404
- static VALUE nogvl_store(void *ptr)
417
+ static void * nogvl_store(void *ptr)
405
418
  {
406
419
  struct store_args *s = ptr;
420
+ long rc = tdb_store(s->tdb, s->key, s->val, s->flag);
407
421
 
408
- return (VALUE)tdb_store(s->tdb, s->key, s->val, s->flag);
422
+ return (void *)rc;
409
423
  }
410
424
 
411
425
  static VALUE rbtdb_store(VALUE self, VALUE key, VALUE val, int flag, int soft)
@@ -417,7 +431,7 @@ static VALUE rbtdb_store(VALUE self, VALUE key, VALUE val, int flag, int soft)
417
431
  TO_TDB_DATA(s.val, val);
418
432
  s.flag = flag;
419
433
 
420
- if ((int)my_tbr(nogvl_store, &s) == -1) {
434
+ if ((long)my_tbr(nogvl_store, &s) == -1) {
421
435
  if (soft) {
422
436
  int ecode = tdb_error(s.tdb);
423
437
 
@@ -462,11 +476,11 @@ struct exists_args {
462
476
  TDB_DATA key;
463
477
  };
464
478
 
465
- static VALUE nogvl_exists(void *ptr)
479
+ static void * nogvl_exists(void *ptr)
466
480
  {
467
481
  struct exists_args *e = ptr;
468
482
 
469
- return tdb_exists(e->tdb, e->key) == 0 ? Qfalse : Qtrue;
483
+ return (void *)(tdb_exists(e->tdb, e->key) == 0 ? Qfalse : Qtrue);
470
484
  }
471
485
 
472
486
  static VALUE has_key(VALUE self, VALUE key)
@@ -476,7 +490,7 @@ static VALUE has_key(VALUE self, VALUE key)
476
490
  e.tdb = db(self, 1);
477
491
  TO_TDB_DATA(e.key, key);
478
492
 
479
- return my_tbr(nogvl_exists, &e);
493
+ return (VALUE)my_tbr(nogvl_exists, &e);
480
494
  }
481
495
 
482
496
  struct traverse_args {
@@ -518,13 +532,13 @@ traverse_fn(struct tdb_context *tdb, TDB_DATA key, TDB_DATA val, void *data)
518
532
  return t->state;
519
533
  }
520
534
 
521
- static VALUE nogvl_traverse(void *ptr)
535
+ static void * nogvl_traverse(void *ptr)
522
536
  {
523
537
  struct traverse_args *t = ptr;
524
538
 
525
539
  (void)tdb_traverse(t->tdb, traverse_fn, t);
526
540
 
527
- return Qfalse;
541
+ return (void *)Qfalse;
528
542
  }
529
543
 
530
544
  static VALUE each(VALUE self)
@@ -545,11 +559,11 @@ struct delete_args {
545
559
  TDB_DATA key;
546
560
  };
547
561
 
548
- static VALUE nogvl_delete(void *ptr)
562
+ static void * nogvl_delete(void *ptr)
549
563
  {
550
564
  struct delete_args *d = ptr;
551
565
 
552
- return tdb_delete(d->tdb, d->key) == 0 ? Qtrue : Qfalse;
566
+ return (void *)(tdb_delete(d->tdb, d->key) == 0 ? Qtrue : Qfalse);
553
567
  }
554
568
 
555
569
  static VALUE nuke(VALUE self, VALUE key)
@@ -559,7 +573,7 @@ static VALUE nuke(VALUE self, VALUE key)
559
573
  d.tdb = db(self, 1);
560
574
  TO_TDB_DATA(d.key, key);
561
575
 
562
- return my_tbr(nogvl_delete, &d);
576
+ return (VALUE)my_tbr(nogvl_delete, &d);
563
577
  }
564
578
 
565
579
  static VALUE aref(VALUE self, VALUE key)
@@ -580,7 +594,7 @@ static VALUE delete(int argc, VALUE *argv, VALUE self)
580
594
  static VALUE lockall(VALUE self)
581
595
  {
582
596
  struct tdb_context *tdb = db(self, 1);
583
- if ((int)my_tbr((rb_blocking_function_t *)tdb_lockall, tdb))
597
+ if (my_tbr(tdb_lockall, tdb))
584
598
  my_raise(tdb);
585
599
 
586
600
  return Qtrue;
@@ -591,7 +605,7 @@ static VALUE trylockall(VALUE self)
591
605
  struct tdb_context *tdb = db(self, 1);
592
606
  void *fn = tdb_lockall_nonblock;
593
607
 
594
- if ((int)my_tbr((rb_blocking_function_t *)fn, tdb)) {
608
+ if (my_tbr(fn, tdb)) {
595
609
  if (tdb_error(tdb) == TDB_ERR_LOCK)
596
610
  return Qfalse;
597
611
  my_raise(tdb);
@@ -602,7 +616,7 @@ static VALUE trylockall(VALUE self)
602
616
  static VALUE unlockall(VALUE self)
603
617
  {
604
618
  struct tdb_context *tdb = db(self, 1);
605
- if ((int)my_tbr((rb_blocking_function_t *)tdb_unlockall, tdb))
619
+ if (my_tbr(tdb_unlockall, tdb))
606
620
  my_raise(tdb);
607
621
  return Qtrue;
608
622
  }
@@ -610,7 +624,7 @@ static VALUE unlockall(VALUE self)
610
624
  static VALUE lockall_read(VALUE self)
611
625
  {
612
626
  struct tdb_context *tdb = db(self, 1);
613
- if ((int)my_tbr((rb_blocking_function_t *)tdb_lockall_read, tdb))
627
+ if (my_tbr(tdb_lockall_read, tdb))
614
628
  my_raise(tdb);
615
629
  return Qtrue;
616
630
  }
@@ -619,7 +633,7 @@ static VALUE trylockall_read(VALUE self)
619
633
  {
620
634
  struct tdb_context *tdb = db(self, 1);
621
635
  void *fn = tdb_lockall_read_nonblock;
622
- if ((int)my_tbr((rb_blocking_function_t *)fn, tdb)) {
636
+ if (my_tbr(fn, tdb)) {
623
637
  if (tdb_error(tdb) == TDB_ERR_LOCK)
624
638
  return Qfalse;
625
639
  my_raise(tdb);
@@ -630,7 +644,7 @@ static VALUE trylockall_read(VALUE self)
630
644
  static VALUE unlockall_read(VALUE self)
631
645
  {
632
646
  struct tdb_context *tdb = db(self, 1);
633
- if ((int)my_tbr((rb_blocking_function_t *)tdb_unlockall_read, tdb))
647
+ if (my_tbr(tdb_unlockall_read, tdb))
634
648
  my_raise(tdb);
635
649
  return Qtrue;
636
650
  }
@@ -638,7 +652,7 @@ static VALUE unlockall_read(VALUE self)
638
652
  static VALUE lockall_mark(VALUE self)
639
653
  {
640
654
  struct tdb_context *tdb = db(self, 1);
641
- if ((int)my_tbr((rb_blocking_function_t *)tdb_lockall_mark, tdb))
655
+ if (my_tbr(tdb_lockall_mark, tdb))
642
656
  my_raise(tdb);
643
657
  return Qtrue;
644
658
  }
@@ -646,7 +660,8 @@ static VALUE lockall_mark(VALUE self)
646
660
  static VALUE lockall_unmark(VALUE self)
647
661
  {
648
662
  struct tdb_context *tdb = db(self, 1);
649
- if ((int)my_tbr((rb_blocking_function_t *)tdb_lockall_unmark, tdb))
663
+
664
+ if (my_tbr(tdb_lockall_unmark, tdb))
650
665
  my_raise(tdb);
651
666
  return Qtrue;
652
667
  }
@@ -657,7 +672,7 @@ static VALUE lockall_unmark(VALUE self)
657
672
  static VALUE clear(VALUE self)
658
673
  {
659
674
  struct tdb_context *tdb = db(self, 1);
660
- if ((int)my_tbr((rb_blocking_function_t *)tdb_wipe_all, tdb))
675
+ if (my_tbr(tdb_wipe_all, tdb))
661
676
  my_raise(tdb);
662
677
  return self;
663
678
  }
@@ -667,7 +682,7 @@ static VALUE clear(VALUE self)
667
682
  static VALUE repack(VALUE self)
668
683
  {
669
684
  struct tdb_context *tdb = db(self, 1);
670
- if ((int)my_tbr((rb_blocking_function_t *)tdb_repack, tdb))
685
+ if (my_tbr(tdb_repack, tdb))
671
686
  my_raise(tdb);
672
687
  return self;
673
688
  }