@@ -8,7 +8,7 @@
9------------------------------------------------------------------------------
9------------------------------------------------------------------------------
11−{-# LANGUAGE DeriveDataTypeable, DeriveFunctor #-}
11+{-# LANGUAGE DeriveDataTypeable, DeriveFunctor, CPP #-}
13module Database.PostgreSQL.Simple.Time.Implementation where
13module Database.PostgreSQL.Simple.Time.Implementation where
@@ -29,6 +29,26 @@ import Data.Monoid(Monoid(..))
29import Data.Fixed (Pico)
29import Data.Fixed (Pico)
30import Unsafe.Coerce
30import Unsafe.Coerce
32+#if !MIN_VERSION_base(4,7,0)
33+-- A kludge to work around the fact that Data.Fixed isn't very fast and
34+-- previously didn't give me access to the MkFixed constructor.
36+mkPico :: Integer -> Pico
39+fromPico :: Pico -> Integer
40+fromPico = unsafeCoerce
42+import Data.Fixed(Fixed(MkFixed))
44+mkPico :: Integer -> Pico
47+fromPico :: Pico -> Integer
48+fromPico (MkFixed x) = x
32data Unbounded a
52data Unbounded a
33 = NegInfinity
53 = NegInfinity
34 | Finite !a
54 | Finite !a
@@ -124,9 +144,8 @@ getTimeOfDay = do
124 decimal secs = do
144 decimal secs = do
125 _ <- A.satisfy (\c -> c == '.' || c == ',')
145 _ <- A.satisfy (\c -> c == '.' || c == ',')
126 digits <- B.take 12 <$> A.takeWhile1 A.isDigit
146 digits <- B.take 12 <$> A.takeWhile1 A.isDigit
127− -- A kludge to work around the fact that Data.Fixed isn't very fast and
147+
128− -- doesn't give me access to the MkFixed constructor.
129− return $! unsafeCoerce (toNum_ secs digits * 10^(12 - B.length digits))
148+ return $! mkPico (toNum_ secs digits * 10^(12 - B.length digits))
131getLocalTime :: A.Parser LocalTime
150getLocalTime :: A.Parser LocalTime
132getLocalTime = LocalTime <$> getDay <*> (todSeparator *> getTimeOfDay)
151getLocalTime = LocalTime <$> getDay <*> (todSeparator *> getTimeOfDay)
@@ -274,9 +293,9 @@ nominalDiffTimeToBuilder xyz
274 | yz < 500000 = sign <> integerDec x
293 | yz < 500000 = sign <> integerDec x
275 | otherwise = sign <> integerDec x <> char8 '.' <> showD6 y
294 | otherwise = sign <> integerDec x <> char8 '.' <> showD6 y
277− -- A kludge to work around the fact that Data.Fixed isn't very fast and
278− -- doesn't give me access to the MkFixed constructor.
279 sign = if xyz >= 0 then mempty else char8 '-'
296 sign = if xyz >= 0 then mempty else char8 '-'
297+ -- A kludge to work around the fact that Data.Fixed isn't very fast and
298+ -- NominalDiffTime doesn't give the MkNominalDiffTime constructor.
280 (x,yz) = ((unsafeCoerce (abs xyz) :: Integer) + 500000) `quotRem` 1000000000000
299 (x,yz) = ((unsafeCoerce (abs xyz) :: Integer) + 500000) `quotRem` 1000000000000
281 (fromIntegral -> y, _z) = yz `quotRem` 1000000
300 (fromIntegral -> y, _z) = yz `quotRem` 1000000
@@ -286,9 +305,7 @@ showSeconds xyz
286 | z == 0 = pad2 x <> char8 '.' <> showD6 y
305 | z == 0 = pad2 x <> char8 '.' <> showD6 y
287 | otherwise = pad2 x <> char8 '.' <> pad6 y <> showD6 z
306 | otherwise = pad2 x <> char8 '.' <> pad6 y <> showD6 z
289− -- A kludge to work around the fact that Data.Fixed isn't very fast and
290− -- doesn't give me access to the MkFixed constructor.
291− (x_,yz) = (unsafeCoerce xyz :: Integer) `quotRem` 1000000000000
308+ (x_,yz) = fromPico xyz `quotRem` 1000000000000
292 x = fromIntegral x_ :: Int
309 x = fromIntegral x_ :: Int
293 (fromIntegral -> y, fromIntegral -> z) = yz `quotRem` 1000000
310 (fromIntegral -> y, fromIntegral -> z) = yz `quotRem` 1000000