* bignum.c (bigdivrem): restart calculation when bigdivrem1 was

interrupted by signal. Otherwise, ruby script may see a garbage
  value.

git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@37850 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This commit is contained in:
kosaki 2012-11-26 07:00:04 +00:00
parent 6f3ad9bd3d
commit cb0a4c0f62
2 changed files with 19 additions and 2 deletions

View File

@ -1,3 +1,9 @@
Mon Nov 26 15:50:29 2012 KOSAKI Motohiro <kosaki.motohiro@gmail.com>
* bignum.c (bigdivrem): restart calculation when bigdivrem1 was
interrupted by signal. Otherwise, ruby script may see a garbage
value.
Mon Nov 26 15:33:02 2012 KOSAKI Motohiro <kosaki.motohiro@gmail.com>
* bignum.c (big_div_struct): added volatile to 'stop' member.

View File

@ -2713,16 +2713,22 @@ rb_big_stop(void *ptr)
}
static VALUE
bigdivrem(VALUE x, VALUE y, volatile VALUE *divp, volatile VALUE *modp)
bigdivrem(VALUE x, VALUE y_, volatile VALUE *divp, volatile VALUE *modp)
{
VALUE y;
struct big_div_struct bds;
long nx = RBIGNUM_LEN(x), ny = RBIGNUM_LEN(y);
long nx, ny;
long i, j;
VALUE z, yy, zz;
BDIGIT *xds, *yds, *zds, *tds;
BDIGIT_DBL t2;
BDIGIT dd, q;
retry:
y = y_;
nx = RBIGNUM_LEN(x);
ny = RBIGNUM_LEN(y);
if (BIGZEROP(y)) rb_num_zerodiv();
xds = BDIGITS(x);
yds = BDIGITS(y);
@ -2795,6 +2801,11 @@ bigdivrem(VALUE x, VALUE y, volatile VALUE *divp, volatile VALUE *modp)
bds.stop = Qfalse;
if (nx > 10000 || ny > 10000) {
rb_thread_call_without_gvl(bigdivrem1, &bds, rb_big_stop, &bds);
if (bds.stop == Qtrue) {
/* execute trap handler, but exception was not raised. */
goto retry;
}
}
else {
bigdivrem1(&bds);