Skip to content
This repository has been archived by the owner on Sep 20, 2023. It is now read-only.

timeConvert does not always work on 32-bit GHC #21

Closed
trofi opened this issue Aug 31, 2015 · 3 comments
Closed

timeConvert does not always work on 32-bit GHC #21

trofi opened this issue Aug 31, 2015 · 3 comments

Comments

@trofi
Copy link

trofi commented Aug 31, 2015

One of the fallouts of vincenthz/hs-asn1#12 is the following:

Running the following

Prelude> import Data.Hourglass
Prelude Data.Hourglass> timeConvert (timeConvert (Date {dateYear = 2046, dateMonth = May, dateDay = 1}) :: Elapsed) :: Date

x86_64-linux-ghc-7.10.2 yields:

Date {dateYear = 2046, dateMonth = May, dateDay = 1}

i686-linux-ghc-7.10.2 yields:

Date {dateYear = 1910, dateMonth = March, dateDay = 25}
@trofi
Copy link
Author

trofi commented Aug 31, 2015

Int64 -> Int32 truncation happens in Data/Hourglass/Internal/Unix.hs
in function rawGmTime where time_t overflows 32 bits and silent truncation happens.

I've slightly changed it to make an error clearer:

rawGmTime :: Elapsed -> CTm
rawGmTime (Elapsed (Seconds s)) = unsafePerformIO callTime
  where callTime =
            alloca $ \ctmPtr -> do
            alloca $ \ctimePtr -> do
                poke ctimePtr ctime
                r <- c_gmtime_r ctimePtr ctmPtr
                if r == nullPtr
                    then error "gmTime failed"
                    else peek ctmPtr
        ctime | fromIntegral (maxBound :: CLong) < s = error $ "CLong overflow in rawGmTime: " ++ show (maxBound :: CLong, s)
              | otherwise                            = fromIntegral s

Results to:

*** Exception: CLong overflow in rawGmTime: (2147483647,2408745600)

trofi added a commit to gentoo-haskell/gentoo-haskell that referenced this issue Aug 31, 2015
On 32-bit systems Hourglass silently breaks dates
out of range '1970 +- 68' years due to use of
'time_t' and 'gmtime_r' from installed libc.

Workaround test failures by not testing times out of this range.

Github-bug: vincenthz/hs-hourglass#21
Github-bug: vincenthz/hs-asn1#12

Package-Manager: portage-2.2.20
mgorny pushed a commit to gentoo/gentoo that referenced this issue Aug 31, 2015
On 32-bit systems Hourglass silently breaks dates
out of range '1970 +- 68' years due to use of
'time_t' and 'gmtime_r' from installed libc.

Workaround test failures by not testing times out of this range.

Github-bug: vincenthz/hs-hourglass#21
Github-bug: vincenthz/hs-asn1#12

Package-Manager: portage-2.2.20
@vincenthz
Copy link
Owner

sadly, I'm not sure that is worth fixing; specially by raising a dynamic error. also technically this hasn't nothing to do with a CLong. CLong could be 32 bits, when CTime is 64 bits

@vincenthz
Copy link
Owner

Closing, because I don't think there's any more efforts to put in this.
This is just an linux ABI problem (and other unixes that use 32 bits ctime), stop using the i386 ABI, and instead move to linux x32 ABI (32 bits with 64 bit ctime) or x86-64, or any other ABI that has 64 bits ctime.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants