ruby-core@ruby-lang.org archive (unofficial mirror)
 help / color / mirror / Atom feed
From: merch-redmine@jeremyevans.net
To: ruby-core@ruby-lang.org
Subject: [ruby-core:94370] [Ruby master Bug#8542] BigMath::exp modifies its first argument
Date: Thu, 15 Aug 2019 19:22:02 +0000 (UTC)	[thread overview]
Message-ID: <redmine.journal-80784.20190815192202.59d73549332675cf@ruby-lang.org> (raw)
In-Reply-To: redmine.issue-8542.20130619082730@ruby-lang.org

Issue #8542 has been updated by jeremyevans0 (Jeremy Evans).


As bigdecimal upstream is in a separate repository, I submitted a pull request for this: https://github.com/ruby/bigdecimal/pull/150.

----------------------------------------
Bug #8542: BigMath::exp modifies its first argument
https://bugs.ruby-lang.org/issues/8542#change-80784

* Author: GSnyder (Garth Snyder)
* Status: Assigned
* Priority: Normal
* Assignee: mrkn (Kenta Murata)
* Target version: 
* ruby -v: ruby 2.0.0p195 (2013-05-14 revision 40734) [i386-solaris2.11]
* Backport: 2.6: REQUIRED
----------------------------------------
=begin
I noticed this when creating the patch at https://github.com/ruby/ruby/pull/332. I believe it affects everything from ruby 1.8 up.

BigMath::exp is implemented for negative numbers according to the identity E ** -x == 1 / (E ** x). At bigdecimal.c:2742 (in GitHub commit 258acf3, in the implementation of BigMath_s_exp), the code flips the sign on the input argument for negative numbers. Later, it returns the reciprocal of the result.

Problem: When the first argument is a BigDecimal (or, presumably, Bignum), the original argument is modified, so its sign bit remains flipped. Hence:

 $ irb
 2.0.0-p195 :001 > require 'bigdecimal/math'
 => true 
 2.0.0-p195 :002 > x = BigDecimal(-1)
 => #<BigDecimal:827d960,'-0.1E1',9(36)> 
 2.0.0-p195 :003 > BigMath.exp(x, 20)
 => #<BigDecimal:822dca8,'0.3678794411 714423216E0',27(54)> 
 2.0.0-p195 :004 > x
 => #<BigDecimal:827d960,'0.1E1',9(36)> 


Here, x is modified when used as an argument to BigMath.exp AND the answer is wrong. I have already submitted the patch mentioned above for the latter problem, but I'm not sure what the appropriate fix would be for the sign modification. Just resetting the sign bit on exit would be easy but not thread safe; BigMath.exp really shouldn't be modifying the argument at all. But copying the whole argument is potentially wasteful if the precision is high.

I suspect that the special calculation track for negative values is actually not needed at all. Without the patch I just submitted, BigMath.exp is reliably returning the reciprocal of the correct answer, which means that it's properly calculating the correct answer by using the (negative) VALUE x passed in as the original argument -- at least for immediate values. So perhaps the basic iteration loop is just as valid for negative exponents as it is already implemented.
=end

---Files--------------------------------
bigdecimal-exp-no-mutate-8542.patch (1.63 KB)


-- 
https://bugs.ruby-lang.org/

  parent reply	other threads:[~2019-08-15 19:22 UTC|newest]

Thread overview: 8+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2013-06-18 23:27 [ruby-core:55550] [ruby-trunk - Bug #8542][Open] BigMath::exp modifies its first argument GSnyder (Garth Snyder)
2013-06-18 23:55 ` [ruby-core:55551] [ruby-trunk - Bug #8542] " GSnyder (Garth Snyder)
2013-06-19 10:42 ` [ruby-core:55555] [ruby-trunk - Bug #8542][Assigned] " naruse (Yui NARUSE)
2013-06-20  7:34 ` [ruby-core:55567] [ruby-trunk - Bug #8542] " GSnyder (Garth Snyder)
2014-01-30  6:17 ` [ruby-core:60298] " shibata.hiroshi
2019-08-10  5:31 ` [ruby-core:94245] [Ruby master Bug#8542] " merch-redmine
2019-08-15 19:22 ` merch-redmine [this message]
2019-10-07 21:25 ` [ruby-core:95265] " merch-redmine

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-list from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

  List information: https://www.ruby-lang.org/en/community/mailing-lists/

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=redmine.journal-80784.20190815192202.59d73549332675cf@ruby-lang.org \
    --to=ruby-core@ruby-lang.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).