mirror of
				https://github.com/ruby/ruby.git
				synced 2022-11-09 12:17:21 -05:00 
			
		
		
		
	Merge branch '5172_bigdecimal_gc_issue' into trunk
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@32996 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This commit is contained in:
		
							parent
							
								
									b30d203fed
								
							
						
					
					
						commit
						4e8d6c105c
					
				
					 4 changed files with 91 additions and 7 deletions
				
			
		
							
								
								
									
										18
									
								
								ChangeLog
									
										
									
									
									
								
							
							
						
						
									
										18
									
								
								ChangeLog
									
										
									
									
									
								
							| 
						 | 
				
			
			@ -1,3 +1,21 @@
 | 
			
		|||
Wed Aug 17 15:27:00 2011  Kenta Murata  <mrkn@mrkn.jp>
 | 
			
		||||
 | 
			
		||||
	* ext/bigdecimal/bigdecimal.c (cannot_be_coerced_into_BigDecimal):
 | 
			
		||||
	  add a new function for raising error when an object cannot coerce
 | 
			
		||||
	  into BigDecimal.  [Bug #5172]
 | 
			
		||||
 | 
			
		||||
	* ext/bigdecimal/bigdecimal.c (BigDecimalValueWithPrec): use
 | 
			
		||||
	  cannot_be_coerced_into_BigDecimal function.
 | 
			
		||||
 | 
			
		||||
	* ext/bigdecimal/bigdecimal.c (BigMath_s_exp): ditto.
 | 
			
		||||
 | 
			
		||||
	* ext/bigdecimal/bigdecimal.c (BigMath_s_log): ditto.
 | 
			
		||||
 | 
			
		||||
	* test/bigdecimal/test_bigdecimal.rb: test for the avobe changes.
 | 
			
		||||
 | 
			
		||||
	* test/bigdecimal/testbase.rb (under_gc_stress): add a new utility
 | 
			
		||||
	  method to run tests under the condition of GC.stress = true.
 | 
			
		||||
 | 
			
		||||
Wed Aug 17 10:16:00 2011  Kenta Murata  <mrkn@mrkn.jp>
 | 
			
		||||
 | 
			
		||||
	* rational.c (nurat_coerce): Rational#coerce should converts itself
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -174,6 +174,25 @@ ToValue(Real *p)
 | 
			
		|||
    return p->obj;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
NORETURN(static void cannot_be_coerced_into_BigDecimal(VALUE, VALUE));
 | 
			
		||||
 | 
			
		||||
static void
 | 
			
		||||
cannot_be_coerced_into_BigDecimal(VALUE exc_class, VALUE v)
 | 
			
		||||
{
 | 
			
		||||
    VALUE str;
 | 
			
		||||
 | 
			
		||||
    if (rb_special_const_p(v)) {
 | 
			
		||||
	str = rb_str_cat2(rb_str_dup(rb_inspect(v)),
 | 
			
		||||
			  " can't be coerced into BigDecimal");
 | 
			
		||||
    }
 | 
			
		||||
    else {
 | 
			
		||||
	str = rb_str_cat2(rb_str_dup(rb_class_name(rb_obj_class(v))),
 | 
			
		||||
			  " can't be coerced into BigDecimal");
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    rb_exc_raise(rb_exc_new3(exc_class, str));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static VALUE BigDecimal_div2(int, VALUE*, VALUE);
 | 
			
		||||
 | 
			
		||||
static Real*
 | 
			
		||||
| 
						 | 
				
			
			@ -240,8 +259,7 @@ again:
 | 
			
		|||
 | 
			
		||||
SomeOneMayDoIt:
 | 
			
		||||
    if (must) {
 | 
			
		||||
	rb_raise(rb_eTypeError, "%s can't be coerced into BigDecimal",
 | 
			
		||||
		 rb_special_const_p(v) ? RSTRING_PTR(rb_inspect(v)) : rb_obj_classname(v));
 | 
			
		||||
	cannot_be_coerced_into_BigDecimal(rb_eTypeError, v);
 | 
			
		||||
    }
 | 
			
		||||
    return NULL; /* NULL means to coerce */
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -2463,8 +2481,7 @@ BigMath_s_exp(VALUE klass, VALUE x, VALUE vprec)
 | 
			
		|||
	return ToValue(vy);
 | 
			
		||||
    }
 | 
			
		||||
    else if (vx == NULL) {
 | 
			
		||||
	rb_raise(rb_eArgError, "%s can't be coerced into BigDecimal",
 | 
			
		||||
		 rb_special_const_p(x) ? RSTRING_PTR(rb_inspect(x)) : rb_obj_classname(x));
 | 
			
		||||
	cannot_be_coerced_into_BigDecimal(rb_eArgError, x);
 | 
			
		||||
    }
 | 
			
		||||
    RB_GC_GUARD(vx->obj);
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -2619,8 +2636,7 @@ get_vp_value:
 | 
			
		|||
		 "Zero or negative argument for log");
 | 
			
		||||
    }
 | 
			
		||||
    else if (vx == NULL) {
 | 
			
		||||
	rb_raise(rb_eArgError, "%s can't be coerced into BigDecimal",
 | 
			
		||||
		 rb_special_const_p(x) ? RSTRING_PTR(rb_inspect(x)) : rb_obj_classname(x));
 | 
			
		||||
	cannot_be_coerced_into_BigDecimal(rb_eArgError, x);
 | 
			
		||||
    }
 | 
			
		||||
    x = ToValue(vx);
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1086,7 +1086,7 @@ class TestBigDecimal < Test::Unit::TestCase
 | 
			
		|||
    assert_equal(BigDecimal::SIGN_NEGATIVE_ZERO, BigDecimal.new("-1E-1" + "0" * 10000).sign)
 | 
			
		||||
  end
 | 
			
		||||
 | 
			
		||||
  def test_gc
 | 
			
		||||
  def test_split_under_gc_stress
 | 
			
		||||
    bug3258 = '[ruby-dev:41213]'
 | 
			
		||||
    stress, GC.stress = GC.stress, true
 | 
			
		||||
    10.upto(20) do |i|
 | 
			
		||||
| 
						 | 
				
			
			@ -1097,6 +1097,21 @@ class TestBigDecimal < Test::Unit::TestCase
 | 
			
		|||
    GC.stress = stress
 | 
			
		||||
  end
 | 
			
		||||
 | 
			
		||||
  def test_coerce_under_gc_stress
 | 
			
		||||
    expect = ":too_long_to_embed_as_string can't be coerced into BigDecimal"
 | 
			
		||||
    under_gc_stress do
 | 
			
		||||
      b = BigDecimal.new("1")
 | 
			
		||||
      10.times do
 | 
			
		||||
        begin
 | 
			
		||||
          b.coerce(:too_long_to_embed_as_string)
 | 
			
		||||
        rescue => e
 | 
			
		||||
          assert_instance_of TypeError, e
 | 
			
		||||
          assert_equal expect, e.message
 | 
			
		||||
        end
 | 
			
		||||
      end
 | 
			
		||||
    end
 | 
			
		||||
  end
 | 
			
		||||
 | 
			
		||||
  def test_INFINITY
 | 
			
		||||
    assert(BigDecimal::INFINITY.infinite?, "BigDecimal::INFINITY is not a infinity")
 | 
			
		||||
  end
 | 
			
		||||
| 
						 | 
				
			
			@ -1157,6 +1172,20 @@ class TestBigDecimal < Test::Unit::TestCase
 | 
			
		|||
    assert_in_epsilon(Math.exp(-40), BigMath.exp(BigDecimal("-40"), n))
 | 
			
		||||
  end
 | 
			
		||||
 | 
			
		||||
  def test_BigMath_exp_under_gc_stress
 | 
			
		||||
    expect = ":too_long_to_embed_as_string can't be coerced into BigDecimal"
 | 
			
		||||
    under_gc_stress do
 | 
			
		||||
      10.times do
 | 
			
		||||
        begin
 | 
			
		||||
          BigMath.exp(:too_long_to_embed_as_string, 6)
 | 
			
		||||
        rescue => e
 | 
			
		||||
          assert_instance_of ArgumentError, e
 | 
			
		||||
          assert_equal expect, e.message
 | 
			
		||||
        end
 | 
			
		||||
      end
 | 
			
		||||
    end
 | 
			
		||||
  end
 | 
			
		||||
 | 
			
		||||
  def test_BigMath_log_with_nil
 | 
			
		||||
    assert_raise(ArgumentError) do
 | 
			
		||||
      BigMath.log(nil, 20)
 | 
			
		||||
| 
						 | 
				
			
			@ -1241,4 +1270,18 @@ class TestBigDecimal < Test::Unit::TestCase
 | 
			
		|||
    assert_in_delta(Math.log(1e-42), BigMath.log(1e-42, 20))
 | 
			
		||||
    assert_in_delta(Math.log(1e-42), BigMath.log(BigDecimal("1e-42"), 20))
 | 
			
		||||
  end
 | 
			
		||||
 | 
			
		||||
  def test_BigMath_log_under_gc_stress
 | 
			
		||||
    expect = ":too_long_to_embed_as_string can't be coerced into BigDecimal"
 | 
			
		||||
    under_gc_stress do
 | 
			
		||||
      10.times do
 | 
			
		||||
        begin
 | 
			
		||||
          BigMath.log(:too_long_to_embed_as_string, 6)
 | 
			
		||||
        rescue => e
 | 
			
		||||
          assert_instance_of ArgumentError, e
 | 
			
		||||
          assert_equal expect, e.message
 | 
			
		||||
        end
 | 
			
		||||
      end
 | 
			
		||||
    end
 | 
			
		||||
  end
 | 
			
		||||
end
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -17,4 +17,11 @@ module TestBigDecimalBase
 | 
			
		|||
      BigDecimal.mode(mode, !(@mode & mode).zero?)
 | 
			
		||||
    end
 | 
			
		||||
  end
 | 
			
		||||
 | 
			
		||||
  def under_gc_stress
 | 
			
		||||
    stress, GC.stress = GC.stress, true
 | 
			
		||||
    yield
 | 
			
		||||
  ensure
 | 
			
		||||
    GC.stress = stress
 | 
			
		||||
  end
 | 
			
		||||
end
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue