base-compat-0.9.3/0000755000000000000000000000000013072705326012111 5ustar0000000000000000base-compat-0.9.3/base-compat.cabal0000644000000000000000000001063413072705326015274 0ustar0000000000000000name: base-compat version: 0.9.3 license: MIT license-file: LICENSE copyright: (c) 2012-2017 Simon Hengel, (c) 2014-2017 João Cristóvão, (c) 2015-2017 Ryan Scott author: Simon Hengel , João Cristóvão , Ryan Scott maintainer: Simon Hengel , João Cristóvão , Ryan Scott build-type: Simple cabal-version: >= 1.8 category: Compatibility synopsis: A compatibility layer for base description: Provides functions available in later versions of @base@ to a wider range of compilers, without requiring you to use CPP pragmas in your code. See the for what is covered. Also see the for recent changes. . Note that @base-compat@ does not add any orphan instances. There is a separate package, @@, for that. . In addition, `base-compat` does not backport any data types or type classes. See @@ for more info. tested-with: GHC == 7.0.1, GHC == 7.0.2, GHC == 7.0.3, GHC == 7.0.4 , GHC == 7.2.1, GHC == 7.2.2 , GHC == 7.4.1, GHC == 7.4.2 , GHC == 7.6.1, GHC == 7.6.2, GHC == 7.6.3 , GHC == 7.8.1, GHC == 7.8.2, GHC == 7.8.3, GHC == 7.8.4 , GHC == 7.10.1, GHC == 7.10.2, GHC == 7.10.3 , GHC == 8.0.1, GHC == 8.0.2 , GHC == 8.2.1 extra-source-files: CHANGES.markdown, README.markdown source-repository head type: git location: https://github.com/haskell-compat/base-compat library ghc-options: -Wall build-depends: base >= 4.3 && < 5 if !os(windows) && !os(halvm) build-depends: unix ghc-options: -fno-warn-duplicate-exports hs-source-dirs: src exposed-modules: Control.Concurrent.Compat Control.Concurrent.MVar.Compat Control.Monad.Compat Control.Monad.ST.Lazy.Unsafe.Compat Control.Monad.ST.Unsafe.Compat Data.Bits.Compat Data.Bool.Compat Data.Complex.Compat Data.Either.Compat Data.Foldable.Compat Data.Function.Compat Data.Functor.Compat Data.Functor.Const.Compat Data.IORef.Compat Data.List.Compat Data.Monoid.Compat Data.Proxy.Compat Data.Ratio.Compat Data.STRef.Compat Data.String.Compat Data.Type.Coercion.Compat Data.Version.Compat Data.Word.Compat Debug.Trace.Compat Foreign.Compat Foreign.ForeignPtr.Compat Foreign.ForeignPtr.Safe.Compat Foreign.ForeignPtr.Unsafe.Compat Foreign.Marshal.Alloc.Compat Foreign.Marshal.Array.Compat Foreign.Marshal.Compat Foreign.Marshal.Safe.Compat Foreign.Marshal.Unsafe.Compat Foreign.Marshal.Utils.Compat Numeric.Compat Prelude.Compat System.Environment.Compat System.Exit.Compat System.IO.Unsafe.Compat Text.Read.Compat test-suite spec type: exitcode-stdio-1.0 ghc-options: -Wall hs-source-dirs: test main-is: Spec.hs other-modules: Control.Monad.CompatSpec Data.Bits.CompatSpec Data.Bool.CompatSpec Data.Either.CompatSpec Data.Foldable.CompatSpec Data.Function.CompatSpec Data.Functor.CompatSpec Data.IORef.CompatSpec Data.List.CompatSpec Data.Monoid.CompatSpec Data.STRef.CompatSpec Data.Version.CompatSpec Data.Word.CompatSpec Foreign.Marshal.Alloc.CompatSpec Foreign.Marshal.Utils.CompatSpec Numeric.CompatSpec System.Environment.CompatSpec Text.Read.CompatSpec build-depends: base >= 4.3 && < 5 , base-compat , hspec >= 1.8 , QuickCheck base-compat-0.9.3/README.markdown0000644000000000000000000003067513072705326014625 0ustar0000000000000000# A compatibility layer for `base` [![Hackage](https://img.shields.io/hackage/v/base-compat.svg)][Hackage: base-compat] [![Hackage Dependencies](https://img.shields.io/hackage-deps/v/base-compat.svg)](http://packdeps.haskellers.com/reverse/base-compat) [![Haskell Programming Language](https://img.shields.io/badge/language-Haskell-blue.svg)][Haskell.org] [![BSD3 License](http://img.shields.io/badge/license-MIT-brightgreen.svg)][tl;dr Legal: MIT] [![Build](https://img.shields.io/travis/haskell-compat/base-compat.svg)](https://travis-ci.org/haskell-compat/base-compat) [Hackage: base-compat]: http://hackage.haskell.org/package/base-compat "base-compat package on Hackage" [Haskell.org]: http://www.haskell.org "The Haskell Programming Language" [tl;dr Legal: MIT]: https://tldrlegal.com/license/mit-license "MIT License" ## Scope The scope of `base-compat` is to provide functions available in later versions of base to a wider (older) range of compilers. In addition, successful library proposals that have been accepted to be part of upcoming versions of `base` are also included. This package is not intended to replace `base`, but to complement it. Note that `base-compat` does not add any orphan instances. There is a separate package [`base-orphans`](https://github.com/haskell-compat/base-orphans) for that. In addition, `base-compat` only backports functions. In particular, we purposefully do not backport data types or type classes introduced in newer versions of `base`. For more info, see the [Data types and type classes](#data-types-and-type-classes) section. ## Basic usage In your cabal file, you should have something like this: ``` build-depends: base >= 4.3 , base-compat >= 0.9.0 ``` Then, lets say you want to use the `isRight` function introduced with `base-4.7.0.0`. Replace: ``` import Data.Either ``` with ``` import Data.Either.Compat ``` _Note (1)_: There is no need to import both unqualified. The `.Compat` modules re-exports the original module. _Note (2)_: If a given module `.Compat` version is not defined, that either means that: * The module has not changed in recent base versions, thus no `.Compat` is needed. * The module has changed, but the changes depend on newer versions of GHC, and thus are not portable. * The module has changed, but those changes have not yet been merged in `base-compat`: patches are welcomed! ## Using `Prelude.Compat` If you want to use `Prelude.Compat` (which provides all the AMP/Traversable/Foldable changes from `base-4.8.0.0`), it's best to hide `Prelude`, e.g.: import Prelude () import Prelude.Compat main :: IO () main = mapM_ print (Just 23) Alternatively, you can use the `NoImplicitPrelude` language extension: {-# LANGUAGE NoImplicitPrelude #-} import Prelude.Compat main :: IO () main = mapM_ print (Just 23) Note that we use mapM_ :: (Foldable t, Monad m) => (a -> m b) -> t a -> m () from `Data.Foldable` here, which is only exposed from `Prelude` since `base-4.8.0.0`. Using this approach allows you to write code that works seamlessly with all versions of GHC that are supported by `base-compat`. ## What is covered So far the following is covered. ### For compatibility with the latest released version of `base` * `Prelude.Compat` incorporates the AMP/Foldable/Traversable changes and exposes the same interface as `Prelude` from `base-4.9.0.0` * `System.IO.Error.catch` is not re-exported from `Prelude.Compat` for older versions of `base` * `Text.Read.Compat.readMaybe` * `Text.Read.Compat.readEither` * `Data.Monoid.Compat.<>` * Added `bitDefault`, `testBitDefault`, and `popCountDefault` to `Data.Bits.Compat` * Added `toIntegralSized` to `Data.Bits.Compat` (if using `base-4.7`) * Added `bool` function to `Data.Bool.Compat` * Added `isLeft`, `isRight`, `fromLeft`, and `fromRight` to `Data.Either.Compat` * Added `forkFinally` to `Control.Concurrent.Compat` * Added `withMVarMasked` function to `Control.Concurrent.MVar.Compat` * Added `(<$!>)` function to `Control.Monad.Compat` * Weakened `RealFloat` constraints on `realPart`, `imagPart`, `conjugate`, `mkPolar`, and `cis` in `Data.Complex.Compat` * Added more efficient `maximumBy`/`minimumBy` to `Data.Foldable.Compat` * Added `($>)` and `void` functions to `Data.Functor.Compat` * `(&)` function to `Data.Function.Compat` * `($>)` and `void` functions to `Data.Functor.Compat` * `modifyIORef'`, `atomicModifyIORef'` and `atomicWriteIORef` to `Data.IORef.Compat` * `dropWhileEnd`, `isSubsequenceOf`, `sortOn`, and `uncons` functions to `Data.List.Compat` * Correct versions of `nub`, `nubBy`, `union`, and `unionBy` to `Data.List.Compat` * `asProxyTypeOf` with a generalized type signature to `Data.Proxy.Compat` * `modifySTRef'` to `Data.STRef.Compat` * `String`, `lines`, `words`, `unlines`, and `unwords` to `Data.String.Compat` * `gcoerceWith` to `Data.Type.Coercion.Compat` * `makeVersion` function to `Data.Version.Compat` * `traceId`, `traceShowId`, `traceM`, and `traceShowM` functions to `Debug.Trace.Compat` * `byteSwap16`, `byteSwap32`, and `byteSwap64` to `Data.Word.Compat` * `plusForeignPtr` to `Foreign.ForeignPtr.Compat` * `calloc` and `callocBytes` functions to `Foreign.Marshal.Alloc.Compat` * `callocArray` and `callocArray0` functions to `Foreign.Marshal.Array.Compat` * `fillBytes` to `Foreign.Marshal.Utils.Compat` * Added `Data.List.Compat.scanl'` * `showFFloatAlt` and `showGFloatAlt` to `Numeric.Compat` * `lookupEnv`, `setEnv` and `unsetEnv` to `System.Environment.Compat` * `unsafeFixIO` and `unsafeDupablePerformIO` to `System.IO.Unsafe.IO` ## What is not covered ### Data types and type classes `base-compat` purposefully does not export any data types or type classes that were introduced in more recent versions of `base`. The main reasoning for this policy is that it is not some data types and type classes have had their APIs change in different versions of `base`, which makes having a consistent compatibility API for them practically impossible. As an example, consider the `FiniteBits` type class. It was introduced in [`base-4.7.0.0`](http://hackage.haskell.org/package/base-4.7.0.0/docs/Data-Bits.html#t:FiniteBits) with the following API: ```haskell class Bits b => FiniteBits b where finiteBitSize :: b -> Int ``` However, in [`base-4.8.0.0`](http://hackage.haskell.org/package/base-4.8.0.0/docs/Data-Bits.html#t:FiniteBits), `FiniteBits` gained additional functions: ```haskell class Bits b => FiniteBits b where finiteBitSize :: b -> Int countLeadingZeros :: b -> Int countTrailingZeros :: b -> Int ``` This raises the question: how can `FiniteBits` be backported consistently across all versions of `base`? One approach is to backport the API exposed in `base-4.8.0.0` on versions prior to `4.7.0.0`. The problem with this is that `countLeadingZeros` and `countTrailingZeros` are not exposed in `base-4.7.0.0`, so instances of `FiniteBits` would have to be declared like this: ```haskell instance FiniteBits Foo where finiteBitSize = ... #if MIN_VERSION_base(4,8,0) || !(MIN_VERSION_base(4,7,0)) countLeadingZeros = ... countTrailingZeros = ... #endif ``` This is a very unsatisfactory solution, and for this reason, we do not pursue it. For similar reasons, we do not backport data types. ### Other compatibility packages If you _really_ need your favorite data type or type class in `base` to be backported, you might be in luck, since several data types have their own compatibility packages on Hackage. Here is a list of such packages: * [`bifunctors`](http://hackage.haskell.org/package/bifunctors) for: * The [`Bifunctor`](http://hackage.haskell.org/package/base-4.8.0.0/docs/Data-Bifunctor.html#t:Bifunctor) type class, introduced in `base-4.8.0.0` * The [`Bifoldable`](http://hackage.haskell.org/package/base-4.10.0.0/docs/Data-Bifoldable.html#t:Bifoldable) and [`Bitraversable`](http://hackage.haskell.org/package/base-4.10.0.0/docs/Data-Bitraversable.html#t:Bitraversable) type classes, introduced in `base-4.10.0.0` * [`fail`](http://hackage.haskell.org/package/fail) for the [`MonadFail`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Control-Monad-Fail.html#t:MonadFail) type class, introduced in `base-4.9.0.0` * [`generic-deriving`](http://hackage.haskell.org/package/generic-deriving) for everything in the [`GHC.Generics`](http://hackage.haskell.org/package/base-4.8.0.0/docs/GHC-Generics.html) module, introduced to `ghc-prim` in GHC 7.2 (and later moved to `base-4.6.0.0`) * [`nats`](http://hackage.haskell.org/package/nats) for the [`Natural`](http://hackage.haskell.org/package/base-4.8.0.0/docs/Numeric-Natural.html) data type, introduced in `base-4.8.0.0` * [`semigroups`](http://hackage.haskell.org/package/semigroups) for the [`Semigroup`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Semigroup.html#t:Semigroup) typeclass and the [`NonEmpty`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-List-NonEmpty.html#t:NonEmpty), [`Min`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Semigroup.html#t:Min), [`Max`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Semigroup.html#t:Max), [`First`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Semigroup.html#t:First), [`Last`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Semigroup.html#t:Last), [`WrappedMonoid`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Semigroup.html#t:WrappedMonoid), [`Option`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Semigroup.html#t:Option), and [`Arg`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Semigroup.html#t:Arg) data types, introduced in `base-4.9.0.0` * [`tagged`](http://hackage.haskell.org/package/tagged) for the [`Proxy`](http://hackage.haskell.org/package/base-4.7.0.0/docs/Data-Proxy.html#t:Proxy) data type, introduced in `base-4.7.0.0` * [`transformers`](http://hackage.haskell.org/package/transformers) for: * The [`Identity`](http://hackage.haskell.org/package/base-4.8.0.0/docs/Data-Functor-Identity.html#t:Identity) data type, introduced in `base-4.8.0.0` * The [`MonadIO`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Control-Monad-IO-Class.html#t:MonadIO), [`Eq1`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Functor-Classes.html#t:Eq1), [`Eq2`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Functor-Classes.html#t:Eq2), [`Ord1`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Functor-Classes.html#t:Ord1), [`Ord2`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Functor-Classes.html#t:Ord2), [`Read1`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Functor-Classes.html#t:Read1), [`Read2`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Functor-Classes.html#t:Read2), [`Show1`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Functor-Classes.html#t:Show1), and [`Show2`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Functor-Classes.html#t:Show2) typeclasses; and the [`Compose`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Functor-Compose.html#t:Compose), [`Product`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Functor-Product.html#t:Product), and [`Sum`](http://hackage.haskell.org/package/base-4.9.0.0/docs/Data-Functor-Sum.html#t:Sum) data types, introduced in `base-4.9.0.0` * [`void`](http://hackage.haskell.org/package/void) for the [`Void`](http://hackage.haskell.org/package/base-4.8.0.0/docs/Data-Void.html#t:Void) data type, introduced in `base-4.8.0.0` ## Supported versions of GHC/`base` * `ghc-8.2.1` / `base-4.10.0.0` * `ghc-8.0.2` / `base-4.9.1.0` * `ghc-8.0.1` / `base-4.9.0.0` * `ghc-7.10.3` / `base-4.8.2.0` * `ghc-7.10.2` / `base-4.8.1.0` * `ghc-7.10.1` / `base-4.8.0.0` * `ghc-7.8.4` / `base-4.7.0.2` * `ghc-7.8.3` / `base-4.7.0.1` * `ghc-7.8.2` / `base-4.7.0.0` * `ghc-7.8.1` / `base-4.7.0.0` * `ghc-7.6.3` / `base-4.6.0.1` * `ghc-7.6.2` / `base-4.6.0.1` * `ghc-7.6.1` / `base-4.6.0.0` * `ghc-7.4.2` / `base-4.5.1.0` * `ghc-7.4.1` / `base-4.5.0.0` * `ghc-7.2.2` / `base-4.4.1.0` * `ghc-7.2.1` / `base-4.4.0.0` * `ghc-7.0.4` / `base-4.3.1.0` * `ghc-7.0.3` / `base-4.3.1.0` * `ghc-7.0.2` / `base-4.3.1.0` * `ghc-7.0.1` / `base-4.3.0.0` We also make an attempt to keep `base-compat` building with GHC HEAD, but due to its volatility, it may not work at any given point in time. If it doesn't, please report it! Patches are welcome; add tests for new code! base-compat-0.9.3/CHANGES.markdown0000644000000000000000000001117613072705326014733 0ustar0000000000000000## Changes in 0.9.3 [2017.04.10] - Sync with `base-4.10`/GHC 8.2 - Backport `fromLeft`/`fromRight` to `Data.Either.Compat` - Backport implementations of `maximumBy`/`minimumBy` which use constant stack space to `Data.Foldable.Compat` - Backport `asProxyTypeOf` with a generalized type signature to `Data.Proxy.Compat` - Backport `gcoerceWith` to `Data.Type.Coercion.Compat` - Backport `plusForeignPtr` to `Foreign.ForeignPtr.Compat` ## Changes in 0.9.2 - Allow building on the HaLVM ## Changes in 0.9.1 - Use the more efficient version of `replicateM` and `replicateM_` introduced in `base-4.9` ## Changes in 0.9.0 - Sync with `base-4.9`/GHC 8.0 - Weakened `RealFloat` constraints on `realPart`, `imagPart`, `conjugate`, `mkPolar`, and `cis` in `Data.Complex.Compat` - Backport `Foreign.ForeignPtr.Safe` and `Foreign.Marshal.Safe` - Generalize `filterM`, `forever`, `mapAndUnzipM`, `zipWithM`, `zipWithM_`, `replicateM`, and `replicateM_` in `Control.Monad` from `Monad` to `Applicative` - Backport `.Unsafe.Compat` modules (for `Control.Monad.ST`, `Control.Monad.ST.Lazy`, `Foreign.ForeignPtr`, and `Foreign.Marshal`) - Backport `forkFinally` and `forkOSWithUnmask` to `Control.Concurrent.Compat` - Backport `Data.Functor.Const` - Backport `modifyIORef'`, `atomicModifyIORef'` and `atomicWriteIORef` to `Data.IORef.Compat` - `Data.Ratio.{denominator,numerator}` have no `Integral` constraint anymore - Backport `modifySTRef'` to `Data.STRef.Compat` - Export `String`, `lines`, `words`, `unlines`, and `unwords` to `Data.String.Compat` - Generalize `Debug.Trace.{traceM, traceShowM}` from `Monad` to `Applicative` - Backport `errorWithoutStackTrace` to `Prelude.Compat` - Backport `unsafeFixIO` and `unsafeDupablePerformIO` to `System.IO.Unsafe.Compat` ## Changes in 0.8.2 - Backport `bitDefault`, `testBitDefault`, and `popCountDefault` in `Data.Bits.Compat` to all versions of `base` - Backport `toIntegralSized` to `base-4.7` - Backport `nub` and `nubBy` (as well as `union` and `unionBy`, which are implemented in terms of them) to fix logic error in `Data.List.Compat` - Backport `byteSwap16`, `byteSwap32`, and `byteSwap64` to `Data.Word.Compat` - Backport `fillBytes` in `Foreign.Marshal.Utils.Compat` - Backport `showFFloatAlt` and `showGFloatAlt` to `Numeric.Compat` ## Changes in 0.8.1.1 - Fixed Windows build ## Changes in 0.8.1 - Implement `setEnv` and `unsetEnv` in `System.Environment.Compat` (which were ported from the `setenv` package). As a result, `base-compat` now depends on `unix` on POSIX-like operating systems. - Drop GHC 6.12 (and `base-4.2.0.0`) compatibility ## Changes in 0.8.0.1 - Retrospective version bump updating the changelog to reflect the changes made in 0.8.0 ## Changes 0.8.0 - All orphan instances were split off into a separate package, [`base-orphans`](https://github.com/haskell-compat/base-orphans) - `base-compat` no longer redefines the data types `Down` and `Alt`. See [here](https://github.com/haskell-compat/base-compat/issues/17) for the discussion that led to this change. - Update `Control.Monad.Compat` for `base-4.8.0.0` - Update `Data.List.Compat` for `base-4.8.0.0` - Update `Data.Foldable.Compat` for `base-4.8.0.0` ## Changes in 0.7.1 - Backported `Alt` to `Data.Monoid.Compat` - Backported `Down` to `Data.Ord.Compat` ## Changes in 0.7.0 - Add functions and orphan instances introduced by changes to `base-4.7.0.0` and `base-4.8.0.0` ## Changes in 0.6.0 - Update `Prelude.Compat` for `base-4.8.0.0` and AMP ## Changes in 0.5.0 - Remove Control.Exception.Base.Compat and GHC.Exception.Compat - Add System.Exit.Compat.die - Compatibility with base-4.7.1 ## Changes in 0.4.1 - Add `setEnv` and `unsetEnv` to `System.Environment.Compat` ## Changes in 0.4.0 - Major refactoring: base-compat no longer aims to replace all base, only new code is included in module .Compat - Removed stubbed modules - Removed generation scripts ## Changes in 0.3 - Added functions from Base 4.7 (bool, isLeft, isRight) - Added instances from Base 4.7 (Either Foldable, Traversable,...) ## Changes in 0.2.1 - Fix build on windows ## Changes in 0.2.0 - Re-export everything from base - provides access to `VERSION_base` and `MIN_VERSION_base` CPP macros (with `#include "base-compat.h"`) - Do not re-export `System.IO.Error.catch` from `Prelude` for `base` < 4.6.0 - Add `Eq`/`Ord` instance for `ErrorCall` - Remove `GHC.IOBase`, `GHC.Handle`, `Control.Concurrent.QSem`, `Control.Concurrent.QSemN`, `Control.Concurrent.SampleVar`, `Data.HashTable` ## Changes in 0.1.0 - Remove getExecutablePath, it did not work with GHC < 7.2 (patches welcome!) - Add `<>` base-compat-0.9.3/Setup.lhs0000644000000000000000000000011413072705326013715 0ustar0000000000000000#!/usr/bin/env runhaskell > import Distribution.Simple > main = defaultMain base-compat-0.9.3/LICENSE0000644000000000000000000000214013072705326013113 0ustar0000000000000000Copyright (c) 2012-2017 Simon Hengel and Ryan Scott Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. base-compat-0.9.3/src/0000755000000000000000000000000013072705326012700 5ustar0000000000000000base-compat-0.9.3/src/Text/0000755000000000000000000000000013072705326013624 5ustar0000000000000000base-compat-0.9.3/src/Text/Read/0000755000000000000000000000000013072705326014477 5ustar0000000000000000base-compat-0.9.3/src/Text/Read/Compat.hs0000644000000000000000000000245513072705326016264 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Text.Read.Compat ( -- * The 'Read' class Read(..), ReadS, -- * Haskell 2010 functions reads, read, readParen, lex, -- * New parsing functions module Text.ParserCombinators.ReadPrec, L.Lexeme(..), lexP, parens, readListDefault, readListPrecDefault, readEither, readMaybe ) where import Text.Read import Text.ParserCombinators.ReadPrec import qualified Text.Read.Lex as L #if !(MIN_VERSION_base(4,6,0)) import Prelude.Compat import qualified Text.ParserCombinators.ReadP as P -- | Parse a string using the 'Read' instance. -- Succeeds if there is exactly one valid result. -- A 'Left' value indicates a parse error. -- -- /Since: 4.6.0.0/ readEither :: Read a => String -> Either String a readEither s = case [ x | (x,"") <- readPrec_to_S read' minPrec s ] of [x] -> Right x [] -> Left "Prelude.read: no parse" _ -> Left "Prelude.read: ambiguous parse" where read' = do x <- readPrec lift P.skipSpaces return x -- | Parse a string using the 'Read' instance. -- Succeeds if there is exactly one valid result. -- -- /Since: 4.6.0.0/ readMaybe :: Read a => String -> Maybe a readMaybe s = case readEither s of Left _ -> Nothing Right a -> Just a #endif base-compat-0.9.3/src/Control/0000755000000000000000000000000013072705326014320 5ustar0000000000000000base-compat-0.9.3/src/Control/Concurrent/0000755000000000000000000000000013072705326016442 5ustar0000000000000000base-compat-0.9.3/src/Control/Concurrent/Compat.hs0000644000000000000000000000231413072705326020221 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} {-# LANGUAGE RankNTypes #-} module Control.Concurrent.Compat ( module Base , forkFinally , forkOSWithUnmask ) where import Control.Concurrent as Base #if !(MIN_VERSION_base(4,6,0)) import Control.Exception #endif #if !(MIN_VERSION_base(4,9,0)) import GHC.IO (unsafeUnmask) import Prelude #endif #if !(MIN_VERSION_base(4,6,0)) -- | fork a thread and call the supplied function when the thread is about -- to terminate, with an exception or a returned value. The function is -- called with asynchronous exceptions masked. -- -- > forkFinally action and_then = -- > mask $ \restore -> -- > forkIO $ try (restore action) >>= and_then -- -- This function is useful for informing the parent when a child -- terminates, for example. -- -- /Since: 4.6.0.0/ forkFinally :: IO a -> (Either SomeException a -> IO ()) -> IO ThreadId forkFinally action and_then = mask $ \restore -> forkIO $ try (restore action) >>= and_then #endif #if !(MIN_VERSION_base(4,9,0)) -- | Like 'forkIOWithUnmask', but the child thread is a bound thread, -- as with 'forkOS'. forkOSWithUnmask :: ((forall a . IO a -> IO a) -> IO ()) -> IO ThreadId forkOSWithUnmask io = forkOS (io unsafeUnmask) #endif base-compat-0.9.3/src/Control/Concurrent/MVar/0000755000000000000000000000000013072705326017307 5ustar0000000000000000base-compat-0.9.3/src/Control/Concurrent/MVar/Compat.hs0000644000000000000000000000122713072705326021070 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Control.Concurrent.MVar.Compat ( module Base , withMVarMasked ) where import Control.Concurrent.MVar as Base #if !(MIN_VERSION_base(4,7,0)) import Control.Exception (mask_, onException) import Control.Monad (return) import Data.Function (($)) import System.IO (IO) {-| Like 'withMVar', but the @IO@ action in the second argument is executed with asynchronous exceptions masked. @since 4.7.0.0 -} {-# INLINE withMVarMasked #-} withMVarMasked :: MVar a -> (a -> IO b) -> IO b withMVarMasked m io = mask_ $ do a <- takeMVar m b <- io a `onException` putMVar m a putMVar m a return b #endif base-compat-0.9.3/src/Control/Monad/0000755000000000000000000000000013072705326015356 5ustar0000000000000000base-compat-0.9.3/src/Control/Monad/Compat.hs0000644000000000000000000001226413072705326017142 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Control.Monad.Compat ( module Base , Monad(..) , MonadPlus(..) #if !(MIN_VERSION_base(4,8,0)) , foldM , foldM_ , forM , forM_ , guard , mapM , mapM_ , msum , sequence , sequence_ , unless , when , (<$!>) #endif #if !(MIN_VERSION_base(4,9,0)) , forever , filterM , mapAndUnzipM , zipWithM , zipWithM_ , replicateM , replicateM_ #endif ) where #if MIN_VERSION_base(4,9,0) import Control.Monad as Base #else import Control.Monad as Base hiding ( forever , filterM , mapAndUnzipM , zipWithM , zipWithM_ , replicateM , replicateM_ # if !(MIN_VERSION_base(4,8,0)) , foldM , foldM_ , forM , forM_ , guard , mapM , mapM_ , msum , sequence , sequence_ , unless , when # endif ) import Control.Applicative import Data.Foldable.Compat import Data.Traversable import Prelude.Compat #endif #if !(MIN_VERSION_base(4,8,0)) -- | Conditional execution of 'Applicative' expressions. For example, -- -- > when debug (putStrLn "Debugging") -- -- will output the string @Debugging@ if the Boolean value @debug@ -- is 'True', and otherwise do nothing. when :: (Applicative f) => Bool -> f () -> f () {-# INLINEABLE when #-} {-# SPECIALISE when :: Bool -> IO () -> IO () #-} {-# SPECIALISE when :: Bool -> Maybe () -> Maybe () #-} when p s = if p then s else pure () -- | @'guard' b@ is @'pure' ()@ if @b@ is 'True', -- and 'empty' if @b@ is 'False'. guard :: (Alternative f) => Bool -> f () guard True = pure () guard False = empty -- | The reverse of 'when'. unless :: (Applicative f) => Bool -> f () -> f () {-# INLINEABLE unless #-} {-# SPECIALISE unless :: Bool -> IO () -> IO () #-} {-# SPECIALISE unless :: Bool -> Maybe () -> Maybe () #-} unless p s = if p then pure () else s {- | The 'foldM' function is analogous to 'foldl', except that its result is encapsulated in a monad. Note that 'foldM' works from left-to-right over the list arguments. This could be an issue where @('>>')@ and the `folded function' are not commutative. > foldM f a1 [x1, x2, ..., xm] == > do > a2 <- f a1 x1 > a3 <- f a2 x2 > ... > f am xm If right-to-left evaluation is required, the input list should be reversed. Note: 'foldM' is the same as 'foldlM' -} foldM :: (Foldable t, Monad m) => (b -> a -> m b) -> b -> t a -> m b {-# INLINEABLE foldM #-} {-# SPECIALISE foldM :: (a -> b -> IO a) -> a -> [b] -> IO a #-} {-# SPECIALISE foldM :: (a -> b -> Maybe a) -> a -> [b] -> Maybe a #-} foldM = foldlM -- | Like 'foldM', but discards the result. foldM_ :: (Foldable t, Monad m) => (b -> a -> m b) -> b -> t a -> m () {-# INLINEABLE foldM_ #-} {-# SPECIALISE foldM_ :: (a -> b -> IO a) -> a -> [b] -> IO () #-} {-# SPECIALISE foldM_ :: (a -> b -> Maybe a) -> a -> [b] -> Maybe () #-} foldM_ f a xs = foldlM f a xs >> return () infixl 4 <$!> -- | Strict version of 'Data.Functor.<$>'. -- -- /Since: 4.8.0.0/ (<$!>) :: Monad m => (a -> b) -> m a -> m b {-# INLINE (<$!>) #-} f <$!> m = do x <- m let z = f x z `seq` return z #endif #if !(MIN_VERSION_base(4,9,0)) -- | @'forever' act@ repeats the action infinitely. forever :: (Applicative f) => f a -> f b {-# INLINE forever #-} forever a = let a' = a *> a' in a' -- Use explicit sharing here, as it is prevents a space leak regardless of -- optimizations. -- | This generalizes the list-based 'filter' function. {-# INLINE filterM #-} filterM :: (Applicative m) => (a -> m Bool) -> [a] -> m [a] filterM p = foldr (\ x -> liftA2 (\ flg -> if flg then (x:) else id) (p x)) (pure []) -- | The 'mapAndUnzipM' function maps its first argument over a list, returning -- the result as a pair of lists. This function is mainly used with complicated -- data structures or a state-transforming monad. mapAndUnzipM :: (Applicative m) => (a -> m (b,c)) -> [a] -> m ([b], [c]) {-# INLINE mapAndUnzipM #-} mapAndUnzipM f xs = unzip <$> traverse f xs -- | The 'zipWithM' function generalizes 'zipWith' to arbitrary applicative functors. zipWithM :: (Applicative m) => (a -> b -> m c) -> [a] -> [b] -> m [c] {-# INLINE zipWithM #-} zipWithM f xs ys = sequenceA (zipWith f xs ys) -- | 'zipWithM_' is the extension of 'zipWithM' which ignores the final result. zipWithM_ :: (Applicative m) => (a -> b -> m c) -> [a] -> [b] -> m () {-# INLINE zipWithM_ #-} zipWithM_ f xs ys = sequenceA_ (zipWith f xs ys) -- | @'replicateM' n act@ performs the action @n@ times, -- gathering the results. replicateM :: (Applicative m) => Int -> m a -> m [a] {-# INLINEABLE replicateM #-} {-# SPECIALISE replicateM :: Int -> IO a -> IO [a] #-} {-# SPECIALISE replicateM :: Int -> Maybe a -> Maybe [a] #-} replicateM cnt0 f = loop cnt0 where loop cnt | cnt <= 0 = pure [] | otherwise = liftA2 (:) f (loop (cnt - 1)) -- | Like 'replicateM', but discards the result. replicateM_ :: (Applicative m) => Int -> m a -> m () {-# INLINEABLE replicateM_ #-} {-# SPECIALISE replicateM_ :: Int -> IO a -> IO () #-} {-# SPECIALISE replicateM_ :: Int -> Maybe a -> Maybe () #-} replicateM_ cnt0 f = loop cnt0 where loop cnt | cnt <= 0 = pure () | otherwise = f *> loop (cnt - 1) #endif base-compat-0.9.3/src/Control/Monad/ST/0000755000000000000000000000000013072705326015704 5ustar0000000000000000base-compat-0.9.3/src/Control/Monad/ST/Lazy/0000755000000000000000000000000013072705326016623 5ustar0000000000000000base-compat-0.9.3/src/Control/Monad/ST/Lazy/Unsafe/0000755000000000000000000000000013072705326020044 5ustar0000000000000000base-compat-0.9.3/src/Control/Monad/ST/Lazy/Unsafe/Compat.hs0000644000000000000000000000051313072705326021622 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Control.Monad.ST.Lazy.Unsafe.Compat ( -- * Unsafe operations unsafeInterleaveST , unsafeIOToST ) where #if MIN_VERSION_base(4,6,0) import Control.Monad.ST.Lazy.Unsafe (unsafeInterleaveST, unsafeIOToST) #else import Control.Monad.ST.Lazy (unsafeInterleaveST, unsafeIOToST) #endif base-compat-0.9.3/src/Control/Monad/ST/Unsafe/0000755000000000000000000000000013072705326017125 5ustar0000000000000000base-compat-0.9.3/src/Control/Monad/ST/Unsafe/Compat.hs0000644000000000000000000000054713072705326020712 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Control.Monad.ST.Unsafe.Compat ( -- * Unsafe operations unsafeInterleaveST , unsafeIOToST , unsafeSTToIO ) where #if MIN_VERSION_base(4,6,0) import Control.Monad.ST.Unsafe (unsafeInterleaveST, unsafeIOToST, unsafeSTToIO) #else import Control.Monad.ST (unsafeInterleaveST, unsafeIOToST, unsafeSTToIO) #endif base-compat-0.9.3/src/Data/0000755000000000000000000000000013072705326013551 5ustar0000000000000000base-compat-0.9.3/src/Data/Bits/0000755000000000000000000000000013072705326014452 5ustar0000000000000000base-compat-0.9.3/src/Data/Bits/Compat.hs0000644000000000000000000000745413072705326016243 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} {-# LANGUAGE BangPatterns, PatternGuards #-} module Data.Bits.Compat ( module Base , bitDefault , testBitDefault , popCountDefault #if MIN_VERSION_base(4,7,0) , toIntegralSized #endif ) where import Data.Bits as Base #if !(MIN_VERSION_base(4,8,0)) import Prelude #endif #if !(MIN_VERSION_base(4,6,0)) -- | Default implementation for 'bit'. -- -- Note that: @bitDefault i = 1 `shiftL` i@ -- -- /Since: 4.6.0.0/ bitDefault :: (Bits a, Num a) => Int -> a bitDefault = \i -> 1 `shiftL` i {-# INLINE bitDefault #-} -- | Default implementation for 'testBit'. -- -- Note that: @testBitDefault x i = (x .&. bit i) /= 0@ -- -- /Since: 4.6.0.0/ testBitDefault :: (Bits a, Num a) => a -> Int -> Bool testBitDefault = \x i -> (x .&. bit i) /= 0 {-# INLINE testBitDefault #-} -- | Default implementation for 'popCount'. -- -- This implementation is intentionally naive. Instances are expected to provide -- an optimized implementation for their size. -- -- /Since: 4.6.0.0/ popCountDefault :: (Bits a, Num a) => a -> Int popCountDefault = go 0 where go !c 0 = c go c w = go (c+1) (w .&. (w - 1)) -- clear the least significant {-# INLINABLE popCountDefault #-} #endif #if MIN_VERSION_base(4,7,0) && !(MIN_VERSION_base(4,8,0)) -- | Attempt to convert an 'Integral' type @a@ to an 'Integral' type @b@ using -- the size of the types as measured by 'Bits' methods. -- -- A simpler version of this function is: -- -- > toIntegral :: (Integral a, Integral b) => a -> Maybe b -- > toIntegral x -- > | toInteger x == y = Just (fromInteger y) -- > | otherwise = Nothing -- > where -- > y = toInteger x -- -- This version requires going through 'Integer', which can be inefficient. -- However, @toIntegralSized@ is optimized to allow GHC to statically determine -- the relative type sizes (as measured by 'bitSizeMaybe' and 'isSigned') and -- avoid going through 'Integer' for many types. (The implementation uses -- 'fromIntegral', which is itself optimized with rules for @base@ types but may -- go through 'Integer' for some type pairs.) -- -- /Since: 4.8.0.0/ toIntegralSized :: (Integral a, Integral b, Bits a, Bits b) => a -> Maybe b toIntegralSized x -- See Note [toIntegralSized optimization] | maybe True (<= x) yMinBound , maybe True (x <=) yMaxBound = Just y | otherwise = Nothing where y = fromIntegral x xWidth = bitSizeMaybe x yWidth = bitSizeMaybe y yMinBound | isBitSubType x y = Nothing | isSigned x, not (isSigned y) = Just 0 | isSigned x, isSigned y , Just yW <- yWidth = Just (negate $ bit (yW-1)) -- Assumes sub-type | otherwise = Nothing yMaxBound | isBitSubType x y = Nothing | isSigned x, not (isSigned y) , Just xW <- xWidth, Just yW <- yWidth , xW <= yW+1 = Nothing -- Max bound beyond a's domain | Just yW <- yWidth = if isSigned y then Just (bit (yW-1)-1) else Just (bit yW-1) | otherwise = Nothing {-# INLINEABLE toIntegralSized #-} -- | 'True' if the size of @a@ is @<=@ the size of @b@, where size is measured -- by 'bitSizeMaybe' and 'isSigned'. isBitSubType :: (Bits a, Bits b) => a -> b -> Bool isBitSubType x y -- Reflexive | xWidth == yWidth, xSigned == ySigned = True -- Every integer is a subset of 'Integer' | ySigned, Nothing == yWidth = True | not xSigned, not ySigned, Nothing == yWidth = True -- Sub-type relations between fixed-with types | xSigned == ySigned, Just xW <- xWidth, Just yW <- yWidth = xW <= yW | not xSigned, ySigned, Just xW <- xWidth, Just yW <- yWidth = xW < yW | otherwise = False where xWidth = bitSizeMaybe x xSigned = isSigned x yWidth = bitSizeMaybe y ySigned = isSigned y {-# INLINE isBitSubType #-} #endif base-compat-0.9.3/src/Data/Complex/0000755000000000000000000000000013072705326015160 5ustar0000000000000000base-compat-0.9.3/src/Data/Complex/Compat.hs0000644000000000000000000000251513072705326016742 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.Complex.Compat ( module Base #if MIN_VERSION_base(4,4,0) && !(MIN_VERSION_base(4,8,0)) , realPart , imagPart , mkPolar , cis , conjugate #endif ) where #if !(MIN_VERSION_base(4,4,0)) || MIN_VERSION_base(4,8,0) import Data.Complex as Base #else import Data.Complex as Base hiding ( realPart , imagPart , mkPolar , cis , conjugate ) import Prelude #endif #if MIN_VERSION_base(4,4,0) && !(MIN_VERSION_base(4,8,0)) -- | Extracts the real part of a complex number. realPart :: Complex a -> a realPart (x :+ _) = x -- | Extracts the imaginary part of a complex number. imagPart :: Complex a -> a imagPart (_ :+ y) = y -- | The conjugate of a complex number. {-# SPECIALISE conjugate :: Complex Double -> Complex Double #-} conjugate :: Num a => Complex a -> Complex a conjugate (x:+y) = x :+ (-y) -- | Form a complex number from polar components of magnitude and phase. {-# SPECIALISE mkPolar :: Double -> Double -> Complex Double #-} mkPolar :: Floating a => a -> a -> Complex a mkPolar r theta = r * cos theta :+ r * sin theta -- | @'cis' t@ is a complex value with magnitude @1@ -- and phase @t@ (modulo @2*'pi'@). {-# SPECIALISE cis :: Double -> Complex Double #-} cis :: Floating a => a -> Complex a cis theta = cos theta :+ sin theta #endif base-compat-0.9.3/src/Data/Monoid/0000755000000000000000000000000013072705326014776 5ustar0000000000000000base-compat-0.9.3/src/Data/Monoid/Compat.hs0000644000000000000000000000046213072705326016557 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.Monoid.Compat ( module Base , (<>) ) where import Data.Monoid as Base #if !(MIN_VERSION_base(4,5,0)) infixr 6 <> -- | An infix synonym for 'mappend'. -- -- /Since: 4.5.0.0/ (<>) :: Monoid m => m -> m -> m (<>) = mappend {-# INLINE (<>) #-} #endif base-compat-0.9.3/src/Data/Type/0000755000000000000000000000000013072705326014472 5ustar0000000000000000base-compat-0.9.3/src/Data/Type/Coercion/0000755000000000000000000000000013072705326016233 5ustar0000000000000000base-compat-0.9.3/src/Data/Type/Coercion/Compat.hs0000644000000000000000000000076213072705326020017 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} {-# LANGUAGE RankNTypes #-} module Data.Type.Coercion.Compat ( #if MIN_VERSION_base(4,7,0) module Base , gcoerceWith #endif ) where #if MIN_VERSION_base(4,7,0) import Data.Type.Coercion as Base # if !(MIN_VERSION_base(4,10,0)) import Data.Coerce (Coercible) -- | Generalized form of type-safe cast using representational equality -- -- /Since: 4.10.0.0/ gcoerceWith :: Coercion a b -> (Coercible a b => r) -> r gcoerceWith Coercion x = x # endif #endif base-compat-0.9.3/src/Data/STRef/0000755000000000000000000000000013072705326014534 5ustar0000000000000000base-compat-0.9.3/src/Data/STRef/Compat.hs0000644000000000000000000000065113072705326016315 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.STRef.Compat ( module Base , modifySTRef' ) where import Data.STRef as Base #if !(MIN_VERSION_base(4,6,0)) import Control.Monad.ST (ST) import Prelude (seq) -- | Strict version of 'modifySTRef' -- -- /Since: 4.6.0.0/ modifySTRef' :: STRef s a -> (a -> a) -> ST s () modifySTRef' ref f = do x <- readSTRef ref let x' = f x x' `seq` writeSTRef ref x' #endif base-compat-0.9.3/src/Data/List/0000755000000000000000000000000013072705326014464 5ustar0000000000000000base-compat-0.9.3/src/Data/List/Compat.hs0000644000000000000000000001254513072705326016252 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} {-# LANGUAGE BangPatterns #-} module Data.List.Compat ( module Base #if !(MIN_VERSION_base(4,8,0)) , all , and , any , concat , concatMap , elem , find , foldl , foldl' , foldl1 , foldr , foldr1 , length , maximum , maximumBy , minimum , minimumBy , notElem , nub , nubBy , null , or , product , sum , union , unionBy , mapAccumL , mapAccumR , isSubsequenceOf , sortOn , uncons , scanl' #endif #if !(MIN_VERSION_base(4,5,0)) , dropWhileEnd #endif ) where #if MIN_VERSION_base(4,8,0) import Data.List as Base #else import Data.List as Base hiding ( all , and , any , concat , concatMap , elem , find , foldl , foldl' , foldl1 , foldr , foldr1 , length , maximum , maximumBy , minimum , minimumBy , notElem , nub , nubBy , null , or , product , sum , union , unionBy , mapAccumL , mapAccumR ) import Data.Foldable.Compat import Data.Traversable import Prelude.Compat hiding (foldr, null) import Data.Ord (comparing) #endif #if !(MIN_VERSION_base(4,5,0)) -- | The 'dropWhileEnd' function drops the largest suffix of a list -- in which the given predicate holds for all elements. For example: -- -- > dropWhileEnd isSpace "foo\n" == "foo" -- > dropWhileEnd isSpace "foo bar" == "foo bar" -- > dropWhileEnd isSpace ("foo\n" ++ undefined) == "foo" ++ undefined -- -- /Since: 4.5.0.0/ dropWhileEnd :: (a -> Bool) -> [a] -> [a] dropWhileEnd p = foldr (\x xs -> if p x && null xs then [] else x : xs) [] #endif #if !(MIN_VERSION_base(4,8,0)) -- | The 'isSubsequenceOf' function takes two lists and returns 'True' if the -- first list is a subsequence of the second list. -- -- @'isSubsequenceOf' x y@ is equivalent to @'elem' x ('subsequences' y)@. -- -- /Since: 4.8.0.0/ -- -- ==== __Examples__ -- -- >>> isSubsequenceOf "GHC" "The Glorious Haskell Compiler" -- True -- >>> isSubsequenceOf ['a','d'..'z'] ['a'..'z'] -- True -- >>> isSubsequenceOf [1..10] [10,9..0] -- False isSubsequenceOf :: (Eq a) => [a] -> [a] -> Bool isSubsequenceOf [] _ = True isSubsequenceOf _ [] = False isSubsequenceOf a@(x:a') (y:b) | x == y = isSubsequenceOf a' b | otherwise = isSubsequenceOf a b -- | Sort a list by comparing the results of a key function applied to each -- element. @sortOn f@ is equivalent to @sortBy . comparing f@, but has the -- performance advantage of only evaluating @f@ once for each element in the -- input list. This is called the decorate-sort-undecorate paradigm, or -- Schwartzian transform. -- -- /Since: 4.8.0.0/ sortOn :: Ord b => (a -> b) -> [a] -> [a] sortOn f = map snd . sortBy (comparing fst) . map (\x -> let y = f x in y `seq` (y, x)) -- | Decompose a list into its head and tail. If the list is empty, -- returns 'Nothing'. If the list is non-empty, returns @'Just' (x, xs)@, -- where @x@ is the head of the list and @xs@ its tail. -- -- /Since: 4.8.0.0/ uncons :: [a] -> Maybe (a, [a]) uncons [] = Nothing uncons (x:xs) = Just (x, xs) -- | A strictly accumulating version of 'scanl' {-# NOINLINE [1] scanl' #-} scanl' :: (b -> a -> b) -> b -> [a] -> [b] -- This peculiar form is needed to prevent scanl' from being rewritten -- in its own right hand side. scanl' = scanlGo' where scanlGo' :: (b -> a -> b) -> b -> [a] -> [b] scanlGo' f !q ls = q : (case ls of [] -> [] x:xs -> scanlGo' f (f q x) xs) -- | /O(n^2)/. The 'nub' function removes duplicate elements from a list. -- In particular, it keeps only the first occurrence of each element. -- (The name 'nub' means \`essence\'.) -- It is a special case of 'nubBy', which allows the programmer to supply -- their own equality test. nub :: (Eq a) => [a] -> [a] nub = nubBy (==) -- | The 'nubBy' function behaves just like 'nub', except it uses a -- user-supplied equality predicate instead of the overloaded '==' -- function. nubBy :: (a -> a -> Bool) -> [a] -> [a] -- stolen from HBC nubBy eq l = nubBy' l [] where nubBy' [] _ = [] nubBy' (y:ys) xs | elem_by eq y xs = nubBy' ys xs | otherwise = y : nubBy' ys (y:xs) -- Not exported: -- Note that we keep the call to `eq` with arguments in the -- same order as in the reference (prelude) implementation, -- and that this order is different from how `elem` calls (==). -- See #2528, #3280 and #7913. -- 'xs' is the list of things we've seen so far, -- 'y' is the potential new element elem_by :: (a -> a -> Bool) -> a -> [a] -> Bool elem_by _ _ [] = False elem_by eq y (x:xs) = x `eq` y || elem_by eq y xs -- | The 'union' function returns the list union of the two lists. -- For example, -- -- > "dog" `union` "cow" == "dogcw" -- -- Duplicates, and elements of the first list, are removed from the -- the second list, but if the first list contains duplicates, so will -- the result. -- It is a special case of 'unionBy', which allows the programmer to supply -- their own equality test. union :: (Eq a) => [a] -> [a] -> [a] union = unionBy (==) -- | The 'unionBy' function is the non-overloaded version of 'union'. unionBy :: (a -> a -> Bool) -> [a] -> [a] -> [a] unionBy eq xs ys = xs ++ foldl (flip (deleteBy eq)) (nubBy eq ys) xs #endif base-compat-0.9.3/src/Data/Proxy/0000755000000000000000000000000013072705326014672 5ustar0000000000000000base-compat-0.9.3/src/Data/Proxy/Compat.hs0000644000000000000000000000124613072705326016454 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.Proxy.Compat ( #if MIN_VERSION_base(4,7,0) module Base, #endif asProxyTypeOf ) where #if MIN_VERSION_base(4,7,0) # if MIN_VERSION_base(4,10,0) import Data.Proxy as Base # else import Data.Proxy as Base hiding (asProxyTypeOf) # endif #endif #if !(MIN_VERSION_base(4,10,0)) import Prelude (const) -- | 'asProxyTypeOf' is a type-restricted version of 'const'. -- It is usually used as an infix operator, and its typing forces its first -- argument (which is usually overloaded) to have the same type as the tag -- of the second. asProxyTypeOf :: a -> proxy a -> a asProxyTypeOf = const {-# INLINE asProxyTypeOf #-} #endif base-compat-0.9.3/src/Data/Word/0000755000000000000000000000000013072705326014464 5ustar0000000000000000base-compat-0.9.3/src/Data/Word/Compat.hs0000644000000000000000000000226713072705326016252 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.Word.Compat ( module Base , byteSwap16 , byteSwap32 , byteSwap64 ) where import Data.Word as Base #if !(MIN_VERSION_base(4,7,0)) import Data.Bits -- | Swap bytes in 'Word16'. -- -- /Since: 4.7.0.0/ byteSwap16 :: Word16 -> Word16 byteSwap16 w = ((w `shiftR` 8) .&. 0x00ff) .|. ((w .&. 0x00ff) `shiftL` 8) -- | Reverse order of bytes in 'Word32'. -- -- /Since: 4.7.0.0/ byteSwap32 :: Word32 -> Word32 byteSwap32 w = ((w .&. 0xff000000) `shiftR` 24) .|. ((w .&. 0x00ff0000) `shiftR` 8) .|. ((w .&. 0x0000ff00) `shiftL` 8) .|. ((w .&. 0x000000ff) `shiftL` 24) -- | Reverse order of bytes in 'Word64'. -- -- /Since: 4.7.0.0/ byteSwap64 :: Word64 -> Word64 byteSwap64 w = ((w .&. 0xff00000000000000) `shiftR` 56) .|. ((w .&. 0x00ff000000000000) `shiftR` 40) .|. ((w .&. 0x0000ff0000000000) `shiftR` 24) .|. ((w .&. 0x000000ff00000000) `shiftR` 8) .|. ((w .&. 0x00000000ff000000) `shiftL` 8) .|. ((w .&. 0x0000000000ff0000) `shiftL` 24) .|. ((w .&. 0x000000000000ff00) `shiftL` 40) .|. ((w .&. 0x00000000000000ff) `shiftL` 56) #endif base-compat-0.9.3/src/Data/Ratio/0000755000000000000000000000000013072705326014627 5ustar0000000000000000base-compat-0.9.3/src/Data/Ratio/Compat.hs0000644000000000000000000000151313072705326016406 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.Ratio.Compat ( module Base #if MIN_VERSION_base(4,4,0) && !(MIN_VERSION_base(4,9,0)) , denominator , numerator #endif ) where #if !(MIN_VERSION_base(4,4,0)) || MIN_VERSION_base(4,9,0) import Data.Ratio as Base #else import Data.Ratio as Base hiding ( denominator , numerator ) import GHC.Real (Ratio(..)) #endif #if MIN_VERSION_base(4,4,0) && !(MIN_VERSION_base(4,9,0)) -- | Extract the numerator of the ratio in reduced form: -- the numerator and denominator have no common factor and the denominator -- is positive. numerator :: Ratio a -> a numerator (x :% _) = x -- | Extract the denominator of the ratio in reduced form: -- the numerator and denominator have no common factor and the denominator -- is positive. denominator :: Ratio a -> a denominator (_ :% y) = y #endif base-compat-0.9.3/src/Data/Either/0000755000000000000000000000000013072705326014771 5ustar0000000000000000base-compat-0.9.3/src/Data/Either/Compat.hs0000644000000000000000000000231313072705326016547 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.Either.Compat ( module Base , isLeft , isRight , fromLeft , fromRight ) where import Data.Either as Base #if !(MIN_VERSION_base(4,7,0)) import Data.Bool (Bool(..)) -- | Return `True` if the given value is a `Left`-value, `False` otherwise. -- -- /Since: 4.7.0.0/ isLeft :: Either a b -> Bool isLeft (Left _) = True isLeft (Right _) = False -- | Return `True` if the given value is a `Right`-value, `False` otherwise. -- -- /Since: 4.7.0.0/ isRight :: Either a b -> Bool isRight (Left _) = False isRight (Right _) = True #endif #if !(MIN_VERSION_base(4,10,0)) -- | Return the contents of a 'Left'-value or a default value otherwise. -- -- /Since: 4.10.0.0/ -- -- ==== __Examples__ -- -- Basic usage: -- -- >>> fromLeft 1 (Left 3) -- 3 -- >>> fromLeft 1 (Right "foo") -- 1 -- fromLeft :: a -> Either a b -> a fromLeft _ (Left a) = a fromLeft a _ = a -- | Return the contents of a 'Right'-value or a default value otherwise. -- -- /Since: 4.10.0.0/ -- -- ==== __Examples__ -- -- Basic usage: -- -- >>> fromRight 1 (Right 3) -- 3 -- >>> fromRight 1 (Left "foo") -- 1 -- fromRight :: b -> Either a b -> b fromRight _ (Right b) = b fromRight b _ = b #endif base-compat-0.9.3/src/Data/IORef/0000755000000000000000000000000013072705326014515 5ustar0000000000000000base-compat-0.9.3/src/Data/IORef/Compat.hs0000644000000000000000000000203513072705326016274 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.IORef.Compat ( module Base , modifyIORef' , atomicModifyIORef' , atomicWriteIORef ) where import Data.IORef as Base #if !(MIN_VERSION_base(4,6,0)) import Prelude -- |Strict version of 'modifyIORef' -- -- /Since: 4.6.0.0/ modifyIORef' :: IORef a -> (a -> a) -> IO () modifyIORef' ref f = do x <- readIORef ref let x' = f x x' `seq` writeIORef ref x' -- | Strict version of 'atomicModifyIORef'. This forces both the value stored -- in the 'IORef' as well as the value returned. -- -- /Since: 4.6.0.0/ atomicModifyIORef' :: IORef a -> (a -> (a,b)) -> IO b atomicModifyIORef' ref f = do b <- atomicModifyIORef ref $ \a -> case f a of v@(a',_) -> a' `seq` v b `seq` return b -- | Variant of 'writeIORef' with the \"barrier to reordering\" property that -- 'atomicModifyIORef' has. -- -- /Since: 4.6.0.0/ atomicWriteIORef :: IORef a -> a -> IO () atomicWriteIORef ref a = do x <- atomicModifyIORef ref (\_ -> (a, ())) x `seq` return () #endif base-compat-0.9.3/src/Data/Functor/0000755000000000000000000000000013072705326015171 5ustar0000000000000000base-compat-0.9.3/src/Data/Functor/Compat.hs0000644000000000000000000000056313072705326016754 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.Functor.Compat ( module Base , Functor(..) , ($>) , void ) where import Data.Functor as Base #if !(MIN_VERSION_base(4,7,0)) import Control.Monad.Compat (void) import Data.Function (flip) infixl 4 $> -- | Flipped version of '$>'. -- -- /Since: 4.7.0.0/ ($>) :: Functor f => f a -> b -> f b ($>) = flip (<$) #endif base-compat-0.9.3/src/Data/Functor/Const/0000755000000000000000000000000013072705326016257 5ustar0000000000000000base-compat-0.9.3/src/Data/Functor/Const/Compat.hs0000644000000000000000000000020313072705326020031 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.Functor.Const.Compat (Const(..)) where import Control.Applicative (Const(..)) base-compat-0.9.3/src/Data/Bool/0000755000000000000000000000000013072705326014444 5ustar0000000000000000base-compat-0.9.3/src/Data/Bool/Compat.hs0000644000000000000000000000060313072705326016222 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.Bool.Compat ( module Base , bool ) where import Data.Bool as Base #if !(MIN_VERSION_base(4,7,0)) -- | Case analysis for the 'Bool' type. -- @bool a b p@ evaluates to @a@ when @p@ is @False@, and evaluates to @b@ -- when @p@ is @True@. -- -- /Since: 4.7.0.0/ bool :: a -> a -> Bool -> a bool f _ False = f bool _ t True = t #endif base-compat-0.9.3/src/Data/String/0000755000000000000000000000000013072705326015017 5ustar0000000000000000base-compat-0.9.3/src/Data/String/Compat.hs0000644000000000000000000000040213072705326016572 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.String.Compat ( module Base , String , lines , words , unlines , unwords ) where import Data.String as Base #if !(MIN_VERSION_base(4,4,0)) import Prelude (String, lines, words, unlines, unwords) #endif base-compat-0.9.3/src/Data/Function/0000755000000000000000000000000013072705326015336 5ustar0000000000000000base-compat-0.9.3/src/Data/Function/Compat.hs0000644000000000000000000000070013072705326017112 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.Function.Compat ( module Base , (&) ) where import Data.Function as Base #if !(MIN_VERSION_base(4,8,0)) infixl 1 & -- | '&' is a reverse application operator. This provides notational -- convenience. Its precedence is one higher than that of the forward -- application operator '$', which allows '&' to be nested in '$'. -- -- /Since: 4.8.0.0/ (&) :: a -> (a -> b) -> b x & f = f x #endif base-compat-0.9.3/src/Data/Version/0000755000000000000000000000000013072705326015176 5ustar0000000000000000base-compat-0.9.3/src/Data/Version/Compat.hs0000644000000000000000000000047113072705326016757 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.Version.Compat ( module Base , makeVersion ) where import Data.Version as Base #if !(MIN_VERSION_base(4,8,0)) import Prelude.Compat -- | Construct tag-less 'Version' -- -- /Since: 4.8.0.0/ makeVersion :: [Int] -> Version makeVersion b = Version b [] #endif base-compat-0.9.3/src/Data/Foldable/0000755000000000000000000000000013072705326015261 5ustar0000000000000000base-compat-0.9.3/src/Data/Foldable/Compat.hs0000644000000000000000000000305413072705326017042 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Data.Foldable.Compat ( module Base #if !(MIN_VERSION_base(4,8,0)) , length , null #endif #if !(MIN_VERSION_base(4,10,0)) , maximumBy , minimumBy #endif ) where #if MIN_VERSION_base(4,10,0) import Data.Foldable as Base #else import Data.Foldable as Base hiding (maximumBy, minimumBy) import Prelude (Ordering(..)) #endif #if !(MIN_VERSION_base(4,8,0)) import Prelude (Bool(..), Int, (+)) -- | Test whether the structure is empty. The default implementation is -- optimized for structures that are similar to cons-lists, because there -- is no general way to do better. null :: Foldable t => t a -> Bool null = foldr (\_ _ -> False) True -- | Returns the size/length of a finite structure as an 'Int'. The -- default implementation is optimized for structures that are similar to -- cons-lists, because there is no general way to do better. length :: Foldable t => t a -> Int length = foldl' (\c _ -> c+1) 0 #endif #if !(MIN_VERSION_base(4,10,0)) -- | The largest element of a non-empty structure with respect to the -- given comparison function. maximumBy :: Foldable t => (a -> a -> Ordering) -> t a -> a maximumBy cmp = foldl1 max' where max' x y = case cmp x y of GT -> x _ -> y -- | The least element of a non-empty structure with respect to the -- given comparison function. minimumBy :: Foldable t => (a -> a -> Ordering) -> t a -> a minimumBy cmp = foldl1 min' where min' x y = case cmp x y of GT -> y _ -> x #endif base-compat-0.9.3/src/Numeric/0000755000000000000000000000000013072705326014302 5ustar0000000000000000base-compat-0.9.3/src/Numeric/Compat.hs0000644000000000000000000000617713072705326016074 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Numeric.Compat ( module Base , showFFloatAlt , showGFloatAlt ) where import Numeric as Base #if !(MIN_VERSION_base(4,7,0)) import Data.Char (intToDigit) import GHC.Float import Prelude -- | Show a signed 'RealFloat' value -- using standard decimal notation (e.g. @245000@, @0.0015@). -- -- This behaves as 'showFFloat', except that a decimal point -- is always guaranteed, even if not needed. -- -- /Since: 4.7.0.0/ showFFloatAlt :: (RealFloat a) => Maybe Int -> a -> ShowS showFFloatAlt d x = showString (formatRealFloatAlt FFFixed d True x) -- | Show a signed 'RealFloat' value -- using standard decimal notation for arguments whose absolute value lies -- between @0.1@ and @9,999,999@, and scientific notation otherwise. -- -- This behaves as 'showFFloat', except that a decimal point -- is always guaranteed, even if not needed. -- -- /Since: 4.7.0.0/ showGFloatAlt :: (RealFloat a) => Maybe Int -> a -> ShowS showGFloatAlt d x = showString (formatRealFloatAlt FFGeneric d True x) formatRealFloatAlt :: (RealFloat a) => FFFormat -> Maybe Int -> Bool -> a -> String formatRealFloatAlt fmt decs alt x | isNaN x = "NaN" | isInfinite x = if x < 0 then "-Infinity" else "Infinity" | x < 0 || isNegativeZero x = '-':doFmt fmt (floatToDigits (toInteger base) (-x)) | otherwise = doFmt fmt (floatToDigits (toInteger base) x) where base = 10 doFmt format (is, e) = let ds = map intToDigit is in case format of FFGeneric -> doFmt (if e < 0 || e > 7 then FFExponent else FFFixed) (is,e) FFExponent -> case decs of Nothing -> let show_e' = show (e-1) in case ds of "0" -> "0.0e0" [d] -> d : ".0e" ++ show_e' (d:ds') -> d : '.' : ds' ++ "e" ++ show_e' [] -> error "formatRealFloat/doFmt/FFExponent: []" Just dec -> let dec' = max dec 1 in case is of [0] -> '0' :'.' : take dec' (repeat '0') ++ "e0" _ -> let (ei,is') = roundTo base (dec'+1) is (d:ds') = map intToDigit (if ei > 0 then init is' else is') in d:'.':ds' ++ 'e':show (e-1+ei) FFFixed -> let mk0 ls = case ls of { "" -> "0" ; _ -> ls} in case decs of Nothing | e <= 0 -> "0." ++ replicate (-e) '0' ++ ds | otherwise -> let f 0 s rs = mk0 (reverse s) ++ '.':mk0 rs f n s "" = f (n-1) ('0':s) "" f n s (r:rs) = f (n-1) (r:s) rs in f e "" ds Just dec -> let dec' = max dec 0 in if e >= 0 then let (ei,is') = roundTo base (dec' + e) is (ls,rs) = splitAt (e+ei) (map intToDigit is') in mk0 ls ++ (if null rs && not alt then "" else '.':rs) else let (ei,is') = roundTo base dec' (replicate (-e) 0 ++ is) d:ds' = map intToDigit (if ei > 0 then is' else 0:is') in d : (if null ds' && not alt then "" else '.':ds') #endif base-compat-0.9.3/src/Foreign/0000755000000000000000000000000013072705326014271 5ustar0000000000000000base-compat-0.9.3/src/Foreign/Compat.hs0000644000000000000000000000024313072705326016047 0ustar0000000000000000{-# LANGUAGE NoImplicitPrelude #-} module Foreign.Compat ( module Base , module Marshal ) where import Foreign as Base import Foreign.Marshal.Compat as Marshal base-compat-0.9.3/src/Foreign/Marshal/0000755000000000000000000000000013072705326015660 5ustar0000000000000000base-compat-0.9.3/src/Foreign/Marshal/Compat.hs0000644000000000000000000000046213072705326017441 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Foreign.Marshal.Compat ( module Base , module Alloc , module Array , module Utils ) where import Foreign.Marshal as Base import Foreign.Marshal.Alloc.Compat as Alloc import Foreign.Marshal.Array.Compat as Array import Foreign.Marshal.Utils.Compat as Utils base-compat-0.9.3/src/Foreign/Marshal/Alloc/0000755000000000000000000000000013072705326016712 5ustar0000000000000000base-compat-0.9.3/src/Foreign/Marshal/Alloc/Compat.hs0000644000000000000000000000237413072705326020477 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} {-# LANGUAGE ForeignFunctionInterface #-} module Foreign.Marshal.Alloc.Compat ( module Base , calloc , callocBytes ) where import Foreign.Marshal.Alloc as Base #if !(MIN_VERSION_base(4,8,0)) import Foreign.C.Types import Foreign.Ptr (Ptr, nullPtr) import Foreign.Storable (Storable(..)) import GHC.IO.Exception import Prelude.Compat -- |Like 'malloc' but memory is filled with bytes of value zero. -- {-# INLINE calloc #-} calloc :: Storable a => IO (Ptr a) calloc = doCalloc undefined where doCalloc :: Storable b => b -> IO (Ptr b) doCalloc dummy = callocBytes (sizeOf dummy) -- |Llike 'mallocBytes' but memory is filled with bytes of value zero. -- callocBytes :: Int -> IO (Ptr a) callocBytes size = failWhenNULL "calloc" $ _calloc 1 (fromIntegral size) -- asserts that the pointer returned from the action in the second argument is -- non-null -- failWhenNULL :: String -> IO (Ptr a) -> IO (Ptr a) failWhenNULL name f = do addr <- f if addr == nullPtr then ioError (IOError Nothing ResourceExhausted name "out of memory" Nothing Nothing) else return addr foreign import ccall unsafe "stdlib.h calloc" _calloc :: CSize -> CSize -> IO (Ptr a) #endif base-compat-0.9.3/src/Foreign/Marshal/Unsafe/0000755000000000000000000000000013072705326017101 5ustar0000000000000000base-compat-0.9.3/src/Foreign/Marshal/Unsafe/Compat.hs0000644000000000000000000000040713072705326020661 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Foreign.Marshal.Unsafe.Compat ( -- * Unsafe functions unsafeLocalState ) where #if MIN_VERSION_base(4,6,0) import Foreign.Marshal.Unsafe (unsafeLocalState) #else import Foreign.Marshal (unsafeLocalState) #endif base-compat-0.9.3/src/Foreign/Marshal/Array/0000755000000000000000000000000013072705326016736 5ustar0000000000000000base-compat-0.9.3/src/Foreign/Marshal/Array/Compat.hs0000644000000000000000000000143713072705326020522 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Foreign.Marshal.Array.Compat ( module Base , callocArray , callocArray0 ) where import Foreign.Marshal.Array as Base #if !(MIN_VERSION_base(4,8,0)) import Foreign.Marshal.Alloc.Compat import Foreign.Ptr (Ptr) import Foreign.Storable (Storable(..)) import Prelude.Compat -- |Like 'mallocArray', but allocated memory is filled with bytes of value zero. -- callocArray :: Storable a => Int -> IO (Ptr a) callocArray = doCalloc undefined where doCalloc :: Storable a' => a' -> Int -> IO (Ptr a') doCalloc dummy size = callocBytes (size * sizeOf dummy) -- |Like 'callocArray0', but allocated memory is filled with bytes of value -- zero. -- callocArray0 :: Storable a => Int -> IO (Ptr a) callocArray0 size = callocArray (size + 1) #endif base-compat-0.9.3/src/Foreign/Marshal/Utils/0000755000000000000000000000000013072705326016760 5ustar0000000000000000base-compat-0.9.3/src/Foreign/Marshal/Utils/Compat.hs0000644000000000000000000000117413072705326020542 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} {-# LANGUAGE ForeignFunctionInterface #-} module Foreign.Marshal.Utils.Compat ( module Base , fillBytes ) where import Foreign.Marshal.Utils as Base #if !(MIN_VERSION_base(4,8,0)) import Data.Word (Word8) import Foreign.C.Types import Foreign.Ptr import Prelude -- |Fill a given number of bytes in memory area with a byte value. -- -- /Since: 4.8.0.0/ fillBytes :: Ptr a -> Word8 -> Int -> IO () fillBytes dest char size = do _ <- memset dest (fromIntegral char) (fromIntegral size) return () foreign import ccall unsafe "string.h" memset :: Ptr a -> CInt -> CSize -> IO (Ptr a) #endif base-compat-0.9.3/src/Foreign/Marshal/Safe/0000755000000000000000000000000013072705326016536 5ustar0000000000000000base-compat-0.9.3/src/Foreign/Marshal/Safe/Compat.hs0000644000000000000000000000105513072705326020316 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Foreign.Marshal.Safe.Compat ( -- | The module "Foreign.Marshal.Safe" re-exports the other modules in the -- @Foreign.Marshal@ hierarchy: module Foreign.Marshal.Alloc , module Foreign.Marshal.Array , module Foreign.Marshal.Error , module Foreign.Marshal.Pool , module Foreign.Marshal.Utils ) where import Foreign.Marshal.Alloc import Foreign.Marshal.Array import Foreign.Marshal.Error import Foreign.Marshal.Pool import Foreign.Marshal.Utils base-compat-0.9.3/src/Foreign/ForeignPtr/0000755000000000000000000000000013072705326016350 5ustar0000000000000000base-compat-0.9.3/src/Foreign/ForeignPtr/Compat.hs0000644000000000000000000000167313072705326020136 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} {-# LANGUAGE MagicHash #-} module Foreign.ForeignPtr.Compat ( module Base , plusForeignPtr ) where import Foreign.ForeignPtr as Base #if !(MIN_VERSION_base(4,10,0)) import GHC.Exts (Int(..), plusAddr#) import GHC.ForeignPtr (ForeignPtr(..)) plusForeignPtr :: ForeignPtr a -> Int -> ForeignPtr b -- ^Advances the given address by the given offset in bytes. -- -- The new 'ForeignPtr' shares the finalizer of the original, -- equivalent from a finalization standpoint to just creating another -- reference to the original. That is, the finalizer will not be -- called before the new 'ForeignPtr' is unreachable, nor will it be -- called an additional time due to this call, and the finalizer will -- be called with the same address that it would have had this call -- not happened, *not* the new address. -- -- /Since: 4.10.0.0/ plusForeignPtr (ForeignPtr addr c) (I# d) = ForeignPtr (plusAddr# addr d) c #endif base-compat-0.9.3/src/Foreign/ForeignPtr/Unsafe/0000755000000000000000000000000013072705326017571 5ustar0000000000000000base-compat-0.9.3/src/Foreign/ForeignPtr/Unsafe/Compat.hs0000644000000000000000000000045313072705326021352 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Foreign.ForeignPtr.Unsafe.Compat ( -- ** Unsafe low-level operations unsafeForeignPtrToPtr ) where #if MIN_VERSION_base(4,6,0) import Foreign.ForeignPtr.Unsafe (unsafeForeignPtrToPtr) #else import Foreign.ForeignPtr (unsafeForeignPtrToPtr) #endif base-compat-0.9.3/src/Foreign/ForeignPtr/Safe/0000755000000000000000000000000013072705326017226 5ustar0000000000000000base-compat-0.9.3/src/Foreign/ForeignPtr/Safe/Compat.hs0000644000000000000000000000154113072705326021006 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Foreign.ForeignPtr.Safe.Compat ( -- * Finalised data pointers ForeignPtr , FinalizerPtr #if defined(__HUGS__) || defined(__GLASGOW_HASKELL__) , FinalizerEnvPtr #endif -- ** Basic operations , newForeignPtr , newForeignPtr_ , addForeignPtrFinalizer #if defined(__HUGS__) || defined(__GLASGOW_HASKELL__) , newForeignPtrEnv , addForeignPtrFinalizerEnv #endif , withForeignPtr #ifdef __GLASGOW_HASKELL__ , finalizeForeignPtr #endif -- ** Low-level operations , touchForeignPtr , castForeignPtr -- ** Allocating managed memory , mallocForeignPtr , mallocForeignPtrBytes , mallocForeignPtrArray , mallocForeignPtrArray0 ) where import Foreign.ForeignPtr base-compat-0.9.3/src/System/0000755000000000000000000000000013072705326014164 5ustar0000000000000000base-compat-0.9.3/src/System/IO/0000755000000000000000000000000013072705326014473 5ustar0000000000000000base-compat-0.9.3/src/System/IO/Unsafe/0000755000000000000000000000000013072705326015714 5ustar0000000000000000base-compat-0.9.3/src/System/IO/Unsafe/Compat.hs0000644000000000000000000000155413072705326017500 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module System.IO.Unsafe.Compat ( module Base , unsafeFixIO , unsafeDupablePerformIO ) where import System.IO.Unsafe as Base #if !(MIN_VERSION_base(4,5,0)) import Control.Exception import Data.IORef import GHC.Base import GHC.IO -- | A slightly faster version of `System.IO.fixIO` that may not be -- safe to use with multiple threads. The unsafety arises when used -- like this: -- -- > unsafeFixIO $ \r -> do -- > forkIO (print r) -- > return (...) -- -- In this case, the child thread will receive a @NonTermination@ -- exception instead of waiting for the value of @r@ to be computed. -- -- /Since: 4.5.0.0/ unsafeFixIO :: (a -> IO a) -> IO a unsafeFixIO k = do ref <- newIORef (throw NonTermination) ans <- unsafeDupableInterleaveIO (readIORef ref) result <- k ans writeIORef ref result return result #endif base-compat-0.9.3/src/System/Environment/0000755000000000000000000000000013072705326016470 5ustar0000000000000000base-compat-0.9.3/src/System/Environment/Compat.hs0000644000000000000000000001015013072705326020244 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} {-# LANGUAGE ForeignFunctionInterface #-} -- | Miscellaneous information about the system environment. module System.Environment.Compat ( getArgs , getProgName , getEnv , lookupEnv , setEnv , unsetEnv , withArgs , withProgName , getEnvironment ) where import System.Environment #if !(MIN_VERSION_base(4,7,0)) import Prelude.Compat # ifdef mingw32_HOST_OS import Control.Monad import Foreign.C import Foreign.Safe import GHC.Windows # else import qualified System.Posix.Env as Posix # endif # ifdef mingw32_HOST_OS # if defined(i386_HOST_ARCH) # define WINDOWS_CCONV stdcall # elif defined(x86_64_HOST_ARCH) # define WINDOWS_CCONV ccall # else # error Unknown mingw32 arch # endif foreign import WINDOWS_CCONV unsafe "windows.h GetLastError" c_GetLastError:: IO DWORD eRROR_ENVVAR_NOT_FOUND :: DWORD eRROR_ENVVAR_NOT_FOUND = 203 # endif # if !(MIN_VERSION_base(4,6,0)) -- | Return the value of the environment variable @var@, or @Nothing@ if -- there is no such value. -- -- For POSIX users, this is equivalent to 'System.Posix.Env.getEnv'. lookupEnv :: String -> IO (Maybe String) lookupEnv k = lookup k `fmap` getEnvironment # endif -- | @setEnv name value@ sets the specified environment variable to @value@. -- -- On Windows setting an environment variable to the /empty string/ removes -- that environment variable from the environment. For the sake of -- compatibility we adopt that behavior. In particular -- -- @ -- setEnv name \"\" -- @ -- -- has the same effect as -- -- @ -- `unsetEnv` name -- @ -- -- If you don't care about Windows support and want to set an environment -- variable to the empty string use @System.Posix.Env.setEnv@ from the @unix@ -- package instead. -- -- Throws `Control.Exception.IOException` if @name@ is the empty string or -- contains an equals sign. -- -- Note that setting Unicode values may not work correctly on versions of GHC -- prior to 7.2. setEnv :: String -> String -> IO () setEnv key value_ | null value = unsetEnv key | otherwise = setEnv_ key value where -- NOTE: Anything that follows NUL is ignored on both POSIX and Windows. -- We still strip it manually so that the null check above succeds if a -- value starts with NUL, and `unsetEnv` is called. This is important for -- two reasons. -- -- * On POSIX setting an environment variable to the empty string does not -- remove it. -- -- * On Windows setting an environment variable to the empty string -- removes that environment variable. A subsequent call to -- GetEnvironmentVariable will then return 0, but the calling thread's -- last-error code will not be updated, and hence a call to GetLastError -- may not return ERROR_ENVVAR_NOT_FOUND. The failed lookup will then -- result in a random error instead of the expected -- `isDoesNotExistError` (this is at least true for Windows XP, SP 3). -- Explicitly calling `unsetEnv` prevents this. value = takeWhile (/= '\NUL') value_ setEnv_ :: String -> String -> IO () # ifdef mingw32_HOST_OS setEnv_ key value = withCWString key $ \k -> withCWString value $ \v -> do success <- c_SetEnvironmentVariable k v unless success (throwGetLastError "setEnv") foreign import WINDOWS_CCONV unsafe "windows.h SetEnvironmentVariableW" c_SetEnvironmentVariable :: LPTSTR -> LPTSTR -> IO Bool # else setEnv_ k v = Posix.setEnv k v True # endif -- | @unsetEnv name@ removes the specified environment variable from the -- environment of the current process. -- -- Throws `Control.Exception.IOException` if @name@ is the empty string or -- contains an equals sign. unsetEnv :: String -> IO () # ifdef mingw32_HOST_OS unsetEnv key = withCWString key $ \k -> do success <- c_SetEnvironmentVariable k nullPtr unless success $ do -- We consider unsetting an environment variable that does not exist not as -- an error, hence we ignore eRROR_ENVVAR_NOT_FOUND. err <- c_GetLastError unless (err == eRROR_ENVVAR_NOT_FOUND) $ do throwGetLastError "unsetEnv" # else unsetEnv = Posix.unsetEnv # endif #endif base-compat-0.9.3/src/System/Exit/0000755000000000000000000000000013072705326015075 5ustar0000000000000000base-compat-0.9.3/src/System/Exit/Compat.hs0000644000000000000000000000060713072705326016657 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} {-# LANGUAGE CPP #-} module System.Exit.Compat ( module Base , die ) where import System.Exit as Base #if !(MIN_VERSION_base(4,8,0)) import Prelude.Compat import System.IO -- | Write given error message to `stderr` and terminate with `exitFailure`. -- -- @since 4.8.0.0 die :: String -> IO a die err = hPutStrLn stderr err >> exitFailure #endif base-compat-0.9.3/src/Prelude/0000755000000000000000000000000013072705326014300 5ustar0000000000000000base-compat-0.9.3/src/Prelude/Compat.hs0000644000000000000000000000614213072705326016062 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Prelude.Compat ( #if MIN_VERSION_base(4,9,0) module Base #else either , all , and , any , concat , concatMap , mapM_ , notElem , or , sequence_ , (<$>) , maybe , lines , unlines , unwords , words , curry , fst , snd , uncurry , ($!) , (++) , (.) , (=<<) , asTypeOf , const , flip , id , map , otherwise , until , ioError , userError , (!!) , break , cycle , drop , dropWhile , filter , head , init , iterate , last , lookup , repeat , replicate , reverse , scanl , scanl1 , scanr , scanr1 , span , splitAt , tail , take , takeWhile , unzip , unzip3 , zip , zip3 , zipWith , zipWith3 , subtract , lex , readParen , (^) , (^^) , even , fromIntegral , gcd , lcm , odd , realToFrac , showChar , showParen , showString , shows , appendFile , getChar , getContents , getLine , interact , print , putChar , putStr , putStrLn , readFile , readIO , readLn , writeFile , read , reads , (&&) , not , (||) , ($) , error , errorWithoutStackTrace , undefined , seq , elem , foldMap , foldl , foldl1 , foldr , foldr1 , length , maximum , minimum , null , product , sum , mapM , sequence , sequenceA , traverse , (*>) , (<*) , (<*>) , pure , (<$) , fmap , (>>) , (>>=) , fail , return , mappend , mconcat , mempty , maxBound , minBound , enumFrom , enumFromThen , enumFromThenTo , enumFromTo , fromEnum , pred , succ , toEnum , (**) , acos , acosh , asin , asinh , atan , atanh , cos , cosh , exp , log , logBase , pi , sin , sinh , sqrt , tan , tanh , atan2 , decodeFloat , encodeFloat , exponent , floatDigits , floatRadix , floatRange , isDenormalized , isIEEE , isInfinite , isNaN , isNegativeZero , scaleFloat , significand , (*) , (+) , (-) , abs , negate , signum , readList , readsPrec , (/) , fromRational , recip , div , divMod , mod , quot , quotRem , rem , toInteger , toRational , ceiling , floor , properFraction , round , truncate , show , showList , showsPrec , (/=) , (==) , (<) , (<=) , (>) , (>=) , compare , max , min -- classes , Applicative , Bounded , Enum , Eq , Floating , Foldable , Fractional , Functor , Integral , Monad , Monoid , Num (fromInteger) , Ord , Read , Real , RealFloat , RealFrac , Show , Traversable -- data types , IO , Char , Double , Float , Int , Integer , Word , Bool (True, False) , Either(Left, Right) , Maybe(Just, Nothing) , Ordering (EQ, GT, LT) -- type synonyms , FilePath , IOError , Rational , ReadS , ShowS , String #endif ) where #if MIN_VERSION_base(4,9,0) import Prelude as Base #else import Prelude hiding ( length , null , foldr , mapM , sequence , all , and , any , concat , concatMap , mapM , mapM_ , notElem , or , sequence , sequence_ , elem , foldl , foldl1 , foldr1 , maximum , minimum , product , sum ) import Data.Foldable.Compat import Data.Traversable # if !(MIN_VERSION_base(4,8,0)) import Control.Applicative import Data.Monoid import Data.Word # endif #endif #if !(MIN_VERSION_base(4,9,0)) -- | A variant of 'error' that does not produce a stack trace. -- -- /Since: 4.9.0.0/ errorWithoutStackTrace :: [Char] -> a errorWithoutStackTrace s = error s {-# NOINLINE errorWithoutStackTrace #-} #endif base-compat-0.9.3/src/Debug/0000755000000000000000000000000013072705326013726 5ustar0000000000000000base-compat-0.9.3/src/Debug/Trace/0000755000000000000000000000000013072705326014764 5ustar0000000000000000base-compat-0.9.3/src/Debug/Trace/Compat.hs0000644000000000000000000000332413072705326016545 0ustar0000000000000000{-# LANGUAGE CPP, NoImplicitPrelude #-} module Debug.Trace.Compat ( module Base , traceId , traceShowId , traceM , traceShowM ) where #if !(MIN_VERSION_base(4,7,0)) || MIN_VERSION_base(4,9,0) import Debug.Trace as Base #else import Debug.Trace as Base hiding ( traceM , traceShowM ) #endif #if !(MIN_VERSION_base(4,9,0)) import Prelude.Compat #endif #if !(MIN_VERSION_base(4,7,0)) {-| Like 'trace' but returns the message instead of a third value. /Since: 4.7.0.0/ -} traceId :: String -> String traceId a = trace a a {-| Like 'traceShow' but returns the shown value instead of a third value. /Since: 4.7.0.0/ -} traceShowId :: (Show a) => a -> a traceShowId a = trace (show a) a #endif #if !(MIN_VERSION_base(4,9,0)) {-| Like 'trace' but returning unit in an arbitrary 'Applicative' context. Allows for convenient use in do-notation. Note that the application of 'traceM' is not an action in the 'Applicative' context, as 'traceIO' is in the 'IO' type. While the fresh bindings in the following example will force the 'traceM' expressions to be reduced every time the @do@-block is executed, @traceM "not crashed"@ would only be reduced once, and the message would only be printed once. If your monad is in 'MonadIO', @liftIO . traceIO@ may be a better option. > ... = do > x <- ... > traceM $ "x: " ++ show x > y <- ... > traceM $ "y: " ++ show y /Since: 4.7.0.0/ -} traceM :: (Applicative f) => String -> f () traceM string = trace string $ pure () {-| Like 'traceM', but uses 'show' on the argument to convert it to a 'String'. > ... = do > x <- ... > traceShowM $ x > y <- ... > traceShowM $ x + y /Since: 4.7.0.0/ -} traceShowM :: (Show a, Applicative f) => a -> f () traceShowM = traceM . show #endif base-compat-0.9.3/test/0000755000000000000000000000000013072705326013070 5ustar0000000000000000base-compat-0.9.3/test/Spec.hs0000644000000000000000000000005413072705326014315 0ustar0000000000000000{-# OPTIONS_GHC -F -pgmF hspec-discover #-} base-compat-0.9.3/test/Text/0000755000000000000000000000000013072705326014014 5ustar0000000000000000base-compat-0.9.3/test/Text/Read/0000755000000000000000000000000013072705326014667 5ustar0000000000000000base-compat-0.9.3/test/Text/Read/CompatSpec.hs0000644000000000000000000000117613072705326017266 0ustar0000000000000000module Text.Read.CompatSpec (main, spec) where import Test.Hspec import Text.Read.Compat main :: IO () main = hspec spec spec :: Spec spec = do describe "readMaybe" $ do it "parses a value" $ do readMaybe "23" `shouldBe` (Just 23 :: Maybe Int) it "returns Nothing if parsing fails" $ do readMaybe "xx" `shouldBe` (Nothing :: Maybe Int) describe "readEither" $ do it "parses a value" $ do readEither "23" `shouldBe` (Right 23 :: Either String Int) it "returns Left if parsing fails" $ do readEither "xx" `shouldBe` (Left "Prelude.read: no parse" :: Either String Int) base-compat-0.9.3/test/Control/0000755000000000000000000000000013072705326014510 5ustar0000000000000000base-compat-0.9.3/test/Control/Monad/0000755000000000000000000000000013072705326015546 5ustar0000000000000000base-compat-0.9.3/test/Control/Monad/CompatSpec.hs0000644000000000000000000000055613072705326020146 0ustar0000000000000000module Control.Monad.CompatSpec (main, spec) where import Test.Hspec import Control.Monad.Compat import Prelude () import Prelude.Compat main :: IO () main = hspec spec spec :: Spec spec = do describe "(<$!>)" $ do it "is a strict version of (<$>)" $ do not <$!> [True, False] `shouldBe` not <$> [True, False] base-compat-0.9.3/test/Data/0000755000000000000000000000000013072705326013741 5ustar0000000000000000base-compat-0.9.3/test/Data/Bits/0000755000000000000000000000000013072705326014642 5ustar0000000000000000base-compat-0.9.3/test/Data/Bits/CompatSpec.hs0000644000000000000000000000237013072705326017236 0ustar0000000000000000{-# LANGUAGE CPP #-} module Data.Bits.CompatSpec (main, spec) where import Test.Hspec import Data.Bits.Compat main :: IO () main = hspec spec spec :: Spec spec = do describe "bitDefault" $ it "sets the ith bit with all other bits clear" $ do bitDefault 0 `shouldBe` (1 :: Int) bitDefault 1 `shouldBe` (2 :: Int) bitDefault 2 `shouldBe` (4 :: Int) bitDefault 3 `shouldBe` (8 :: Int) describe "testBitDefault" $ it "returns True if the nth bit of the argument is 1" $ do testBitDefault (10 :: Int) 0 `shouldBe` False testBitDefault (10 :: Int) 1 `shouldBe` True testBitDefault (10 :: Int) 2 `shouldBe` False testBitDefault (10 :: Int) 3 `shouldBe` True describe "popCountDefault" $ it "returns the number of set bits in the argument" $ do popCountDefault (0 :: Int) `shouldBe` 0 popCountDefault (1 :: Int) `shouldBe` 1 popCountDefault (10 :: Int) `shouldBe` 2 #if MIN_VERSION_base(4,7,0) describe "toIntegralSized" $ it "converts an Integral type to another as measured by bitSizeMaybe" $ do toIntegralSized (42 :: Integer) `shouldBe` (Just 42 :: Maybe Int) toIntegralSized (12345678901234567890 :: Integer) `shouldBe` (Nothing :: Maybe Int) #endif base-compat-0.9.3/test/Data/Monoid/0000755000000000000000000000000013072705326015166 5ustar0000000000000000base-compat-0.9.3/test/Data/Monoid/CompatSpec.hs0000644000000000000000000000054413072705326017563 0ustar0000000000000000module Data.Monoid.CompatSpec (main, spec) where import Test.Hspec import Test.QuickCheck import Data.Monoid.Compat main :: IO () main = hspec spec spec :: Spec spec = do describe "<>" $ do it "is an infix synonym for mappend" $ do property $ \xs ys -> do xs <> ys `shouldBe` (mappend xs ys :: String) base-compat-0.9.3/test/Data/STRef/0000755000000000000000000000000013072705326014724 5ustar0000000000000000base-compat-0.9.3/test/Data/STRef/CompatSpec.hs0000644000000000000000000000072013072705326017315 0ustar0000000000000000module Data.STRef.CompatSpec (main, spec) where import Test.Hspec import Control.Monad import Control.Monad.ST import Data.STRef.Compat main :: IO () main = hspec spec spec :: Spec spec = describe "modifySTRef'" $ it "should mutate the contents of an STRef strictly" $ shouldBe (1000000 :: Int) $ runST $ do ref <- newSTRef 0 replicateM_ 1000000 $ modifySTRef' ref (+1) readSTRef ref base-compat-0.9.3/test/Data/List/0000755000000000000000000000000013072705326014654 5ustar0000000000000000base-compat-0.9.3/test/Data/List/CompatSpec.hs0000644000000000000000000000306113072705326017246 0ustar0000000000000000module Data.List.CompatSpec (main, spec) where import Test.Hspec import Data.List.Compat data Asymmetric = A | B deriving Show instance Eq Asymmetric where A == _ = True B == _ = False main :: IO () main = hspec spec spec :: Spec spec = do describe "dropWhileEnd" $ do it "drops the largest suffix of a list in which a predicate holds for all elements" $ do dropWhileEnd (== ' ') "foo " `shouldBe` "foo" dropWhileEnd (== ' ') "foo bar" `shouldBe` "foo bar" describe "isSubsequenceOf" $ do it "returns True if the first list is a subsequence of the second list" $ do isSubsequenceOf "GHC" "The Glorious Haskell Compiler" `shouldBe` True isSubsequenceOf "JHC" "The Glorious Haskell Compiler" `shouldBe` False describe "nub" $ it "preserves the order of arguments to (==)" $ nub [A, B] `shouldBe` [A] describe "nubBy" $ it "preserves the order of arguments to the equality function" $ nubBy (<) "12" `shouldBe` "1" describe "sortOn" $ do it "sorts a list by comparing the results of a key function applied to each element" $ do sortOn (>='b') "cba" `shouldBe` "acb" describe "uncons" $ do it "decomposes a list into its head and tail" $ do uncons "" `shouldBe` Nothing uncons "12" `shouldBe` Just ('1', "2") describe "union" $ it "nubs arguments in the same order as (==)" $ do union [A] [A, B] `shouldBe` [A] describe "unionBy" $ it "nubs arguments in the same order as nubBy's equality function" $ do unionBy (<) "1" "21" `shouldBe` "11" base-compat-0.9.3/test/Data/Word/0000755000000000000000000000000013072705326014654 5ustar0000000000000000base-compat-0.9.3/test/Data/Word/CompatSpec.hs0000644000000000000000000000132113072705326017243 0ustar0000000000000000module Data.Word.CompatSpec (main, spec) where import Test.Hspec import Data.Word.Compat main :: IO () main = hspec spec spec :: Spec spec = do describe "byteSwap16" $ it "reverses the order of bytes in a Word16 value" $ do byteSwap16 0x1100 `shouldBe` 0x0011 byteSwap16 0x1010 `shouldBe` 0x1010 describe "byteSwap32" $ it "reverses the order of bytes in a Word32 value" $ do byteSwap32 0x11001010 `shouldBe` 0x10100011 byteSwap32 0x10101111 `shouldBe` 0x11111010 describe "byteSwap64" $ it "reverses the order of bytes in a Word64 value" $ do byteSwap64 0x1010111110101111 `shouldBe` 0x1111101011111010 byteSwap64 0x1100000000000011 `shouldBe` 0x1100000000000011 base-compat-0.9.3/test/Data/Either/0000755000000000000000000000000013072705326015161 5ustar0000000000000000base-compat-0.9.3/test/Data/Either/CompatSpec.hs0000644000000000000000000000124113072705326017551 0ustar0000000000000000module Data.Either.CompatSpec (main, spec) where import Test.Hspec import Data.Either.Compat main :: IO () main = hspec spec spec :: Spec spec = do describe "isLeft" $ do it "returns True for a Left value" $ do isLeft (Left "23" :: Either String String) `shouldBe` True it "returns False for a Right value" $ do isLeft (Right "23" :: Either String String) `shouldBe` False describe "isRight" $ do it "returns False for a Left value" $ do isRight (Left "23" :: Either String String) `shouldBe` False it "returns True for a Right value" $ do isRight (Right "23" :: Either String String) `shouldBe` True base-compat-0.9.3/test/Data/IORef/0000755000000000000000000000000013072705326014705 5ustar0000000000000000base-compat-0.9.3/test/Data/IORef/CompatSpec.hs0000644000000000000000000000122213072705326017274 0ustar0000000000000000module Data.IORef.CompatSpec (main, spec) where import Test.Hspec import Control.Monad import Data.IORef.Compat main :: IO () main = hspec spec spec :: Spec spec = do describe "modifyIORef'" $ it "mutates the contents of an IORef strictly" $ do ref <- newIORef 0 replicateM_ 1000000 $ modifyIORef' ref (+1) readIORef ref `shouldReturn` (1000000 :: Int) describe "atomicModifyIORef'" $ it "atomically modifies the contents of an IORef strictly" $ do ref <- newIORef 0 replicateM_ 1000000 . atomicModifyIORef' ref $ \n -> (n+1, ()) readIORef ref `shouldReturn` (1000000 :: Int) base-compat-0.9.3/test/Data/Functor/0000755000000000000000000000000013072705326015361 5ustar0000000000000000base-compat-0.9.3/test/Data/Functor/CompatSpec.hs0000644000000000000000000000064013072705326017753 0ustar0000000000000000module Data.Functor.CompatSpec (main, spec) where import Test.Hspec import Data.Functor.Compat main :: IO () main = hspec spec spec :: Spec spec = do describe "void" $ do it "discards computation result" $ do void (return 1 :: IO Int) `shouldReturn` () describe "$>" $ do it "is the same as flipped <$" $ do (Just 5 :: Maybe Int) $> 6 `shouldBe` (Just 6 :: Maybe Int) base-compat-0.9.3/test/Data/Bool/0000755000000000000000000000000013072705326014634 5ustar0000000000000000base-compat-0.9.3/test/Data/Bool/CompatSpec.hs0000644000000000000000000000063013072705326017225 0ustar0000000000000000module Data.Bool.CompatSpec (main, spec) where import Test.Hspec import Data.Bool.Compat main :: IO () main = hspec spec spec :: Spec spec = do describe "bool" $ do it "evaluates to first parameter if condition is False" $ do bool "KO" "OK" False `shouldBe` "KO" it "evaluates to second parameter if condition is True" $ do bool "KO" "OK" True `shouldBe` "OK" base-compat-0.9.3/test/Data/Function/0000755000000000000000000000000013072705326015526 5ustar0000000000000000base-compat-0.9.3/test/Data/Function/CompatSpec.hs0000644000000000000000000000042313072705326020117 0ustar0000000000000000module Data.Function.CompatSpec (main, spec) where import Test.Hspec import Data.Function.Compat main :: IO () main = hspec spec spec :: Spec spec = do describe "&" $ do it "reverses function application" $ do (False & not) `shouldBe` True base-compat-0.9.3/test/Data/Version/0000755000000000000000000000000013072705326015366 5ustar0000000000000000base-compat-0.9.3/test/Data/Version/CompatSpec.hs0000644000000000000000000000040113072705326017753 0ustar0000000000000000module Data.Version.CompatSpec (spec) where import Test.Hspec import Data.Version.Compat spec :: Spec spec = do describe "makeVersion" $ it "constructs a tagless Version" $ makeVersion [1,2,3] `shouldBe` Version [1,2,3] [] base-compat-0.9.3/test/Data/Foldable/0000755000000000000000000000000013072705326015451 5ustar0000000000000000base-compat-0.9.3/test/Data/Foldable/CompatSpec.hs0000644000000000000000000000045713072705326020051 0ustar0000000000000000module Data.Foldable.CompatSpec (main, spec) where import Test.Hspec import Data.Foldable.Compat main :: IO () main = hspec spec spec :: Spec spec = do describe "maximumBy" $ do it "runs in constant space" $ do maximumBy compare [1..10000] `shouldBe` (10000 :: Int) base-compat-0.9.3/test/Numeric/0000755000000000000000000000000013072705326014472 5ustar0000000000000000base-compat-0.9.3/test/Numeric/CompatSpec.hs0000644000000000000000000000226313072705326017067 0ustar0000000000000000module Numeric.CompatSpec (main, spec) where import Test.Hspec import Numeric.Compat main :: IO () main = hspec spec spec :: Spec spec = do describe "showFFloatAlt" $ do it "shows a RealFloat value, always using decimal notation" $ showFFloatAlt Nothing (12 :: Double) "" `shouldBe` "12.0" it "allows to specify the number of decimal places" $ showFFloatAlt (Just 4) (12 :: Double) "" `shouldBe` "12.0000" describe "showGFloatAlt" $ do it "shows a RealFloat value, using decimal notation if the absolute value lies between 0.1 and 9,999,999" $ showGFloatAlt Nothing (12 :: Double) "" `shouldBe` "12.0" it "shows a RealFloat value, using decimal notation and specifying the number of decimal places" $ showGFloatAlt (Just 4) (12 :: Double) "" `shouldBe` "12.0000" it "shows a RealFloat value, using scientific notation if the absolute value falls outside of the range" $ showGFloatAlt Nothing (1234567890 :: Double) "" `shouldBe` "1.23456789e9" it "shows a RealFloat value, using scientific notation and specifying the number of decimal places" $ showGFloatAlt (Just 4) (1234567890 :: Double) "" `shouldBe` "1.2346e9" base-compat-0.9.3/test/Foreign/0000755000000000000000000000000013072705326014461 5ustar0000000000000000base-compat-0.9.3/test/Foreign/Marshal/0000755000000000000000000000000013072705326016050 5ustar0000000000000000base-compat-0.9.3/test/Foreign/Marshal/Alloc/0000755000000000000000000000000013072705326017102 5ustar0000000000000000base-compat-0.9.3/test/Foreign/Marshal/Alloc/CompatSpec.hs0000644000000000000000000000064513072705326021501 0ustar0000000000000000module Foreign.Marshal.Alloc.CompatSpec (main, spec) where import Test.Hspec import Control.Exception import Foreign.Marshal.Alloc.Compat import Foreign.Storable main :: IO () main = hspec spec spec :: Spec spec = do describe "calloc" $ it "allocates memory with bytes of value zero" $ do bracket calloc free $ \ptr -> do peek ptr `shouldReturn` (0 :: Int) base-compat-0.9.3/test/Foreign/Marshal/Utils/0000755000000000000000000000000013072705326017150 5ustar0000000000000000base-compat-0.9.3/test/Foreign/Marshal/Utils/CompatSpec.hs0000644000000000000000000000073213072705326021544 0ustar0000000000000000module Foreign.Marshal.Utils.CompatSpec (main, spec) where import Test.Hspec import Foreign.Marshal.Alloc import Foreign.Marshal.Utils.Compat import Foreign.Ptr import Foreign.Storable main :: IO () main = hspec spec spec :: Spec spec = do describe "fillBytes" $ it "fills a given number of bytes in memory area with a byte value" $ do alloca $ \ptr -> do let _ = ptr :: Ptr Int fillBytes ptr 0 $ sizeOf ptr peek ptr `shouldReturn` 0 base-compat-0.9.3/test/System/0000755000000000000000000000000013072705326014354 5ustar0000000000000000base-compat-0.9.3/test/System/Environment/0000755000000000000000000000000013072705326016660 5ustar0000000000000000base-compat-0.9.3/test/System/Environment/CompatSpec.hs0000644000000000000000000000745313072705326021263 0ustar0000000000000000{-# LANGUAGE CPP #-} module System.Environment.CompatSpec (main, spec) where import Test.Hspec import Test.QuickCheck import qualified Control.Exception as E import GHC.IO.Exception (IOErrorType (InvalidArgument)) import System.Environment.Compat import System.IO.Error main :: IO () main = hspec spec withEnv :: String -> String -> IO a -> IO a withEnv k v action = E.bracket save restore $ \_ -> do setEnv k v >> action where save = lookupEnv k restore = maybe (unsetEnv k) (setEnv k) withoutEnv :: String -> IO a -> IO a withoutEnv k action = E.bracket save restore $ \_ -> do unsetEnv k >> action where save = lookupEnv k restore = maybe (unsetEnv k) (setEnv k) spec :: Spec spec = do describe "lookupEnv" $ do it "returns specified environment variable" $ do withEnv "FOOBAR" "23" $ do lookupEnv "FOOBAR" `shouldReturn` Just "23" it "returns Nothing if specified environment variable is not set" $ do withoutEnv "FOOBAR" $ do lookupEnv "FOOBAR" `shouldReturn` Nothing describe "unsetEnv" $ do it "removes specified environment variable" $ do setEnv "FOO" "foo" unsetEnv "FOO" getEnv "FOO" `shouldThrow` isDoesNotExistError it "does nothing if specified environment variable is not set" $ do unsetEnv "BAR" unsetEnv "BAR" getEnv "BAR" `shouldThrow` isDoesNotExistError it "throws an exception if key is the empty string" $ do unsetEnv "" `shouldThrow` (== InvalidArgument) . ioeGetErrorType it "throws an exception if key contains '='" $ do unsetEnv "some=key" `shouldThrow` (== InvalidArgument) . ioeGetErrorType it "works for arbitrary keys" $ property $ \k -> ('\NUL' `notElem` k && '=' `notElem` k && (not . null) k) ==> do setEnv k "foo" unsetEnv k getEnv k `shouldThrow` isDoesNotExistError describe "setEnv" $ do it "sets specified environment variable to given value" $ do unsetEnv "FOO" setEnv "FOO" "foo" getEnv "FOO" `shouldReturn` "foo" it "resets specified environment variable, if it is already set" $ do unsetEnv "FOO" setEnv "FOO" "foo" setEnv "FOO" "bar" getEnv "FOO" `shouldReturn` "bar" it "removes specified environment variable when value is the empty string" $ do setEnv "FOO" "foo" setEnv "FOO" "" getEnv "FOO" `shouldThrow` isDoesNotExistError it "removes specified environment variable when first character of value is NUL" $ do setEnv "FOO" "foo" setEnv "FOO" "\NULfoo" getEnv "FOO" `shouldThrow` isDoesNotExistError it "truncates value at NUL character" $ do unsetEnv "FOO" setEnv "FOO" "foo\NULbar" getEnv "FOO" `shouldReturn` "foo" it "truncates key at NUL character" $ do unsetEnv "FOO" setEnv "FOO\NULBAR" "foo" getEnv "FOO" `shouldReturn` "foo" #if __GLASGOW_HASKELL__ >= 702 it "works for unicode" $ do unsetEnv "FOO" setEnv "FOO" "foo-\955-bar" getEnv "FOO" `shouldReturn` "foo-\955-bar" #endif it "works for arbitrary values" $ property $ \v -> ('\NUL' `notElem` v && (not . null) v) ==> do setEnv "FOO" v getEnv "FOO" `shouldReturn` v it "works for unicode keys" $ do setEnv "foo-\955-bar" "foo" getEnv "foo-\955-bar" `shouldReturn` "foo" it "throws an exception if key is the empty string" $ do setEnv "" "foo" `shouldThrow` (== InvalidArgument) . ioeGetErrorType it "throws an exception if key contains '='" $ do setEnv "some=key" "foo" `shouldThrow` (== InvalidArgument) . ioeGetErrorType it "works for arbitrary keys" $ property $ \k -> ('\NUL' `notElem` k && '=' `notElem` k && (not . null) k) ==> do setEnv k "foo" getEnv k `shouldReturn` "foo"