[GHC] #8695: Arithmetic overflow from (minBound :: Int) `quot` (-1)
GHC
ghc-devs at haskell.org
Tue Jan 28 23:14:18 UTC 2014
#8695: Arithmetic overflow from (minBound :: Int) `quot` (-1)
------------------------------------------------+--------------------------
Reporter: rleslie | Owner:
Type: bug | Status: patch
Priority: normal | Milestone: 7.8.1
Component: libraries/haskell2010 | Version: 7.6.3
Resolution: | Keywords:
Operating System: Unknown/Multiple | Architecture:
Type of failure: Incorrect result at runtime | Unknown/Multiple
Test Case: | Difficulty:
Blocking: | Unknown
| Blocked By:
| Related Tickets: #1042
------------------------------------------------+--------------------------
Comment (by ekmett):
rwbarton: I fully expected to get dinged on the fact that Int can't be a
proper domain. I should have included the caveat that it is 'insofar as it
can be'.
That said, when a function can be continuously extended sensibly in only
one way, I tend to favor extending it.
Re: `div (toInteger a) (-1) == toInteger c`, here `(-1)` is a even unit of
`Z mod 2^n`, but we can't even multiply it by all of the ring and pass
that law.
The only way to pass your condition without partiality would be to use 1s
complement to fix the asymmetry between positive and negative values, but
it of course comes with all sorts of other problems and is a complete non-
starter.
That said, the operation can pass a slightly different condition, which is
that the answers match mod 2^n.
In other words
{{{
c = div a b = fromInteger (div (toInteger a) (toInteger b))
}}}
{{{
>>> fromInteger $ toInteger (minBound :: Int) `div` (-1) :: Int
-9223372036854775808
>>> fromInteger $ toInteger (minBound :: Int) `quot` (-1) :: Int
-9223372036854775808
}}}
This extension to `div` and `quot` complies with doing this operation in
the larger `Integer` domain and coming back down into the restricted
range, just like `(*)`, `(-)`, `(+)`, etc. do. Those operations also don't
comply with your desired law.
carter: There are multiple packages that provide overflow protection. e.g.
http://hackage.haskell.org/package/safeint
That said, `Int` explicitly does not.
2s complement introduces particularly hairy corner cases around
`minBound`. `-minBound = minBound`, `abs minBound < (0 :: Int)` etc. and
it is that same counter-intuitive corner case arising here.
--
Ticket URL: <http://ghc.haskell.org/trac/ghc/ticket/8695#comment:22>
GHC <http://www.haskell.org/ghc/>
The Glasgow Haskell Compiler
More information about the ghc-tickets
mailing list