summaryrefslogtreecommitdiff
path: root/spec/rubyspec/core/bignum
diff options
context:
space:
mode:
Diffstat (limited to 'spec/rubyspec/core/bignum')
-rw-r--r--spec/rubyspec/core/bignum/abs_spec.rb7
-rw-r--r--spec/rubyspec/core/bignum/bignum_spec.rb7
-rw-r--r--spec/rubyspec/core/bignum/bit_and_spec.rb50
-rw-r--r--spec/rubyspec/core/bignum/bit_length_spec.rb33
-rw-r--r--spec/rubyspec/core/bignum/bit_or_spec.rb41
-rw-r--r--spec/rubyspec/core/bignum/bit_xor_spec.rb47
-rw-r--r--spec/rubyspec/core/bignum/case_compare_spec.rb6
-rw-r--r--spec/rubyspec/core/bignum/coerce_spec.rb65
-rw-r--r--spec/rubyspec/core/bignum/comparison_spec.rb162
-rw-r--r--spec/rubyspec/core/bignum/complement_spec.rb9
-rw-r--r--spec/rubyspec/core/bignum/div_spec.rb21
-rw-r--r--spec/rubyspec/core/bignum/divide_spec.rb18
-rw-r--r--spec/rubyspec/core/bignum/divmod_spec.rb81
-rw-r--r--spec/rubyspec/core/bignum/element_reference_spec.rb30
-rw-r--r--spec/rubyspec/core/bignum/eql_spec.rb22
-rw-r--r--spec/rubyspec/core/bignum/equal_value_spec.rb6
-rw-r--r--spec/rubyspec/core/bignum/even_spec.rb19
-rw-r--r--spec/rubyspec/core/bignum/exponent_spec.rb29
-rw-r--r--spec/rubyspec/core/bignum/fdiv_spec.rb5
-rw-r--r--spec/rubyspec/core/bignum/gt_spec.rb20
-rw-r--r--spec/rubyspec/core/bignum/gte_spec.rb19
-rw-r--r--spec/rubyspec/core/bignum/hash_spec.rb12
-rw-r--r--spec/rubyspec/core/bignum/left_shift_spec.rb73
-rw-r--r--spec/rubyspec/core/bignum/lt_spec.rb22
-rw-r--r--spec/rubyspec/core/bignum/lte_spec.rb24
-rw-r--r--spec/rubyspec/core/bignum/magnitude_spec.rb6
-rw-r--r--spec/rubyspec/core/bignum/minus_spec.rb19
-rw-r--r--spec/rubyspec/core/bignum/modulo_spec.rb10
-rw-r--r--spec/rubyspec/core/bignum/multiply_spec.rb20
-rw-r--r--spec/rubyspec/core/bignum/odd_spec.rb19
-rw-r--r--spec/rubyspec/core/bignum/plus_spec.rb19
-rw-r--r--spec/rubyspec/core/bignum/remainder_spec.rb21
-rw-r--r--spec/rubyspec/core/bignum/right_shift_spec.rb99
-rw-r--r--spec/rubyspec/core/bignum/shared/abs.rb6
-rw-r--r--spec/rubyspec/core/bignum/shared/divide.rb27
-rw-r--r--spec/rubyspec/core/bignum/shared/equal.rb31
-rw-r--r--spec/rubyspec/core/bignum/shared/modulo.rb29
-rw-r--r--spec/rubyspec/core/bignum/size_spec.rb16
-rw-r--r--spec/rubyspec/core/bignum/to_f_spec.rb13
-rw-r--r--spec/rubyspec/core/bignum/to_s_spec.rb48
-rw-r--r--spec/rubyspec/core/bignum/uminus_spec.rb11
41 files changed, 1222 insertions, 0 deletions
diff --git a/spec/rubyspec/core/bignum/abs_spec.rb b/spec/rubyspec/core/bignum/abs_spec.rb
new file mode 100644
index 0000000000..b551dd95ad
--- /dev/null
+++ b/spec/rubyspec/core/bignum/abs_spec.rb
@@ -0,0 +1,7 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+require File.expand_path('../shared/abs', __FILE__)
+
+describe "Bignum#abs" do
+ it_behaves_like(:bignum_abs, :abs)
+end
+
diff --git a/spec/rubyspec/core/bignum/bignum_spec.rb b/spec/rubyspec/core/bignum/bignum_spec.rb
new file mode 100644
index 0000000000..b723718f69
--- /dev/null
+++ b/spec/rubyspec/core/bignum/bignum_spec.rb
@@ -0,0 +1,7 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum" do
+ it "includes Comparable" do
+ Bignum.include?(Comparable).should == true
+ end
+end
diff --git a/spec/rubyspec/core/bignum/bit_and_spec.rb b/spec/rubyspec/core/bignum/bit_and_spec.rb
new file mode 100644
index 0000000000..6eca0e56f0
--- /dev/null
+++ b/spec/rubyspec/core/bignum/bit_and_spec.rb
@@ -0,0 +1,50 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#&" do
+ before :each do
+ @bignum = bignum_value(5)
+ end
+
+ it "returns self bitwise AND other" do
+ @bignum = bignum_value(5)
+ (@bignum & 3).should == 1
+ (@bignum & 52).should == 4
+ (@bignum & bignum_value(9921)).should == 9223372036854775809
+
+ ((2*bignum_value) & 1).should == 0
+ ((2*bignum_value) & (2*bignum_value)).should == 18446744073709551616
+ end
+
+ it "returns self bitwise AND other when one operand is negative" do
+ ((2*bignum_value) & -1).should == 18446744073709551616
+ ((4*bignum_value) & -1).should == 36893488147419103232
+ (@bignum & -0xffffffffffffff5).should == 9223372036854775809
+ (@bignum & -@bignum).should == 1
+ (@bignum & -0x8000000000000000).should == 9223372036854775808
+ end
+
+ it "returns self bitwise AND other when both operands are negative" do
+ (-@bignum & -0x4000000000000005).should == -13835058055282163717
+ (-@bignum & -@bignum).should == -9223372036854775813
+ (-@bignum & -0x4000000000000000).should == -13835058055282163712
+ end
+
+ it "returns self bitwise AND other when both are negative and a multiple in bitsize of Fixnum::MIN" do
+ val = - ((1 << 93) - 1)
+ (val & val).should == val
+
+ val = - ((1 << 126) - 1)
+ (val & val).should == val
+ end
+
+ it "raises a TypeError when passed a Float" do
+ lambda { (@bignum & 3.4) }.should raise_error(TypeError)
+ end
+
+ it "raises a TypeError and does not call #to_int when defined on an object" do
+ obj = mock("bignum bit and")
+ obj.should_not_receive(:to_int)
+
+ lambda { @bignum & obj }.should raise_error(TypeError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/bit_length_spec.rb b/spec/rubyspec/core/bignum/bit_length_spec.rb
new file mode 100644
index 0000000000..1c4c518345
--- /dev/null
+++ b/spec/rubyspec/core/bignum/bit_length_spec.rb
@@ -0,0 +1,33 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#bit_length" do
+ it "returns the position of the leftmost bit of a positive number" do
+ (2**1000-1).bit_length.should == 1000
+ (2**1000).bit_length.should == 1001
+ (2**1000+1).bit_length.should == 1001
+
+ (2**10000-1).bit_length.should == 10000
+ (2**10000).bit_length.should == 10001
+ (2**10000+1).bit_length.should == 10001
+
+ (1 << 100).bit_length.should == 101
+ (1 << 100).succ.bit_length.should == 101
+ (1 << 100).pred.bit_length.should == 100
+ (1 << 10000).bit_length.should == 10001
+ end
+
+ it "returns the position of the leftmost 0 bit of a negative number" do
+ (-2**10000-1).bit_length.should == 10001
+ (-2**10000).bit_length.should == 10000
+ (-2**10000+1).bit_length.should == 10000
+
+ (-2**1000-1).bit_length.should == 1001
+ (-2**1000).bit_length.should == 1000
+ (-2**1000+1).bit_length.should == 1000
+
+ ((-1 << 100)-1).bit_length.should == 101
+ ((-1 << 100)-1).succ.bit_length.should == 100
+ ((-1 << 100)-1).pred.bit_length.should == 101
+ ((-1 << 10000)-1).bit_length.should == 10001
+ end
+end
diff --git a/spec/rubyspec/core/bignum/bit_or_spec.rb b/spec/rubyspec/core/bignum/bit_or_spec.rb
new file mode 100644
index 0000000000..6bcb6ead6b
--- /dev/null
+++ b/spec/rubyspec/core/bignum/bit_or_spec.rb
@@ -0,0 +1,41 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#|" do
+ before :each do
+ @bignum = bignum_value(11)
+ end
+
+ it "returns self bitwise OR other" do
+ (@bignum | 2).should == 9223372036854775819
+ (@bignum | 9).should == 9223372036854775819
+ (@bignum | bignum_value).should == 9223372036854775819
+ end
+
+ it "returns self bitwise OR other when one operand is negative" do
+ (@bignum | -0x40000000000000000).should == -64563604257983430645
+ (@bignum | -@bignum).should == -1
+ (@bignum | -0x8000000000000000).should == -9223372036854775797
+ end
+
+ it "returns self bitwise OR other when both operands are negative" do
+ (-@bignum | -0x4000000000000005).should == -1
+ (-@bignum | -@bignum).should == -9223372036854775819
+ (-@bignum | -0x4000000000000000).should == -11
+ end
+
+ it "raises a TypeError when passed a Float" do
+ not_supported_on :opal do
+ lambda {
+ bignum_value | bignum_value(0xffff).to_f
+ }.should raise_error(TypeError)
+ end
+ lambda { @bignum | 9.9 }.should raise_error(TypeError)
+ end
+
+ it "raises a TypeError and does not call #to_int when defined on an object" do
+ obj = mock("bignum bit or")
+ obj.should_not_receive(:to_int)
+
+ lambda { @bignum | obj }.should raise_error(TypeError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/bit_xor_spec.rb b/spec/rubyspec/core/bignum/bit_xor_spec.rb
new file mode 100644
index 0000000000..ef4b4e6ae3
--- /dev/null
+++ b/spec/rubyspec/core/bignum/bit_xor_spec.rb
@@ -0,0 +1,47 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#^" do
+ before :each do
+ @bignum = bignum_value(18)
+ end
+
+ it "returns self bitwise EXCLUSIVE OR other" do
+ (@bignum ^ 2).should == 9223372036854775824
+ (@bignum ^ @bignum).should == 0
+ (@bignum ^ 14).should == 9223372036854775836
+ end
+
+ it "returns self bitwise EXCLUSIVE OR other when one operand is negative" do
+ (@bignum ^ -0x40000000000000000).should == -64563604257983430638
+ (@bignum ^ -@bignum).should == -4
+ (@bignum ^ -0x8000000000000000).should == -18446744073709551598
+ end
+
+ it "returns self bitwise EXCLUSIVE OR other when both operands are negative" do
+ (-@bignum ^ -0x40000000000000000).should == 64563604257983430638
+ (-@bignum ^ -@bignum).should == 0
+ (-@bignum ^ -0x4000000000000000).should == 13835058055282163694
+ end
+
+ it "returns self bitwise EXCLUSIVE OR other when all bits are 1 and other value is negative" do
+ (9903520314283042199192993791 ^ -1).should == -9903520314283042199192993792
+ (784637716923335095479473677900958302012794430558004314111 ^ -1).should ==
+ -784637716923335095479473677900958302012794430558004314112
+ end
+
+ it "raises a TypeError when passed a Float" do
+ not_supported_on :opal do
+ lambda {
+ bignum_value ^ bignum_value(0xffff).to_f
+ }.should raise_error(TypeError)
+ end
+ lambda { @bignum ^ 14.5 }.should raise_error(TypeError)
+ end
+
+ it "raises a TypeError and does not call #to_int when defined on an object" do
+ obj = mock("bignum bit xor")
+ obj.should_not_receive(:to_int)
+
+ lambda { @bignum ^ obj }.should raise_error(TypeError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/case_compare_spec.rb b/spec/rubyspec/core/bignum/case_compare_spec.rb
new file mode 100644
index 0000000000..d7e0a89487
--- /dev/null
+++ b/spec/rubyspec/core/bignum/case_compare_spec.rb
@@ -0,0 +1,6 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+require File.expand_path('../shared/equal', __FILE__)
+
+describe "Bignum#===" do
+ it_behaves_like :bignum_equal, :===
+end
diff --git a/spec/rubyspec/core/bignum/coerce_spec.rb b/spec/rubyspec/core/bignum/coerce_spec.rb
new file mode 100644
index 0000000000..40decaf51a
--- /dev/null
+++ b/spec/rubyspec/core/bignum/coerce_spec.rb
@@ -0,0 +1,65 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#coerce" do
+ it "coerces other to a Bignum and returns [other, self] when passed a Fixnum" do
+ a = bignum_value
+ ary = a.coerce(2)
+
+ ary[0].should be_kind_of(Bignum)
+ ary[1].should be_kind_of(Bignum)
+ ary.should == [2, a]
+ end
+
+ it "returns [other, self] when passed a Bignum" do
+ a = bignum_value
+ b = bignum_value
+ ary = a.coerce(b)
+
+ ary[0].should be_kind_of(Bignum)
+ ary[1].should be_kind_of(Bignum)
+ ary.should == [b, a]
+ end
+
+ it "raises a TypeError when not passed a Fixnum or Bignum" do
+ a = bignum_value
+
+ lambda { a.coerce(nil) }.should raise_error(TypeError)
+ lambda { a.coerce(mock('str')) }.should raise_error(TypeError)
+ lambda { a.coerce(1..4) }.should raise_error(TypeError)
+ lambda { a.coerce(:test) }.should raise_error(TypeError)
+ end
+
+ ruby_version_is ""..."2.4" do
+ it "raises a TypeError when passed a String" do
+ a = bignum_value
+ lambda { a.coerce("123") }.should raise_error(TypeError)
+ end
+
+ it "raises a TypeError when passed a Float" do
+ a = bignum_value
+ lambda { a.coerce(12.3) }.should raise_error(TypeError)
+ end
+ end
+
+ ruby_version_is "2.4" do
+ it "coerces both values to Floats and returns [other, self] when passed a Float" do
+ a = bignum_value
+ a.coerce(1.2).should == [1.2, a.to_f]
+ end
+
+ it "coerces both values to Floats and returns [other, self] when passed a String" do
+ a = bignum_value
+ a.coerce("123").should == [123.0, a.to_f]
+ end
+
+ it "calls #to_f to coerce other to a Float" do
+ b = mock("bignum value")
+ b.should_receive(:to_f).and_return(1.2)
+
+ a = bignum_value
+ ary = a.coerce(b)
+
+ ary.should == [1.2, a.to_f]
+ end
+ end
+end
diff --git a/spec/rubyspec/core/bignum/comparison_spec.rb b/spec/rubyspec/core/bignum/comparison_spec.rb
new file mode 100644
index 0000000000..435cc9aea2
--- /dev/null
+++ b/spec/rubyspec/core/bignum/comparison_spec.rb
@@ -0,0 +1,162 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#<=>" do
+ describe "with a Fixnum" do
+ it "returns -1 when other is larger" do
+ (-bignum_value <=> 2).should == -1
+ end
+
+ it "returns 1 when other is smaller" do
+ (bignum_value <=> 2).should == 1
+ end
+ end
+
+ describe "with a Bignum" do
+ describe "when other is negative" do
+ it "returns -1 when self is negative and other is larger" do
+ (-bignum_value(42) <=> -bignum_value).should == -1
+ end
+
+ it "returns 0 when other is equal" do
+ (-bignum_value <=> -bignum_value).should == 0
+ end
+
+ it "returns 1 when self is negative and other is smaller" do
+ (-bignum_value <=> -bignum_value(94)).should == 1
+ end
+
+ it "returns 1 when self is positive" do
+ (bignum_value <=> -bignum_value).should == 1
+ end
+ end
+
+ describe "when other is positive" do
+ it "returns -1 when self is negative" do
+ (-bignum_value <=> bignum_value).should == -1
+ end
+
+ it "returns -1 when self is positive and other is larger" do
+ (bignum_value <=> bignum_value(38)).should == -1
+ end
+
+ it "returns 0 when other is equal" do
+ (bignum_value <=> bignum_value).should == 0
+ end
+
+ it "returns 1 when other is smaller" do
+ (bignum_value(56) <=> bignum_value).should == 1
+ end
+ end
+ end
+
+ describe "with a Float" do
+ describe "when other is negative" do
+ it "returns -1 when self is negative and other is larger" do
+ (-bignum_value(0xffff) <=> -bignum_value.to_f).should == -1
+ end
+
+ it "returns 0 when other is equal" do
+ (-bignum_value <=> -bignum_value.to_f).should == 0
+ end
+
+ it "returns 1 when self is negative and other is smaller" do
+ (-bignum_value <=> -bignum_value(0xffef).to_f).should == 1
+ end
+
+ it "returns 1 when self is positive" do
+ (bignum_value <=> -bignum_value.to_f).should == 1
+ end
+ end
+
+ describe "when other is positive" do
+ it "returns -1 when self is negative" do
+ (-bignum_value <=> bignum_value.to_f).should == -1
+ end
+
+ it "returns -1 when self is positive and other is larger" do
+ (bignum_value <=> bignum_value(0xfffe).to_f).should == -1
+ end
+
+ it "returns 0 when other is equal" do
+ (bignum_value <=> bignum_value.to_f).should == 0
+ end
+
+ it "returns 1 when other is smaller" do
+ (bignum_value(0xfeff) <=> bignum_value.to_f).should == 1
+ end
+ end
+ end
+
+ describe "with an Object" do
+ before :each do
+ @big = bignum_value
+ @num = mock("value for Bignum#<=>")
+ end
+
+ it "calls #coerce on other" do
+ @num.should_receive(:coerce).with(@big).and_return([@big.to_f, 2.5])
+ @big <=> @num
+ end
+
+ ruby_version_is ""..."2.5" do
+ it "returns nil if #coerce raises an exception" do
+ @num.should_receive(:coerce).with(@big).and_raise(RuntimeError)
+ lambda {
+ @result = (@big <=> @num)
+ }.should complain(/Numerical comparison operators will no more rescue exceptions/)
+ @result.should be_nil
+ end
+ end
+
+ ruby_version_is "2.5" do
+ it "lets the exception go through if #coerce raises an exception" do
+ @num.should_receive(:coerce).with(@big).and_raise(RuntimeError.new("my error"))
+ lambda {
+ @big <=> @num
+ }.should raise_error(RuntimeError, "my error")
+ end
+ end
+
+ it "raises an exception if #coerce raises a non-StandardError exception" do
+ @num.should_receive(:coerce).with(@big).and_raise(Exception)
+ lambda { @big <=> @num }.should raise_error(Exception)
+ end
+
+ it "returns nil if #coerce does not return an Array" do
+ @num.should_receive(:coerce).with(@big).and_return(nil)
+ (@big <=> @num).should be_nil
+ end
+
+ it "returns -1 if the coerced value is larger" do
+ @num.should_receive(:coerce).with(@big).and_return([@big, bignum_value(10)])
+ (@big <=> @num).should == -1
+ end
+
+ it "returns 0 if the coerced value is equal" do
+ @num.should_receive(:coerce).with(@big).and_return([@big, bignum_value])
+ (@big <=> @num).should == 0
+ end
+
+ it "returns 1 if the coerced value is smaller" do
+ @num.should_receive(:coerce).with(@big).and_return([@big, 22])
+ (@big <=> @num).should == 1
+ end
+ end
+
+ # The tests below are taken from matz's revision 23730 for Ruby trunk
+ it "returns 1 when self is Infinity and other is a Bignum" do
+ (infinity_value <=> Float::MAX.to_i*2).should == 1
+ end
+
+ it "returns -1 when self is negative and other is Infinty" do
+ (-Float::MAX.to_i*2 <=> infinity_value).should == -1
+ end
+
+ it "returns 1 when self is negative and other is -Infinity" do
+ (-Float::MAX.to_i*2 <=> -infinity_value).should == 1
+ end
+
+ it "returns -1 when self is -Infinity and other is negative" do
+ (-infinity_value <=> -Float::MAX.to_i*2).should == -1
+ end
+end
diff --git a/spec/rubyspec/core/bignum/complement_spec.rb b/spec/rubyspec/core/bignum/complement_spec.rb
new file mode 100644
index 0000000000..be6bc21b19
--- /dev/null
+++ b/spec/rubyspec/core/bignum/complement_spec.rb
@@ -0,0 +1,9 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#~" do
+ it "returns self with each bit flipped" do
+ (~bignum_value(48)).should == -9223372036854775857
+ (~(-bignum_value(21))).should == 9223372036854775828
+ (~bignum_value(1)).should == -9223372036854775810
+ end
+end
diff --git a/spec/rubyspec/core/bignum/div_spec.rb b/spec/rubyspec/core/bignum/div_spec.rb
new file mode 100644
index 0000000000..6c165289e8
--- /dev/null
+++ b/spec/rubyspec/core/bignum/div_spec.rb
@@ -0,0 +1,21 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+require File.expand_path('../shared/divide', __FILE__)
+
+describe "Bignum#div" do
+ it_behaves_like(:bignum_divide, :div)
+
+ it "returns a result of integer division of self by a float argument" do
+ bignum_value(88).div(4294967295.5).should eql(2147483648)
+ not_supported_on :opal do
+ bignum_value(88).div(4294967295.0).should eql(2147483648)
+ bignum_value(88).div(bignum_value(88).to_f).should eql(1)
+ bignum_value(88).div(-bignum_value(88).to_f).should eql(-1)
+ end
+ end
+
+ # #5490
+ it "raises ZeroDivisionError if the argument is Float zero" do
+ lambda { bignum_value(88).div(0.0) }.should raise_error(ZeroDivisionError)
+ lambda { bignum_value(88).div(-0.0) }.should raise_error(ZeroDivisionError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/divide_spec.rb b/spec/rubyspec/core/bignum/divide_spec.rb
new file mode 100644
index 0000000000..b81938b707
--- /dev/null
+++ b/spec/rubyspec/core/bignum/divide_spec.rb
@@ -0,0 +1,18 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+require File.expand_path('../shared/divide', __FILE__)
+
+describe "Bignum#/" do
+ it_behaves_like(:bignum_divide, :/)
+
+ it "returns self divided by float" do
+ not_supported_on :opal do
+ (bignum_value(88) / 4294967295.0).should be_close(2147483648.5, TOLERANCE)
+ end
+ (bignum_value(88) / 4294967295.5).should be_close(2147483648.25, TOLERANCE)
+ end
+
+ it "does NOT raise ZeroDivisionError if other is zero and is a Float" do
+ (bignum_value / 0.0).to_s.should == 'Infinity'
+ (bignum_value / -0.0).to_s.should == '-Infinity'
+ end
+end
diff --git a/spec/rubyspec/core/bignum/divmod_spec.rb b/spec/rubyspec/core/bignum/divmod_spec.rb
new file mode 100644
index 0000000000..656f23482b
--- /dev/null
+++ b/spec/rubyspec/core/bignum/divmod_spec.rb
@@ -0,0 +1,81 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#divmod" do
+ before :each do
+ @bignum = bignum_value(55)
+ end
+
+ # Based on MRI's test/test_integer.rb (test_divmod),
+ # MRI maintains the following property:
+ # if q, r = a.divmod(b) ==>
+ # assert(0 < b ? (0 <= r && r < b) : (b < r && r <= 0))
+ # So, r is always between 0 and b.
+ it "returns an Array containing quotient and modulus obtained from dividing self by the given argument" do
+ @bignum.divmod(4).should == [2305843009213693965, 3]
+ @bignum.divmod(13).should == [709490156681136604, 11]
+
+ @bignum.divmod(4.5).should == [2049638230412172288, 3.5]
+
+ not_supported_on :opal do
+ @bignum.divmod(4.0).should == [2305843009213693952, 0.0]
+ @bignum.divmod(13.0).should == [709490156681136640, 8.0]
+
+ @bignum.divmod(2.0).should == [4611686018427387904, 0.0]
+ end
+
+ @bignum.divmod(bignum_value).should == [1, 55]
+
+ (-(10**50)).divmod(-(10**40 + 1)).should == [9999999999, -9999999999999999999999999999990000000001]
+ (10**50).divmod(10**40 + 1).should == [9999999999, 9999999999999999999999999999990000000001]
+
+ (-10**50).divmod(10**40 + 1).should == [-10000000000, 10000000000]
+ (10**50).divmod(-(10**40 + 1)).should == [-10000000000, -10000000000]
+ end
+
+ describe "with q = floor(x/y), a = q*b + r," do
+ it "returns [q,r] when a < 0, b > 0 and |a| < b" do
+ a = -@bignum + 1
+ b = @bignum
+ a.divmod(b).should == [-1, 1]
+ end
+
+ it "returns [q,r] when a > 0, b < 0 and a > |b|" do
+ b = -@bignum + 1
+ a = @bignum
+ a.divmod(b).should == [-2, -@bignum + 2]
+ end
+
+ it "returns [q,r] when a > 0, b < 0 and a < |b|" do
+ a = @bignum - 1
+ b = -@bignum
+ a.divmod(b).should == [-1, -1]
+ end
+
+ it "returns [q,r] when a < 0, b < 0 and |a| < |b|" do
+ a = -@bignum + 1
+ b = -@bignum
+ a.divmod(b).should == [0, -@bignum + 1]
+ end
+ end
+
+ it "raises a ZeroDivisionError when the given argument is 0" do
+ lambda { @bignum.divmod(0) }.should raise_error(ZeroDivisionError)
+ lambda { (-@bignum).divmod(0) }.should raise_error(ZeroDivisionError)
+ end
+
+ # Behaviour established as correct in r23953
+ it "raises a FloatDomainError if other is NaN" do
+ lambda { @bignum.divmod(nan_value) }.should raise_error(FloatDomainError)
+ end
+
+ it "raises a ZeroDivisionError when the given argument is 0 and a Float" do
+ lambda { @bignum.divmod(0.0) }.should raise_error(ZeroDivisionError)
+ lambda { (-@bignum).divmod(0.0) }.should raise_error(ZeroDivisionError)
+ end
+
+ it "raises a TypeError when the given argument is not an Integer" do
+ lambda { @bignum.divmod(mock('10')) }.should raise_error(TypeError)
+ lambda { @bignum.divmod("10") }.should raise_error(TypeError)
+ lambda { @bignum.divmod(:symbol) }.should raise_error(TypeError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/element_reference_spec.rb b/spec/rubyspec/core/bignum/element_reference_spec.rb
new file mode 100644
index 0000000000..e5ee9e15ac
--- /dev/null
+++ b/spec/rubyspec/core/bignum/element_reference_spec.rb
@@ -0,0 +1,30 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#[]" do
+ before :each do
+ @bignum = bignum_value(4996)
+ end
+
+ it "returns the nth bit in the binary representation of self" do
+ @bignum[2].should == 1
+ @bignum[9.2].should == 1
+ @bignum[21].should == 0
+ @bignum[0xffffffff].should == 0
+ @bignum[-0xffffffff].should == 0
+ end
+
+ it "tries to convert the given argument to an Integer using #to_int" do
+ @bignum[1.3].should == @bignum[1]
+
+ (obj = mock('2')).should_receive(:to_int).at_least(1).and_return(2)
+ @bignum[obj].should == 1
+ end
+
+ it "raises a TypeError when the given argument can't be converted to Integer" do
+ obj = mock('asdf')
+ lambda { @bignum[obj] }.should raise_error(TypeError)
+
+ obj.should_receive(:to_int).and_return("asdf")
+ lambda { @bignum[obj] }.should raise_error(TypeError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/eql_spec.rb b/spec/rubyspec/core/bignum/eql_spec.rb
new file mode 100644
index 0000000000..c9eff9ef08
--- /dev/null
+++ b/spec/rubyspec/core/bignum/eql_spec.rb
@@ -0,0 +1,22 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#eql? when given a Bignum" do
+ it "returns true if the given argument has the same value" do
+ a = bignum_value(13)
+ a.should eql(bignum_value(13))
+ (-a).should eql(-bignum_value(13))
+ end
+end
+
+describe "Bignum#eql? when given a non-Bignum" do
+ it "returns false" do
+ a = bignum_value(13)
+ a.should_not eql(a.to_f)
+
+ a.should_not eql(2)
+ a.should_not eql(3.14)
+ a.should_not eql(:symbol)
+ a.should_not eql("String")
+ a.should_not eql(mock('str'))
+ end
+end
diff --git a/spec/rubyspec/core/bignum/equal_value_spec.rb b/spec/rubyspec/core/bignum/equal_value_spec.rb
new file mode 100644
index 0000000000..0117d58683
--- /dev/null
+++ b/spec/rubyspec/core/bignum/equal_value_spec.rb
@@ -0,0 +1,6 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+require File.expand_path('../shared/equal', __FILE__)
+
+describe "Bignum#==" do
+ it_behaves_like :bignum_equal, :==
+end
diff --git a/spec/rubyspec/core/bignum/even_spec.rb b/spec/rubyspec/core/bignum/even_spec.rb
new file mode 100644
index 0000000000..a84ea80075
--- /dev/null
+++ b/spec/rubyspec/core/bignum/even_spec.rb
@@ -0,0 +1,19 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#even?" do
+ it "returns true if self is even and positive" do
+ (10000**10).even?.should be_true
+ end
+
+ it "returns true if self is even and negative" do
+ (-10000**10).even?.should be_true
+ end
+
+ it "returns false if self is odd and positive" do
+ (9879**976).even?.should be_false
+ end
+
+ it "returns false if self is odd and negative" do
+ (-9879**976).even?.should be_false
+ end
+end
diff --git a/spec/rubyspec/core/bignum/exponent_spec.rb b/spec/rubyspec/core/bignum/exponent_spec.rb
new file mode 100644
index 0000000000..f69da833fd
--- /dev/null
+++ b/spec/rubyspec/core/bignum/exponent_spec.rb
@@ -0,0 +1,29 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#**" do
+ before :each do
+ @bignum = bignum_value(47)
+ end
+
+ it "returns self raised to other power" do
+ (@bignum ** 4).should == 7237005577332262361485077344629993318496048279512298547155833600056910050625
+ (@bignum ** 1.2).should be_close(57262152889751597425762.57804, TOLERANCE)
+ end
+
+ it "raises a TypeError when given a non-Integer" do
+ lambda { @bignum ** mock('10') }.should raise_error
+ lambda { @bignum ** "10" }.should raise_error
+ lambda { @bignum ** :symbol }.should raise_error
+ end
+
+ it "switch to a Float when the values is too big" do
+ flt = (@bignum ** @bignum)
+ flt.should be_kind_of(Float)
+ flt.infinite?.should == 1
+ end
+
+ it "returns a complex number when negative and raised to a fractional power" do
+ ((-@bignum) ** (1.0/3)) .should be_close(Complex(1048576,1816186.907597341), TOLERANCE)
+ ((-@bignum) ** Rational(1,3)).should be_close(Complex(1048576,1816186.907597341), TOLERANCE)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/fdiv_spec.rb b/spec/rubyspec/core/bignum/fdiv_spec.rb
new file mode 100644
index 0000000000..35f3ede010
--- /dev/null
+++ b/spec/rubyspec/core/bignum/fdiv_spec.rb
@@ -0,0 +1,5 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#fdiv" do
+ it "needs to be reviewed for spec completeness"
+end
diff --git a/spec/rubyspec/core/bignum/gt_spec.rb b/spec/rubyspec/core/bignum/gt_spec.rb
new file mode 100644
index 0000000000..5c814eedd1
--- /dev/null
+++ b/spec/rubyspec/core/bignum/gt_spec.rb
@@ -0,0 +1,20 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#>" do
+ before :each do
+ @bignum = bignum_value(732)
+ end
+
+ it "returns true if self is greater than the given argument" do
+ (@bignum > (@bignum - 1)).should == true
+ (@bignum > 14.6).should == true
+ (@bignum > 10).should == true
+
+ (@bignum > (@bignum + 500)).should == false
+ end
+
+ it "raises an ArgumentError when given a non-Integer" do
+ lambda { @bignum > "4" }.should raise_error(ArgumentError)
+ lambda { @bignum > mock('str') }.should raise_error(ArgumentError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/gte_spec.rb b/spec/rubyspec/core/bignum/gte_spec.rb
new file mode 100644
index 0000000000..e32ce19e0f
--- /dev/null
+++ b/spec/rubyspec/core/bignum/gte_spec.rb
@@ -0,0 +1,19 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#>=" do
+ before :each do
+ @bignum = bignum_value(14)
+ end
+
+ it "returns true if self is greater than or equal to other" do
+ (@bignum >= @bignum).should == true
+ (@bignum >= (@bignum + 2)).should == false
+ (@bignum >= 5664.2).should == true
+ (@bignum >= 4).should == true
+ end
+
+ it "raises an ArgumentError when given a non-Integer" do
+ lambda { @bignum >= "4" }.should raise_error(ArgumentError)
+ lambda { @bignum >= mock('str') }.should raise_error(ArgumentError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/hash_spec.rb b/spec/rubyspec/core/bignum/hash_spec.rb
new file mode 100644
index 0000000000..bdc85c3fdc
--- /dev/null
+++ b/spec/rubyspec/core/bignum/hash_spec.rb
@@ -0,0 +1,12 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#hash" do
+ it "is provided" do
+ bignum_value.respond_to?(:hash).should == true
+ end
+
+ it "is stable" do
+ bignum_value.hash.should == bignum_value.hash
+ bignum_value.hash.should_not == bignum_value(1).hash
+ end
+end
diff --git a/spec/rubyspec/core/bignum/left_shift_spec.rb b/spec/rubyspec/core/bignum/left_shift_spec.rb
new file mode 100644
index 0000000000..364f51b708
--- /dev/null
+++ b/spec/rubyspec/core/bignum/left_shift_spec.rb
@@ -0,0 +1,73 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#<< with n << m" do
+ before :each do
+ @bignum = bignum_value * 16
+ end
+
+ it "returns n shifted left m bits when n > 0, m > 0" do
+ (@bignum << 4).should == 2361183241434822606848
+ end
+
+ it "returns n shifted left m bits when n < 0, m > 0" do
+ (-@bignum << 9).should == -75557863725914323419136
+ end
+
+ it "returns n shifted right m bits when n > 0, m < 0" do
+ (@bignum << -1).should == 73786976294838206464
+ end
+
+ it "returns n shifted right m bits when n < 0, m < 0" do
+ (-@bignum << -2).should == -36893488147419103232
+ end
+
+ it "returns n when n > 0, m == 0" do
+ (@bignum << 0).should == @bignum
+ end
+
+ it "returns n when n < 0, m == 0" do
+ (-@bignum << 0).should == -@bignum
+ end
+
+ it "returns 0 when m < 0 and m == p where 2**p > n >= 2**(p-1)" do
+ (@bignum << -68).should == 0
+ end
+
+ it "returns 0 when m < 0 and m is a Bignum" do
+ (@bignum << -bignum_value).should == 0
+ end
+
+ it "returns a Fixnum == fixnum_max when (fixnum_max * 2) << -1 and n > 0" do
+ result = (fixnum_max * 2) << -1
+ result.should be_an_instance_of(Fixnum)
+ result.should == fixnum_max
+ end
+
+ it "returns a Fixnum == fixnum_min when (fixnum_min * 2) << -1 and n < 0" do
+ result = (fixnum_min * 2) << -1
+ result.should be_an_instance_of(Fixnum)
+ result.should == fixnum_min
+ end
+
+ it "calls #to_int to convert the argument to an Integer" do
+ obj = mock("4")
+ obj.should_receive(:to_int).and_return(4)
+
+ (@bignum << obj).should == 2361183241434822606848
+ end
+
+ it "raises a TypeError when #to_int does not return an Integer" do
+ obj = mock("a string")
+ obj.should_receive(:to_int).and_return("asdf")
+
+ lambda { @bignum << obj }.should raise_error(TypeError)
+ end
+
+ it "raises a TypeError when passed nil" do
+ lambda { @bignum << nil }.should raise_error(TypeError)
+ end
+
+ it "raises a TypeError when passed a String" do
+ lambda { @bignum << "4" }.should raise_error(TypeError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/lt_spec.rb b/spec/rubyspec/core/bignum/lt_spec.rb
new file mode 100644
index 0000000000..802c68a58b
--- /dev/null
+++ b/spec/rubyspec/core/bignum/lt_spec.rb
@@ -0,0 +1,22 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#<" do
+ before :each do
+ @bignum = bignum_value(32)
+ end
+
+ it "returns true if self is less than the given argument" do
+ (@bignum < @bignum + 1).should == true
+ (-@bignum < -(@bignum - 1)).should == true
+
+ (@bignum < 1).should == false
+ (@bignum < 5).should == false
+
+ (@bignum < 4.999).should == false
+ end
+
+ it "raises an ArgumentError when given a non-Integer" do
+ lambda { @bignum < "4" }.should raise_error(ArgumentError)
+ lambda { @bignum < mock('str') }.should raise_error(ArgumentError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/lte_spec.rb b/spec/rubyspec/core/bignum/lte_spec.rb
new file mode 100644
index 0000000000..9a1d22d3be
--- /dev/null
+++ b/spec/rubyspec/core/bignum/lte_spec.rb
@@ -0,0 +1,24 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#<=" do
+ before :each do
+ @bignum = bignum_value(39)
+ end
+
+ it "returns true if self is less than or equal to other" do
+ (@bignum <= @bignum).should == true
+ (-@bignum <= -(@bignum - 1)).should == true
+
+ (@bignum <= 4.999).should == false
+ end
+
+ it "returns false if compares with near float" do
+ (@bignum <= (@bignum + 0.0)).should == false
+ (@bignum <= (@bignum + 0.5)).should == false
+ end
+
+ it "raises an ArgumentError when given a non-Integer" do
+ lambda { @bignum <= "4" }.should raise_error(ArgumentError)
+ lambda { @bignum <= mock('str') }.should raise_error(ArgumentError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/magnitude_spec.rb b/spec/rubyspec/core/bignum/magnitude_spec.rb
new file mode 100644
index 0000000000..35b9ba6f1e
--- /dev/null
+++ b/spec/rubyspec/core/bignum/magnitude_spec.rb
@@ -0,0 +1,6 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+require File.expand_path('../shared/abs', __FILE__)
+
+describe "Bignum#magnitude" do
+ it_behaves_like(:bignum_abs, :magnitude)
+end
diff --git a/spec/rubyspec/core/bignum/minus_spec.rb b/spec/rubyspec/core/bignum/minus_spec.rb
new file mode 100644
index 0000000000..754ef7fa42
--- /dev/null
+++ b/spec/rubyspec/core/bignum/minus_spec.rb
@@ -0,0 +1,19 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#-" do
+ before :each do
+ @bignum = bignum_value(314)
+ end
+
+ it "returns self minus the given Integer" do
+ (@bignum - 9).should == 9223372036854776113
+ (@bignum - 12.57).should be_close(9223372036854776109.43, TOLERANCE)
+ (@bignum - bignum_value(42)).should == 272
+ end
+
+ it "raises a TypeError when given a non-Integer" do
+ lambda { @bignum - mock('10') }.should raise_error(TypeError)
+ lambda { @bignum - "10" }.should raise_error(TypeError)
+ lambda { @bignum - :symbol }.should raise_error(TypeError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/modulo_spec.rb b/spec/rubyspec/core/bignum/modulo_spec.rb
new file mode 100644
index 0000000000..eee1dc76a6
--- /dev/null
+++ b/spec/rubyspec/core/bignum/modulo_spec.rb
@@ -0,0 +1,10 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+require File.expand_path('../shared/modulo', __FILE__)
+
+describe "Bignum#%" do
+ it_behaves_like(:bignum_modulo, :%)
+end
+
+describe "Bignum#modulo" do
+ it_behaves_like(:bignum_modulo, :modulo)
+end
diff --git a/spec/rubyspec/core/bignum/multiply_spec.rb b/spec/rubyspec/core/bignum/multiply_spec.rb
new file mode 100644
index 0000000000..486e36ecbc
--- /dev/null
+++ b/spec/rubyspec/core/bignum/multiply_spec.rb
@@ -0,0 +1,20 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#*" do
+ before :each do
+ @bignum = bignum_value(772)
+ end
+
+ it "returns self multiplied by the given Integer" do
+ (@bignum * (1/bignum_value(0xffff).to_f)).should be_close(1.0, TOLERANCE)
+ (@bignum * (1/bignum_value(0xffff).to_f)).should be_close(1.0, TOLERANCE)
+ (@bignum * 10).should == 92233720368547765800
+ (@bignum * (@bignum - 40)).should == 85070591730234629737795195287525433200
+ end
+
+ it "raises a TypeError when given a non-Integer" do
+ lambda { @bignum * mock('10') }.should raise_error(TypeError)
+ lambda { @bignum * "10" }.should raise_error(TypeError)
+ lambda { @bignum * :symbol }.should raise_error(TypeError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/odd_spec.rb b/spec/rubyspec/core/bignum/odd_spec.rb
new file mode 100644
index 0000000000..9d4c1191f6
--- /dev/null
+++ b/spec/rubyspec/core/bignum/odd_spec.rb
@@ -0,0 +1,19 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#odd?" do
+ it "returns true if self is odd and positive" do
+ (987279**19).odd?.should be_true
+ end
+
+ it "returns true if self is odd and negative" do
+ (-9873389**97).odd?.should be_true
+ end
+
+ it "returns false if self is even and positive" do
+ (10000000**10).odd?.should be_false
+ end
+
+ it "returns false if self is even and negative" do
+ (-1000000**100).odd?.should be_false
+ end
+end
diff --git a/spec/rubyspec/core/bignum/plus_spec.rb b/spec/rubyspec/core/bignum/plus_spec.rb
new file mode 100644
index 0000000000..411e226649
--- /dev/null
+++ b/spec/rubyspec/core/bignum/plus_spec.rb
@@ -0,0 +1,19 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#+" do
+ before :each do
+ @bignum = bignum_value(76)
+ end
+
+ it "returns self plus the given Integer" do
+ (@bignum + 4).should == 9223372036854775888
+ (@bignum + 4.2).should be_close(9223372036854775888.2, TOLERANCE)
+ (@bignum + bignum_value(3)).should == 18446744073709551695
+ end
+
+ it "raises a TypeError when given a non-Integer" do
+ lambda { @bignum + mock('10') }.should raise_error(TypeError)
+ lambda { @bignum + "10" }.should raise_error(TypeError)
+ lambda { @bignum + :symbol}.should raise_error(TypeError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/remainder_spec.rb b/spec/rubyspec/core/bignum/remainder_spec.rb
new file mode 100644
index 0000000000..59f7eb4326
--- /dev/null
+++ b/spec/rubyspec/core/bignum/remainder_spec.rb
@@ -0,0 +1,21 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#remainder" do
+ it "returns the remainder of dividing self by other" do
+ a = bignum_value(79)
+ a.remainder(2).should == 1
+ a.remainder(97.345).should be_close(46.5674996147722, TOLERANCE)
+ a.remainder(bignum_value).should == 79
+ end
+
+ it "raises a ZeroDivisionError if other is zero and not a Float" do
+ lambda { bignum_value(66).remainder(0) }.should raise_error(ZeroDivisionError)
+ end
+
+ it "does raises ZeroDivisionError if other is zero and a Float" do
+ a = bignum_value(7)
+ b = bignum_value(32)
+ lambda { a.remainder(0.0) }.should raise_error(ZeroDivisionError)
+ lambda { b.remainder(-0.0) }.should raise_error(ZeroDivisionError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/right_shift_spec.rb b/spec/rubyspec/core/bignum/right_shift_spec.rb
new file mode 100644
index 0000000000..d65f7c00a9
--- /dev/null
+++ b/spec/rubyspec/core/bignum/right_shift_spec.rb
@@ -0,0 +1,99 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#>> with n >> m" do
+ before :each do
+ @bignum = bignum_value * 16
+ end
+
+ it "returns n shifted right m bits when n > 0, m > 0" do
+ (@bignum >> 1).should == 73786976294838206464
+ end
+
+ it "returns n shifted right m bits when n < 0, m > 0" do
+ (-@bignum >> 2).should == -36893488147419103232
+ end
+
+ it "respects twos complement signed shifting" do
+ # This explicit left hand value is important because it is the
+ # exact bit pattern that matters, so it's important it's right
+ # here to show the significance.
+ #
+
+ (-42949672980000000000000 >> 14).should == -2621440001220703125
+ (-42949672980000000000001 >> 14).should == -2621440001220703126
+ # Note the off by one -------------------- ^^^^^^^^^^^^^^^^^^^^
+ # This is because even though we discard the lowest bit, in twos
+ # complement it would influence the bits to the left of it.
+
+ (-42949672980000000000000 >> 15).should == -1310720000610351563
+ (-42949672980000000000001 >> 15).should == -1310720000610351563
+
+ (-0xfffffffffffffffff >> 32).should == -68719476736
+ end
+
+ it "respects twos complement signed shifting for very large values" do
+ giant = 42949672980000000000000000000000000000000000000000000000000000000000000000000000000000000000
+ neg = -giant
+
+ (giant >> 84).should == 2220446050284288846538547929770901490087453566957265138626098632812
+ (neg >> 84).should == -2220446050284288846538547929770901490087453566957265138626098632813
+ end
+
+ it "returns n shifted left m bits when n > 0, m < 0" do
+ (@bignum >> -2).should == 590295810358705651712
+ end
+
+ it "returns n shifted left m bits when n < 0, m < 0" do
+ (-@bignum >> -3).should == -1180591620717411303424
+ end
+
+ it "returns n when n > 0, m == 0" do
+ (@bignum >> 0).should == @bignum
+ end
+
+ it "returns n when n < 0, m == 0" do
+ (-@bignum >> 0).should == -@bignum
+ end
+
+ it "returns 0 when m > 0 and m == p where 2**p > n >= 2**(p-1)" do
+ (@bignum >> 68).should == 0
+ end
+
+ it "returns 0 when m is a Bignum" do
+ (@bignum >> bignum_value).should == 0
+ end
+
+ it "returns a Fixnum == fixnum_max when (fixnum_max * 2) >> 1 and n > 0" do
+ result = (fixnum_max * 2) >> 1
+ result.should be_an_instance_of(Fixnum)
+ result.should == fixnum_max
+ end
+
+ it "returns a Fixnum == fixnum_min when (fixnum_min * 2) >> 1 and n < 0" do
+ result = (fixnum_min * 2) >> 1
+ result.should be_an_instance_of(Fixnum)
+ result.should == fixnum_min
+ end
+
+ it "calls #to_int to convert the argument to an Integer" do
+ obj = mock("2")
+ obj.should_receive(:to_int).and_return(2)
+
+ (@bignum >> obj).should == 36893488147419103232
+ end
+
+ it "raises a TypeError when #to_int does not return an Integer" do
+ obj = mock("a string")
+ obj.should_receive(:to_int).and_return("asdf")
+
+ lambda { @bignum >> obj }.should raise_error(TypeError)
+ end
+
+ it "raises a TypeError when passed nil" do
+ lambda { @bignum >> nil }.should raise_error(TypeError)
+ end
+
+ it "raises a TypeError when passed a String" do
+ lambda { @bignum >> "4" }.should raise_error(TypeError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/shared/abs.rb b/spec/rubyspec/core/bignum/shared/abs.rb
new file mode 100644
index 0000000000..35fd85060c
--- /dev/null
+++ b/spec/rubyspec/core/bignum/shared/abs.rb
@@ -0,0 +1,6 @@
+describe :bignum_abs, shared: true do
+ it "returns the absolute value" do
+ bignum_value(39).send(@method).should == 9223372036854775847
+ (-bignum_value(18)).send(@method).should == 9223372036854775826
+ end
+end
diff --git a/spec/rubyspec/core/bignum/shared/divide.rb b/spec/rubyspec/core/bignum/shared/divide.rb
new file mode 100644
index 0000000000..cbde69bbb2
--- /dev/null
+++ b/spec/rubyspec/core/bignum/shared/divide.rb
@@ -0,0 +1,27 @@
+describe :bignum_divide, shared: true do
+ before :each do
+ @bignum = bignum_value(88)
+ end
+
+ it "returns self divided by other" do
+ @bignum.send(@method, 4).should == 2305843009213693974
+
+ @bignum.send(@method, bignum_value(2)).should be_close(1, TOLERANCE)
+
+ (-(10**50)).send(@method, -(10**40 + 1)).should == 9999999999
+ (10**50).send(@method, 10**40 + 1).should == 9999999999
+
+ (-10**50).send(@method, 10**40 + 1).should == -10000000000
+ (10**50).send(@method, -(10**40 + 1)).should == -10000000000
+ end
+
+ it "raises a ZeroDivisionError if other is zero and not a Float" do
+ lambda { @bignum.send(@method, 0) }.should raise_error(ZeroDivisionError)
+ end
+
+ it "raises a TypeError when given a non-Integer" do
+ lambda { @bignum.send(@method, mock('10')) }.should raise_error(TypeError)
+ lambda { @bignum.send(@method, "2") }.should raise_error(TypeError)
+ lambda { @bignum.send(@method, :symbol) }.should raise_error(TypeError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/shared/equal.rb b/spec/rubyspec/core/bignum/shared/equal.rb
new file mode 100644
index 0000000000..ffe4daf4f1
--- /dev/null
+++ b/spec/rubyspec/core/bignum/shared/equal.rb
@@ -0,0 +1,31 @@
+describe :bignum_equal, shared: true do
+ before :each do
+ @bignum = bignum_value
+ end
+
+ it "returns true if self has the same value as the given argument" do
+ @bignum.send(@method, @bignum).should == true
+ @bignum.send(@method, @bignum.to_f).should == true
+
+ @bignum.send(@method, @bignum + 1).should == false
+ (@bignum + 1).send(@method, @bignum).should == false
+
+ @bignum.send(@method, 9).should == false
+ @bignum.send(@method, 9.01).should == false
+
+ @bignum.send(@method, bignum_value(10)).should == false
+ end
+
+ it "calls 'other == self' if the given argument is not an Integer" do
+ obj = mock('not integer')
+ obj.should_receive(:==).and_return(true)
+ @bignum.send(@method, obj).should == true
+ end
+
+ it "returns the result of 'other == self' as a boolean" do
+ obj = mock('not integer')
+ obj.should_receive(:==).exactly(2).times.and_return("woot", nil)
+ @bignum.send(@method, obj).should == true
+ @bignum.send(@method, obj).should == false
+ end
+end
diff --git a/spec/rubyspec/core/bignum/shared/modulo.rb b/spec/rubyspec/core/bignum/shared/modulo.rb
new file mode 100644
index 0000000000..9814e22f3b
--- /dev/null
+++ b/spec/rubyspec/core/bignum/shared/modulo.rb
@@ -0,0 +1,29 @@
+describe :bignum_modulo, shared: true do
+ before :each do
+ @bignum = bignum_value
+ end
+
+ it "returns the modulus obtained from dividing self by the given argument" do
+ @bignum.send(@method, 5).should == 3
+ @bignum.send(@method, -5).should == -2
+ @bignum.send(@method, -100).should == -92
+ @bignum.send(@method, 2.22).should be_close(0.780180180180252, TOLERANCE)
+ @bignum.send(@method, bignum_value(10)).should == 9223372036854775808
+ end
+
+ it "raises a ZeroDivisionError when the given argument is 0" do
+ lambda { @bignum.send(@method, 0) }.should raise_error(ZeroDivisionError)
+ lambda { (-@bignum).send(@method, 0) }.should raise_error(ZeroDivisionError)
+ end
+
+ it "raises a ZeroDivisionError when the given argument is 0 and a Float" do
+ lambda { @bignum.send(@method, 0.0) }.should raise_error(ZeroDivisionError)
+ lambda { -@bignum.send(@method, 0.0) }.should raise_error(ZeroDivisionError)
+ end
+
+ it "raises a TypeError when given a non-Integer" do
+ lambda { @bignum.send(@method, mock('10')) }.should raise_error(TypeError)
+ lambda { @bignum.send(@method, "10") }.should raise_error(TypeError)
+ lambda { @bignum.send(@method, :symbol) }.should raise_error(TypeError)
+ end
+end
diff --git a/spec/rubyspec/core/bignum/size_spec.rb b/spec/rubyspec/core/bignum/size_spec.rb
new file mode 100644
index 0000000000..8629cba972
--- /dev/null
+++ b/spec/rubyspec/core/bignum/size_spec.rb
@@ -0,0 +1,16 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#size" do
+ it "returns the number of bytes required to hold the unsigned bignum data" do
+ # that is, n such that 256 * n <= val.abs < 256 * (n+1)
+ (256**7).size.should == 8
+ (256**8).size.should == 9
+ (256**9).size.should == 10
+ (256**10).size.should == 11
+ (256**10-1).size.should == 10
+ (256**11).size.should == 12
+ (256**12).size.should == 13
+ (256**20-1).size.should == 20
+ (256**40-1).size.should == 40
+ end
+end
diff --git a/spec/rubyspec/core/bignum/to_f_spec.rb b/spec/rubyspec/core/bignum/to_f_spec.rb
new file mode 100644
index 0000000000..8d99045c95
--- /dev/null
+++ b/spec/rubyspec/core/bignum/to_f_spec.rb
@@ -0,0 +1,13 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#to_f" do
+ it "returns self converted to a Float" do
+ bignum_value(0x4000_0aa0_0bb0_0000).to_f.should eql(13_835_069_737_789_292_544.00)
+ bignum_value(0x8000_0000_0000_0ccc).to_f.should eql(18_446_744_073_709_555_712.00)
+ (-bignum_value(99)).to_f.should eql(-9_223_372_036_854_775_808.00)
+ end
+
+ it "converts number close to Float::MAX without exceeding MAX or producing NaN" do
+ (10**308).to_f.should == 10.0 ** 308
+ end
+end
diff --git a/spec/rubyspec/core/bignum/to_s_spec.rb b/spec/rubyspec/core/bignum/to_s_spec.rb
new file mode 100644
index 0000000000..524639adb6
--- /dev/null
+++ b/spec/rubyspec/core/bignum/to_s_spec.rb
@@ -0,0 +1,48 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#to_s when given a base" do
+ it "returns self converted to a String using the given base" do
+ a = 2**64
+ a.to_s(2).should == "10000000000000000000000000000000000000000000000000000000000000000"
+ a.to_s(8).should == "2000000000000000000000"
+ a.to_s(16).should == "10000000000000000"
+ a.to_s(32).should == "g000000000000"
+ end
+
+ it "raises an ArgumentError if the base is less than 2 or higher than 36" do
+ lambda { 123.to_s(-1) }.should raise_error(ArgumentError)
+ lambda { 123.to_s(0) }.should raise_error(ArgumentError)
+ lambda { 123.to_s(1) }.should raise_error(ArgumentError)
+ lambda { 123.to_s(37) }.should raise_error(ArgumentError)
+ end
+end
+
+describe "Bignum#to_s when given no base" do
+ it "returns self converted to a String using base 10" do
+ bignum_value(9).to_s.should == "9223372036854775817"
+ bignum_value.to_s.should == "9223372036854775808"
+ (-bignum_value(675)).to_s.should == "-9223372036854776483"
+ end
+end
+
+with_feature :encoding do
+ describe "Bignum#to_s" do
+ before :each do
+ @internal = Encoding.default_internal
+ end
+
+ after :each do
+ Encoding.default_internal = @internal
+ end
+
+ it "returns a String in US-ASCII encoding when Encoding.default_internal is nil" do
+ Encoding.default_internal = nil
+ bignum_value.to_s.encoding.should equal(Encoding::US_ASCII)
+ end
+
+ it "returns a String in US-ASCII encoding when Encoding.default_internal is not nil" do
+ Encoding.default_internal = Encoding::IBM437
+ bignum_value.to_s.encoding.should equal(Encoding::US_ASCII)
+ end
+ end
+end
diff --git a/spec/rubyspec/core/bignum/uminus_spec.rb b/spec/rubyspec/core/bignum/uminus_spec.rb
new file mode 100644
index 0000000000..7ec432ac71
--- /dev/null
+++ b/spec/rubyspec/core/bignum/uminus_spec.rb
@@ -0,0 +1,11 @@
+require File.expand_path('../../../spec_helper', __FILE__)
+
+describe "Bignum#-@" do
+ it "returns self as a negative value" do
+ bignum_value.send(:-@).should == -9223372036854775808
+ (-bignum_value).send(:-@).should == 9223372036854775808
+
+ bignum_value(921).send(:-@).should == -9223372036854776729
+ (-bignum_value(921).send(:-@)).should == 9223372036854776729
+ end
+end