overflow 0.0.1 → 0.1.0

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: da45bcd93d214011fe0426b29f28127b9db55af8
4
- data.tar.gz: ab817a7f4ccfbe748cb8911ed5ce11acd0d37c86
3
+ metadata.gz: 833a4630a30e7f8723e782791f9ab23b165a06e7
4
+ data.tar.gz: 449f416ff31101f37f2a320a72db5d6cf5cbe1b9
5
5
  SHA512:
6
- metadata.gz: 94ab24a96c978d9f1d556109114b2177fdcd9c9ba84c24a23d23dde617b7db169ad516419a197fe7e254724595c1b8cec426b55fa7ee087b008d974b5f2fb9a9
7
- data.tar.gz: 22cc6db2db596113391d75120589109e96b201361cdc02cb558f17063248ea62e93f61da1798b0ab0495543b236845cad1f2896dd246e1413e26b151cbb333ac
6
+ metadata.gz: d895399c9ce7b662012efc2421bcb0618cba2a4d5eeb49cb23b3ed7efbb886e016311968ee05e5275ff9ea4edcf9cf9ff97ce98d33246a3e29ac7bff8784f2b8
7
+ data.tar.gz: b6ffe5f740632d821c863d07a01963d42f43559f3eb486c26325c2d43dca6aab429fb5f9cec2e284cb7a47c7d992c7b0a6c18d64e18a6b8f0b45d7764ded48c6
data/README.md CHANGED
@@ -1,5 +1,8 @@
1
1
  # Overflow
2
2
 
3
+ [![Gem Version](https://badge.fury.io/rb/overflow.png)](http://badge.fury.io/rb/overflow)
4
+ [![Build Status](https://travis-ci.org/ksss/overflow.png?branch=master)](https://travis-ci.org/ksss/overflow)
5
+
3
6
  Overflow is a class to overflow calculated as C language in Ruby.
4
7
 
5
8
  ## Usage
@@ -7,43 +10,84 @@ Overflow is a class to overflow calculated as C language in Ruby.
7
10
  ```ruby
8
11
  require 'overflow'
9
12
 
10
- def murmur_hash str
11
- data = str.dup.unpack("C*")
12
- m = 0x5bd1e995
13
- r = 16
14
- length = Overflow.new "C" # "C" mean 32bit unsigned char (same as pack template)
15
- length.set str.bytesize
16
- h = length * m
17
-
18
- while 4 <= length
19
- d = data.shift(4).pack("C*").unpack("I")[0]
20
- h += d # calculate not need `& 0xffffffff`
21
- h *= m
22
- h ^= h >> r
23
- length -= 4
24
- end
25
-
26
- if 2 < length
27
- h += (data[2] << 16) & 0xffffffff
28
- end
29
- if 1 < length
30
- h += (data[1] << 8) & 0xffffffff
31
- end
32
- if 0 < length
33
- h += data[0]
34
- h *= m
35
- h ^= h >> r
36
- end
37
-
38
- h *= m
39
- h ^= h >> 10
40
- h *= m
41
- h ^= h >> 17
42
-
43
- h
44
- end
13
+ over = Overflow.new "C" #=> "C" mean 8bit unsigned char (same as pack template)
14
+ over.set 255 #=> set a number (0b11111111)
15
+ p over.to_i #=> 255 (out Fixnum object)
16
+ over = over << 4 #=> left bit shift (0b11110000)
17
+ p over.to_i #=> 240 (overflow bit is dropped)
18
+ p (over >> 4).to_i #=> 15 (0b00001111)
19
+ p (200 - over) #=> -40 (Call Overflow#coerce.)
45
20
  ```
46
21
 
22
+ ## APIs
23
+
24
+ ### initialize(type[, number])
25
+
26
+ **type**: defined C type
27
+
28
+ All type mean same that pack template.
29
+
30
+ - c: `int8_t`
31
+ - C: `uint8_t`
32
+ - s: `int16_t`
33
+ - S: `uint16_t`
34
+ - i: `int`
35
+ - I: `unsigned int`
36
+ - l: `int32_t`
37
+ - L: `uint32_t`
38
+ - q: `int64_t`
39
+ - Q: `uint64_t`
40
+
41
+ ### set(number)
42
+
43
+ ```ruby
44
+ over = Overflow.new "C"
45
+ over.set 1
46
+ p over.to_i #=> 1
47
+ over.set 10
48
+ p over.to_i #=> 10
49
+ ```
50
+
51
+ ### to\_i
52
+
53
+ ```ruby
54
+ over = Overflow.new "C", 256
55
+ over.to_i #=> 0
56
+ ```
57
+
58
+ ### +, -, \*
59
+
60
+ ```ruby
61
+ over = Overflow.new "C", 100
62
+ over += 200 #=> 44
63
+ over -= 50 #=> 250
64
+ over *= 10 #=> 196
65
+ ```
66
+
67
+ ### ~, &, |, ^
68
+
69
+ ```ruby
70
+ over = Overflow.new "C", 0xaa
71
+ ~over #=> 0x55
72
+ over & 0x99 #=> 0x88
73
+ over | 0x99 #=> 0xbb
74
+ over ^ 0x99 #=> 0x33
75
+ ```
76
+
77
+ ### \<\<, \>\>
78
+
79
+ ```ruby
80
+ over = Overflow.new "C", 0xff
81
+ over << 4 #=> 0xf0
82
+ over >> 4 #=> 0x0f
83
+ ```
84
+
85
+ and all `Numeric` methods.
86
+
87
+ ## Class tree
88
+
89
+ Overflow < Numeric
90
+
47
91
  ## Installation
48
92
 
49
93
  Add this line to your application's Gemfile:
data/Rakefile CHANGED
@@ -18,4 +18,4 @@ Rake::ExtensionTask.new('overflow', spec) do |ext|
18
18
  end
19
19
 
20
20
 
21
- task :default => [:spec]
21
+ task :default => [:spec, :build]
@@ -0,0 +1,44 @@
1
+ #! /usr/bin/env ruby
2
+
3
+ lib = File.expand_path('../../lib', __FILE__)
4
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
5
+
6
+ require 'overflow'
7
+
8
+ def murmur_hash str
9
+ data = str.dup.unpack("C*")
10
+ m = 0x5bd1e995
11
+ r = 16
12
+ length = Overflow.new "I", str.bytesize
13
+ h = length * m
14
+
15
+ while 4 <= length
16
+ d = data.shift(4).pack("C*").unpack("I")[0]
17
+ h += d
18
+ h *= m
19
+ h ^= h >> r
20
+ length -= 4
21
+ end
22
+
23
+ if 2 < length
24
+ h += data[2] << 16
25
+ end
26
+ if 1 < length
27
+ h += data[1] << 8
28
+ end
29
+ if 0 < length
30
+ h += data[0]
31
+ h *= m
32
+ h ^= h >> r
33
+ end
34
+
35
+ h *= m
36
+ h ^= h >> 10
37
+ h *= m
38
+ h ^= h >> 17
39
+
40
+ h.to_i
41
+ end
42
+
43
+ # p murmur_hash "murmur" #=> 2800467524
44
+ puts murmur_hash ARGV[0]
@@ -1,3 +1,5 @@
1
1
  require 'mkmf'
2
2
 
3
+ $CFLAGS << " -Wall"
4
+
3
5
  create_makefile('overflow/overflow')
@@ -0,0 +1,455 @@
1
+ #include "ruby.h"
2
+
3
+ #define OVERFLOW_TYPES_ALL_CASE(ptr, callback) do { \
4
+ switch (ptr->type) { \
5
+ case i8: ptr->value = (int8_t) callback; break; \
6
+ case ui8: ptr->value = (uint8_t) callback; break; \
7
+ case i16: ptr->value = (int16_t) callback; break; \
8
+ case ui16: ptr->value = (uint16_t) callback; break; \
9
+ case in: ptr->value = (int) callback; break; \
10
+ case uin: ptr->value = (unsigned int) callback; break; \
11
+ case i32: ptr->value = (int32_t) callback; break; \
12
+ case ui32: ptr->value = (uint32_t) callback; break; \
13
+ case i64: ptr->value = (int64_t) callback; break; \
14
+ case ui64: ptr->value = (uint64_t) callback; break; \
15
+ } \
16
+ } while(0)
17
+
18
+ #define TYPE_PLUS(type, value, other) ((type)((type)(value) + (type)(other)))
19
+ #define TYPE_MINUS(type, value, other) ((type)((type)(value) - (type)(other)))
20
+ #define TYPE_MUL(type, value, other) ((type)((type)(value) * (type)(other)))
21
+ #define TYPE_DIV(type, value, other) ((type)((type)(value) / (type)(other)))
22
+
23
+ #define SWITCH_MACRO(type, macro, a, b) do { \
24
+ switch (type) { \
25
+ case i8: a = macro(int8_t, a, b); break; \
26
+ case ui8: a = macro(uint8_t, a, b); break; \
27
+ case i16: a = macro(int16_t, a, b); break; \
28
+ case ui16: a = macro(uint16_t, a, b); break; \
29
+ case in: a = macro(int, a, b); break; \
30
+ case uin: a = macro(unsigned int, a, b); break; \
31
+ case i32: a = macro(int32_t, a, b); break; \
32
+ case ui32: a = macro(uint32_t, a, b); break; \
33
+ case i64: a = macro(int64_t, a, b); break; \
34
+ case ui64: a = macro(uint64_t, a, b); break; \
35
+ } \
36
+ } while(0)
37
+
38
+ typedef enum {
39
+ i8,
40
+ ui8,
41
+ i16,
42
+ ui16,
43
+ in,
44
+ uin,
45
+ i32,
46
+ ui32,
47
+ i64,
48
+ ui64
49
+ } types;
50
+
51
+ typedef struct {
52
+ types type;
53
+ uint64_t value;
54
+ } overflow_t;
55
+
56
+ static VALUE overflow_set(VALUE self, VALUE obj);
57
+
58
+ types char2type (char c)
59
+ {
60
+ switch (c) {
61
+ case 'c': return i8;
62
+ case 'C': return ui8;
63
+ case 's': return i16;
64
+ case 'S': return ui16;
65
+ case 'i': return in;
66
+ case 'I': return uin;
67
+ case 'l': return i32;
68
+ case 'L': return ui32;
69
+ case 'q': return i64;
70
+ case 'Q': return ui64;
71
+ default:
72
+ rb_raise(rb_eArgError, "type %c is not support", c);
73
+ }
74
+ }
75
+
76
+ static VALUE
77
+ overflow_alloc(VALUE self)
78
+ {
79
+ overflow_t* ptr = ALLOC(overflow_t);
80
+ return Data_Wrap_Struct(self, 0, -1, ptr);
81
+ }
82
+
83
+ static VALUE
84
+ overflow_initialize(int argc, VALUE *argv, VALUE self)
85
+ {
86
+ overflow_t *ptr;
87
+ char *p;
88
+ VALUE obj = argv[0];
89
+
90
+ if (argc < 1 || rb_type(obj) != T_STRING) {
91
+ rb_raise(rb_eArgError, "set a type char for `pack' template");
92
+ }
93
+
94
+ Data_Get_Struct(self, overflow_t, ptr);
95
+ p = RSTRING_PTR(obj);
96
+
97
+ ptr->type = char2type(*p);
98
+ ptr->value = 0;
99
+ if (1 < argc) {
100
+ overflow_set(self, argv[1]);
101
+ }
102
+ return self;
103
+ }
104
+
105
+ static VALUE
106
+ overflow_initialize_copy(VALUE copy, VALUE origin)
107
+ {
108
+ overflow_t *ptr_copy, *ptr_origin;
109
+
110
+ if (copy == origin) return copy;
111
+
112
+ rb_check_frozen(copy);
113
+
114
+ Data_Get_Struct(copy, overflow_t, ptr_copy);
115
+ Data_Get_Struct(origin, overflow_t, ptr_origin);
116
+
117
+ ptr_copy->value = ptr_origin->value;
118
+ ptr_copy->type = ptr_origin->type;
119
+
120
+ return copy;
121
+ }
122
+
123
+ static VALUE
124
+ overflow_to_i(VALUE self)
125
+ {
126
+ overflow_t *ptr;
127
+ Data_Get_Struct(self, overflow_t, ptr);
128
+
129
+ switch (ptr->type) {
130
+ case i8: return INT2NUM((int8_t)ptr->value);
131
+ case ui8: return UINT2NUM((uint8_t)ptr->value);
132
+ case i16: return INT2NUM((int16_t)ptr->value);
133
+ case ui16: return UINT2NUM((uint16_t)ptr->value);
134
+ case in: return LONG2NUM((int)ptr->value);
135
+ case uin: return ULONG2NUM((unsigned int)ptr->value);
136
+ case i32: return LONG2NUM((int32_t)ptr->value);
137
+ case ui32: return ULONG2NUM((uint32_t)ptr->value);
138
+ case i64: return LL2NUM((int64_t)ptr->value);
139
+ case ui64: return ULL2NUM((uint64_t)ptr->value);
140
+ }
141
+ rb_raise(rb_eRuntimeError, "undefined type seted");
142
+ return Qnil;
143
+ }
144
+
145
+ static VALUE
146
+ overflow_coerce(VALUE self, VALUE other)
147
+ {
148
+ if (CLASS_OF(self) == CLASS_OF(other)) {
149
+ return rb_assoc_new(overflow_to_i(other), overflow_to_i(self));
150
+ }
151
+ return rb_assoc_new(other, overflow_to_i(self));
152
+ }
153
+
154
+ static VALUE
155
+ overflow_cmp(VALUE self, VALUE other)
156
+ {
157
+ VALUE i;
158
+
159
+ if (self == other) return 0;
160
+
161
+ i = overflow_to_i(self);
162
+ if (i == other) return INT2FIX(0);
163
+
164
+ if (FIXNUM_P(i)) {
165
+ if (FIXNUM_P(other)) {
166
+ if (FIX2LONG(i) < FIX2LONG(other)) {
167
+ return INT2FIX(-1);
168
+ } else {
169
+ return INT2FIX(1);
170
+ }
171
+ } else if (RB_TYPE_P(other, T_BIGNUM)) {
172
+ return rb_big_cmp(rb_int2big(FIX2LONG(i)), other);
173
+ }
174
+ } else if (RB_TYPE_P(i, T_BIGNUM)) {
175
+ return rb_big_cmp(i, other);
176
+ }
177
+ return rb_num_coerce_cmp(self, other, rb_intern("<=>"));
178
+ }
179
+
180
+ static VALUE
181
+ overflow_hash(VALUE self)
182
+ {
183
+ st_index_t h[2];
184
+ overflow_t *ptr;
185
+ Data_Get_Struct(self, overflow_t, ptr);
186
+ h[0] = NUM2LONG(rb_hash(INT2FIX(ptr->type)));
187
+ h[1] = NUM2LONG(rb_hash(overflow_to_i(self)));
188
+ return LONG2FIX(rb_memhash(h, sizeof(h)));
189
+ }
190
+
191
+ static VALUE
192
+ overflow_eql(VALUE self, VALUE other)
193
+ {
194
+ overflow_t *ptr_self;
195
+ overflow_t *ptr_other;
196
+
197
+ if (TYPE(other) != T_DATA) {
198
+ return Qfalse;
199
+ }
200
+ Data_Get_Struct(self, overflow_t, ptr_self);
201
+ Data_Get_Struct(other, overflow_t, ptr_other);
202
+ if (ptr_self->type != ptr_other->type) {
203
+ return Qfalse;
204
+ }
205
+ if (ptr_self->value != ptr_other->value) {
206
+ return Qfalse;
207
+ }
208
+ return Qtrue;
209
+ }
210
+
211
+ static VALUE
212
+ overflow_to_f(VALUE self)
213
+ {
214
+ return DBL2NUM((double)FIX2LONG(overflow_to_i(self)));
215
+ }
216
+
217
+ static VALUE
218
+ overflow_modulo(VALUE self, VALUE other)
219
+ {
220
+ return rb_funcall(overflow_to_i(self), '-', 1,
221
+ rb_funcall(other, '*', 1,
222
+ rb_funcall(overflow_to_i(self), rb_intern("div"), 1, other)));
223
+ }
224
+
225
+ static VALUE
226
+ overflow_int_p(VALUE self)
227
+ {
228
+ return Qtrue;
229
+ }
230
+
231
+ static VALUE
232
+ overflow_set(VALUE self, VALUE obj)
233
+ {
234
+ VALUE other;
235
+ overflow_t *ptr;
236
+ Data_Get_Struct(self, overflow_t, ptr);
237
+
238
+ switch (rb_type(obj)) {
239
+ case T_FIXNUM:
240
+ OVERFLOW_TYPES_ALL_CASE(ptr, NUM2LL(obj));
241
+ break;
242
+ case T_BIGNUM:
243
+ if (RBIGNUM_POSITIVE_P(obj)) {
244
+ other = rb_funcall(obj, rb_intern("&"), 1, ULL2NUM(0xffffffffffffffffLL));
245
+ ptr->value = (uint64_t) NUM2ULL(other);
246
+ } else {
247
+ ptr->value = (int64_t) NUM2LL(obj);
248
+ }
249
+ break;
250
+ }
251
+ return self;
252
+ }
253
+
254
+ static inline VALUE
255
+ pre_arithmetic(VALUE num)
256
+ {
257
+ switch (rb_type(num)) {
258
+ case T_FIXNUM:
259
+ return num;
260
+ case T_BIGNUM:
261
+ return rb_funcall(num, rb_intern("&"), 1, ULL2NUM(0xffffffffffffffffLL));
262
+ case T_DATA: // self
263
+ return overflow_to_i(num);
264
+ }
265
+ rb_raise(rb_eArgError, "cannot arithmetic");
266
+ return Qnil;
267
+ }
268
+
269
+ static inline VALUE
270
+ overflow_arithmetic(VALUE self, char method, VALUE other)
271
+ {
272
+ uint64_t b;
273
+ overflow_t *ptr;
274
+ VALUE clone = rb_obj_clone(self);
275
+
276
+ Data_Get_Struct(clone, overflow_t, ptr);
277
+
278
+ b = NUM2ULL(pre_arithmetic(other));
279
+
280
+ switch (method) {
281
+ case '+':
282
+ SWITCH_MACRO(ptr->type, TYPE_PLUS, ptr->value, b);
283
+ break;
284
+ case '-':
285
+ SWITCH_MACRO(ptr->type, TYPE_MINUS, ptr->value, b);
286
+ break;
287
+ case '*':
288
+ SWITCH_MACRO(ptr->type, TYPE_MUL, ptr->value, b);
289
+ break;
290
+ case '/':
291
+ SWITCH_MACRO(ptr->type, TYPE_DIV, ptr->value, b);
292
+ break;
293
+ }
294
+ return clone;
295
+ }
296
+
297
+ static VALUE
298
+ overflow_plus(VALUE self, VALUE num)
299
+ {
300
+ return overflow_arithmetic(self, '+', num);
301
+ }
302
+
303
+ static VALUE
304
+ overflow_minus(VALUE self, VALUE num)
305
+ {
306
+ return overflow_arithmetic(self, '-', num);
307
+ }
308
+
309
+ static VALUE
310
+ overflow_mul(VALUE self, VALUE num)
311
+ {
312
+ return overflow_arithmetic(self, '*', num);
313
+ }
314
+
315
+ static VALUE
316
+ overflow_div(VALUE self, VALUE num)
317
+ {
318
+ return overflow_arithmetic(self, '/', num);
319
+ }
320
+
321
+ static VALUE
322
+ overflow_rev(VALUE self)
323
+ {
324
+ VALUE clone = rb_obj_clone(self);
325
+ overflow_t *ptr;
326
+ Data_Get_Struct(clone, overflow_t, ptr);
327
+
328
+ ptr->value = ~ptr->value;
329
+ return clone;
330
+ }
331
+
332
+ static VALUE
333
+ overflow_and(VALUE self, VALUE num)
334
+ {
335
+ VALUE clone = rb_obj_clone(self);
336
+ overflow_t *ptr;
337
+ Data_Get_Struct(clone, overflow_t, ptr);
338
+
339
+ ptr->value = ptr->value & NUM2ULL(pre_arithmetic(num));
340
+ return clone;
341
+ }
342
+
343
+ static VALUE
344
+ overflow_or(VALUE self, VALUE num)
345
+ {
346
+ VALUE clone = rb_obj_clone(self);
347
+ overflow_t *ptr;
348
+ Data_Get_Struct(clone, overflow_t, ptr);
349
+
350
+ ptr->value = ptr->value | NUM2ULL(pre_arithmetic(num));
351
+ return clone;
352
+ }
353
+
354
+ static VALUE
355
+ overflow_xor(VALUE self, VALUE num)
356
+ {
357
+ VALUE clone = rb_obj_clone(self);
358
+ overflow_t *ptr;
359
+ Data_Get_Struct(clone, overflow_t, ptr);
360
+
361
+ ptr->value = ptr->value ^ NUM2ULL(pre_arithmetic(num));
362
+ return clone;
363
+ }
364
+
365
+ static void
366
+ lshift(overflow_t *ptr, long width)
367
+ {
368
+ OVERFLOW_TYPES_ALL_CASE(ptr, (ptr->value << width));
369
+ }
370
+
371
+ static void
372
+ rshift(overflow_t *ptr, long width)
373
+ {
374
+ OVERFLOW_TYPES_ALL_CASE(ptr, (ptr->value >> width));
375
+ }
376
+
377
+ static VALUE
378
+ overflow_lshift(VALUE self, VALUE obj)
379
+ {
380
+ VALUE clone = rb_obj_clone(self);
381
+ long width;
382
+ overflow_t *ptr;
383
+ Data_Get_Struct(clone, overflow_t, ptr);
384
+
385
+ if (!FIXNUM_P(obj))
386
+ rb_raise(rb_eArgError, "too big shift not support");
387
+
388
+ width = FIX2LONG(obj);
389
+
390
+ if (width < 0) {
391
+ rshift(ptr, -width);
392
+ } else {
393
+ lshift(ptr, width);
394
+ }
395
+ return clone;
396
+ }
397
+
398
+ static VALUE
399
+ overflow_rshift(VALUE self, VALUE obj)
400
+ {
401
+ VALUE clone = rb_obj_clone(self);
402
+ long width;
403
+ overflow_t *ptr;
404
+ Data_Get_Struct(clone, overflow_t, ptr);
405
+
406
+ if (!FIXNUM_P(obj))
407
+ rb_raise(rb_eArgError, "too big shift not support");
408
+
409
+ width = FIX2LONG(obj);
410
+
411
+ if (width < 0) {
412
+ lshift(ptr, -width);
413
+ } else {
414
+ rshift(ptr, width);
415
+ }
416
+ return clone;
417
+ }
418
+
419
+ void
420
+ Init_overflow(void)
421
+ {
422
+ VALUE cOverflow;
423
+
424
+ cOverflow = rb_define_class("Overflow", rb_cNumeric);
425
+ rb_define_const(cOverflow, "VERSION", rb_str_new2("0.0.1"));
426
+ rb_define_alloc_func(cOverflow, overflow_alloc);
427
+ rb_define_method(cOverflow, "initialize", overflow_initialize, -1);
428
+ rb_define_method(cOverflow, "initialize_copy", overflow_initialize_copy, 1);
429
+
430
+ /* override on Numeric */
431
+ rb_define_method(cOverflow, "coerce", overflow_coerce, 1);
432
+ rb_define_method(cOverflow, "<=>", overflow_cmp, 1);
433
+ rb_define_method(cOverflow, "hash", overflow_hash, 0);
434
+ rb_define_method(cOverflow, "eql?", overflow_eql, 1);
435
+ rb_define_method(cOverflow, "to_f", overflow_to_f, 0);
436
+ rb_define_method(cOverflow, "%", overflow_modulo, 1);
437
+ rb_define_method(cOverflow, "modulo", overflow_modulo, 1);
438
+ rb_define_method(cOverflow, "integer?", overflow_int_p, 0);
439
+
440
+ rb_define_method(cOverflow, "set", overflow_set, 1);
441
+ rb_define_method(cOverflow, "to_i", overflow_to_i, 0);
442
+
443
+ rb_define_method(cOverflow, "+", overflow_plus, 1);
444
+ rb_define_method(cOverflow, "-", overflow_minus, 1);
445
+ rb_define_method(cOverflow, "*", overflow_mul, 1);
446
+ rb_define_method(cOverflow, "/", overflow_div, 1);
447
+
448
+ rb_define_method(cOverflow, "~", overflow_rev, 0);
449
+ rb_define_method(cOverflow, "&", overflow_and, 1);
450
+ rb_define_method(cOverflow, "|", overflow_or, 1);
451
+ rb_define_method(cOverflow, "^", overflow_xor, 1);
452
+
453
+ rb_define_method(cOverflow, "<<", overflow_lshift, 1);
454
+ rb_define_method(cOverflow, ">>", overflow_rshift, 1);
455
+ }